chore: initial import
This commit is contained in:
112
AppConfig.py
Normal file
112
AppConfig.py
Normal file
@@ -0,0 +1,112 @@
|
||||
import json
|
||||
import os
|
||||
|
||||
|
||||
promptsFolderPath = os.path.join(os.path.dirname(__file__), "prompts")
|
||||
schemaTemplateName = "prompt_schema.template.json"
|
||||
defaultPromptsName = "defaultPrompts.json"
|
||||
toolInstructionsName = "tool_instructions.md"
|
||||
toolInstructionsPath = os.path.join(promptsFolderPath, toolInstructionsName)
|
||||
discordLogPath = os.path.join(os.path.dirname(__file__), "discordMessages.json")
|
||||
discordLogLimit = 500
|
||||
|
||||
schemaTemplateData = {
|
||||
"category": "general",
|
||||
"name": "welcome",
|
||||
"description": "Explain what this prompt should accomplish for the ADHD assistant.",
|
||||
"variables": ["user", "user_firstname", "context"],
|
||||
"template": "Hey {user_firstname}! Let's work through this together. You mentioned: {context}",
|
||||
}
|
||||
|
||||
defaultPromptRecords = [
|
||||
{
|
||||
"category": "general",
|
||||
"name": "welcome",
|
||||
"description": "First interaction focused on ADHD-friendly support.",
|
||||
"variables": ["user", "user_firstname", "context"],
|
||||
"template": "Hey {user_firstname}! I'm your ADHD-focused executive function assistant. You mentioned: {context}. Tell me where you feel stuck—reminding yourself, planning something, or getting started—and I'll help you pick a light next action. If you ever want me to save a plan or schedule a reminder, just say so and I'll include the right JSON payload. When you explicitly say to take or log a note (including inside the context), close with one ```json block containing {\"action\": \"take_note\", \"note\": \"<note text>\"}.",
|
||||
},
|
||||
{
|
||||
"category": "general",
|
||||
"name": "fallback",
|
||||
"description": "Backup voice when a prompt is missing.",
|
||||
"variables": ["user", "context"],
|
||||
"template": "Still working on that, {user}. Let's keep momentum by focusing on the next doable step from this context: {context}",
|
||||
},
|
||||
{
|
||||
"category": "planning",
|
||||
"name": "breakdown",
|
||||
"description": "Helps the user break a task into ADHD-friendly chunks and optionally store it.",
|
||||
"variables": ["user", "user_firstname", "context"],
|
||||
"template": "You are an executive function coach for {user_firstname}. Use the context to:\\n1. Reflect empathy in one short sentence.\\n2. Identify the desired outcome.\\n3. Break the work into 2-5 tiny, observable steps with relaxing estimates (\"~5 min\", \"1 song\" etc.).\\n4. Offer a prompt that nudges initiation (\"Want me to save this plan or set a reminder?\").\\n\\nIf the user clearly wants to save the plan, append a single ```json block with:\\n{\\n \"action\": \"store_task\",\\n \"task\": {\\n \"title\": \"short label\",\\n \"steps\": [\\n {\"order\": 1, \"description\": \"step detail\", \"duration\": \"~5 min\"}\\n ],\\n \"next_step\": \"first step text\",\\n \"context\": \"{context}\",\\n \"status\": \"not_started\"\\n }\\n}\\nOnly include the JSON when explicitly requested or confirmed; otherwise stay conversational.",
|
||||
},
|
||||
{
|
||||
"category": "reminders",
|
||||
"name": "schedule",
|
||||
"description": "Collaboratively schedules reminders for the user.",
|
||||
"variables": ["user", "user_firstname", "context"],
|
||||
"template": "You help {user_firstname} set ADHD-friendly reminders. Confirm the task, timing, and delivery preference. Summarize the reminder in natural language and invite any tweaks.\\n\\nWhen the user gives enough detail or explicitly says to schedule it, append one ```json block with:\\n{\\n \"action\": \"schedule_reminder\",\\n \"reminder\": {\\n \"title\": \"short label\",\\n \"details\": \"context summary\",\\n \"trigger\": {\\n \"type\": \"datetime | relative | habit\",\\n \"value\": \"ISO timestamp or human-friendly string\"\\n },\\n \"follow_up\": \"check-in question\",\\n \"metadata\": {\\n \"user\": \"{user}\",\\n \"source\": \"prompt\"\\n }\\n }\\n}\\nSkip the JSON when the reminder details are incomplete—keep the conversation going instead.",
|
||||
},
|
||||
]
|
||||
|
||||
defaultToolInstructions = """Tooling and JSON actions\n\n1. Only emit JSON when the user confirms they want an action performed.\n2. Wrap every payload in a single fenced ```json block.\n3. Supported payloads today: take_note, store_task, schedule_reminder.\n4. Keep conversational text before or after the block short and clear.\n\nWhen logging a note, output exactly:\n```json\n{\n \"action\": \"take_note\",\n \"note\": \"<verbatim note text>\"\n}\n```\nSwap in the user's wording (including emojis or punctuation) for the placeholder.\n"""
|
||||
|
||||
|
||||
def ensurePromptAssets():
|
||||
if not os.path.isdir(promptsFolderPath):
|
||||
os.makedirs(promptsFolderPath, exist_ok=True)
|
||||
schemaPath = os.path.join(promptsFolderPath, schemaTemplateName)
|
||||
if not os.path.exists(schemaPath):
|
||||
with open(schemaPath, "w", encoding="utf-8") as schemaFile:
|
||||
json.dump(schemaTemplateData, schemaFile, indent=2)
|
||||
defaultPromptsPath = os.path.join(promptsFolderPath, defaultPromptsName)
|
||||
if not os.path.exists(defaultPromptsPath):
|
||||
with open(defaultPromptsPath, "w", encoding="utf-8") as defaultFile:
|
||||
json.dump(defaultPromptRecords, defaultFile, indent=2)
|
||||
ensureToolInstructions()
|
||||
|
||||
|
||||
def ensureToolInstructions():
|
||||
if os.path.exists(toolInstructionsPath):
|
||||
return
|
||||
with open(toolInstructionsPath, "w", encoding="utf-8") as handle:
|
||||
handle.write(defaultToolInstructions)
|
||||
|
||||
|
||||
def ensureDiscordLog():
|
||||
if not os.path.exists(discordLogPath):
|
||||
with open(discordLogPath, "w", encoding="utf-8") as logFile:
|
||||
json.dump([], logFile)
|
||||
|
||||
|
||||
def readDiscordLog():
|
||||
if not os.path.exists(discordLogPath):
|
||||
return []
|
||||
try:
|
||||
with open(discordLogPath, "r", encoding="utf-8") as logFile:
|
||||
records = json.load(logFile)
|
||||
except (json.JSONDecodeError, OSError):
|
||||
return []
|
||||
if not isinstance(records, list):
|
||||
return []
|
||||
return records
|
||||
|
||||
|
||||
def writeDiscordLog(records):
|
||||
trimmed = records[-discordLogLimit:]
|
||||
with open(discordLogPath, "w", encoding="utf-8") as logFile:
|
||||
json.dump(trimmed, logFile, indent=2)
|
||||
|
||||
|
||||
def readToolInstructions():
|
||||
if not os.path.exists(toolInstructionsPath):
|
||||
ensureToolInstructions()
|
||||
try:
|
||||
with open(toolInstructionsPath, "r", encoding="utf-8") as handle:
|
||||
return handle.read().strip()
|
||||
except OSError:
|
||||
return ""
|
||||
|
||||
|
||||
ensurePromptAssets()
|
||||
ensureDiscordLog()
|
||||
Reference in New Issue
Block a user