Add AI persona profiles for prompt injection

Profiles allow users to inject system instructions into prompts,
customizing the AI's behavior and persona for tool execution.

Features:
- Profile dataclass with name, description, system_prompt
- 8 built-in profiles: None, Comedian, Technical Writer, Teacher,
  Concise, Creative, Code Reviewer, Analyst
- Custom profile creation and storage in ~/.cmdforge/profiles/
- Profile selector in Prompt Step dialog
- Profile injection during tool execution
- Profiles page in GUI (Ctrl+4) for viewing and managing profiles

Co-Authored-By: Claude Opus 4.5 <[email protected]>
This commit is contained in:
rob
2026-01-14 05:22:31 -04:00
co-authored by Claude Opus 4.5
parent 9d56f703cd
commit 9588c3f8b0
6 changed files with 473 additions and 3 deletions
+24 -1
View File
@@ -5,9 +5,11 @@ from PySide6.QtWidgets import (
QComboBox, QPushButton, QHBoxLayout, QLabel,
QPlainTextEdit
)
from PySide6.QtCore import Qt
from ...tool import PromptStep, CodeStep
from ...providers import load_providers
from ...profiles import list_profiles
class PromptStepDialog(QDialog):
@@ -43,6 +45,16 @@ class PromptStepDialog(QDialog):
self.provider_combo.addItem(default)
form.addRow("Provider:", self.provider_combo)
# Profile selection
self.profile_combo = QComboBox()
profiles = list_profiles()
for profile in profiles:
self.profile_combo.addItem(profile.name)
# Set tooltip with description
idx = self.profile_combo.count() - 1
self.profile_combo.setItemData(idx, profile.description, Qt.ToolTipRole)
form.addRow("Profile:", self.profile_combo)
# Output variable
self.output_input = QLineEdit()
self.output_input.setPlaceholderText("response")
@@ -87,6 +99,12 @@ class PromptStepDialog(QDialog):
else:
self.provider_combo.setCurrentText(step.provider)
# Load profile
if step.profile:
idx = self.profile_combo.findText(step.profile)
if idx >= 0:
self.profile_combo.setCurrentIndex(idx)
self.output_input.setText(step.output_var)
self.prompt_input.setPlainText(step.prompt)
@@ -106,10 +124,15 @@ class PromptStepDialog(QDialog):
def get_step(self) -> PromptStep:
"""Get the step from form data."""
profile = self.profile_combo.currentText()
# Don't store "None" profile
if profile == "None":
profile = None
return PromptStep(
prompt=self.prompt_input.toPlainText(),
provider=self.provider_combo.currentText(),
output_var=self.output_input.text().strip()
output_var=self.output_input.text().strip(),
profile=profile
)