Co-authored-by: Jason Woltje <jason@diversecanvas.com> Co-committed-by: Jason Woltje <jason@diversecanvas.com>
146 lines
5.1 KiB
TypeScript
146 lines
5.1 KiB
TypeScript
import type { CommunicationStyle, SoulConfig, UserConfig, ToolsConfig, GitProvider } from '../types.js';
|
|
import { DEFAULTS } from '../constants.js';
|
|
import type { TemplateVars } from './engine.js';
|
|
|
|
/**
|
|
* Build behavioral principles text based on communication style.
|
|
* Replicates mosaic-init lines 177-204 exactly.
|
|
*/
|
|
function buildBehavioralPrinciples(
|
|
style: CommunicationStyle,
|
|
accessibility?: string,
|
|
): string {
|
|
let principles: string;
|
|
|
|
switch (style) {
|
|
case 'direct':
|
|
principles = `1. Clarity over performance theater.
|
|
2. Practical execution over abstract planning.
|
|
3. Truthfulness over confidence: state uncertainty explicitly.
|
|
4. Visible state over hidden assumptions.
|
|
5. Accessibility-aware — see \`~/.config/mosaic/USER.md\` for user-specific accommodations.`;
|
|
break;
|
|
case 'friendly':
|
|
principles = `1. Be helpful and approachable while staying efficient.
|
|
2. Provide context and explain reasoning when helpful.
|
|
3. Truthfulness over confidence: state uncertainty explicitly.
|
|
4. Visible state over hidden assumptions.
|
|
5. Accessibility-aware — see \`~/.config/mosaic/USER.md\` for user-specific accommodations.`;
|
|
break;
|
|
case 'formal':
|
|
principles = `1. Maintain professional, structured communication.
|
|
2. Provide thorough analysis with explicit tradeoffs.
|
|
3. Truthfulness over confidence: state uncertainty explicitly.
|
|
4. Document decisions and rationale clearly.
|
|
5. Accessibility-aware — see \`~/.config/mosaic/USER.md\` for user-specific accommodations.`;
|
|
break;
|
|
}
|
|
|
|
if (accessibility && accessibility !== 'none' && accessibility.length > 0) {
|
|
principles += `\n6. ${accessibility}.`;
|
|
}
|
|
|
|
return principles;
|
|
}
|
|
|
|
/**
|
|
* Build communication style text based on style choice.
|
|
* Replicates mosaic-init lines 208-227 exactly.
|
|
*/
|
|
function buildCommunicationStyleText(style: CommunicationStyle): string {
|
|
switch (style) {
|
|
case 'direct':
|
|
return `- Be direct, concise, and concrete.
|
|
- Avoid fluff, hype, and anthropomorphic roleplay.
|
|
- Do not simulate certainty when facts are missing.
|
|
- Prefer actionable next steps and explicit tradeoffs.`;
|
|
case 'friendly':
|
|
return `- Be warm and conversational while staying focused.
|
|
- Explain your reasoning when it helps the user.
|
|
- Do not simulate certainty when facts are missing.
|
|
- Prefer actionable next steps with clear context.`;
|
|
case 'formal':
|
|
return `- Use professional, structured language.
|
|
- Provide thorough explanations with supporting detail.
|
|
- Do not simulate certainty when facts are missing.
|
|
- Present options with explicit tradeoffs and recommendations.`;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Build communication preferences for USER.md based on style.
|
|
* Replicates mosaic-init lines 299-316 exactly.
|
|
*/
|
|
function buildCommunicationPrefs(style: CommunicationStyle): string {
|
|
switch (style) {
|
|
case 'direct':
|
|
return `- Direct and concise
|
|
- No sycophancy
|
|
- Executive summaries and tables for overview`;
|
|
case 'friendly':
|
|
return `- Warm and conversational
|
|
- Explain reasoning when helpful
|
|
- Balance thoroughness with brevity`;
|
|
case 'formal':
|
|
return `- Professional and structured
|
|
- Thorough explanations with supporting detail
|
|
- Formal tone with explicit recommendations`;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Build git providers markdown table from provider list.
|
|
* Replicates mosaic-init lines 362-384.
|
|
*/
|
|
function buildGitProvidersTable(providers?: GitProvider[]): string {
|
|
if (!providers || providers.length === 0) {
|
|
return DEFAULTS.gitProvidersTable;
|
|
}
|
|
|
|
const rows = providers
|
|
.map((p) => `| ${p.name} | ${p.url} | \`${p.cli}\` | ${p.purpose} |`)
|
|
.join('\n');
|
|
|
|
return `| Instance | URL | CLI | Purpose |
|
|
|----------|-----|-----|---------|
|
|
${rows}`;
|
|
}
|
|
|
|
export function buildSoulTemplateVars(config: SoulConfig): TemplateVars {
|
|
const style = config.communicationStyle ?? 'direct';
|
|
const guardrails = config.customGuardrails
|
|
? `- ${config.customGuardrails}`
|
|
: '';
|
|
|
|
return {
|
|
AGENT_NAME: config.agentName ?? DEFAULTS.agentName,
|
|
ROLE_DESCRIPTION: config.roleDescription ?? DEFAULTS.roleDescription,
|
|
BEHAVIORAL_PRINCIPLES: buildBehavioralPrinciples(style, config.accessibility),
|
|
COMMUNICATION_STYLE: buildCommunicationStyleText(style),
|
|
CUSTOM_GUARDRAILS: guardrails,
|
|
};
|
|
}
|
|
|
|
export function buildUserTemplateVars(config: UserConfig): TemplateVars {
|
|
return {
|
|
USER_NAME: config.userName ?? '',
|
|
PRONOUNS: config.pronouns ?? DEFAULTS.pronouns,
|
|
TIMEZONE: config.timezone ?? DEFAULTS.timezone,
|
|
BACKGROUND: config.background ?? DEFAULTS.background,
|
|
ACCESSIBILITY_SECTION: config.accessibilitySection ?? DEFAULTS.accessibilitySection,
|
|
COMMUNICATION_PREFS: config.communicationPrefs ?? buildCommunicationPrefs('direct'),
|
|
PERSONAL_BOUNDARIES: config.personalBoundaries ?? DEFAULTS.personalBoundaries,
|
|
PROJECTS_TABLE: config.projectsTable ?? DEFAULTS.projectsTable,
|
|
};
|
|
}
|
|
|
|
export function buildToolsTemplateVars(config: ToolsConfig): TemplateVars {
|
|
return {
|
|
GIT_PROVIDERS_TABLE: buildGitProvidersTable(config.gitProviders),
|
|
CREDENTIALS_LOCATION: config.credentialsLocation ?? DEFAULTS.credentialsLocation,
|
|
CUSTOM_TOOLS_SECTION: config.customToolsSection ?? DEFAULTS.customToolsSection,
|
|
};
|
|
}
|
|
|
|
export { buildCommunicationPrefs };
|