158 lines
7.8 KiB
C#
158 lines
7.8 KiB
C#
// File: SclPromptBuilder.cs
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using System.Text;
|
|
|
|
namespace AI.Client.SCL
|
|
{
|
|
/// <summary>
|
|
/// Represents a definition of an SCL command to be taught to the AI.
|
|
/// </summary>
|
|
public class SclCommandDefinition
|
|
{
|
|
/// <summary>
|
|
/// The alphanumeric identifier for the command (e.g., "ls", "wr").
|
|
/// </summary>
|
|
public string CommandId { get; set; }
|
|
|
|
/// <summary>
|
|
/// A brief description of what the command does.
|
|
/// </summary>
|
|
public string Description { get; set; }
|
|
|
|
/// <summary>
|
|
/// A list of parameter names expected by the command.
|
|
/// </summary>
|
|
public List<string> Parameters { get; set; }
|
|
|
|
public SclCommandDefinition(string commandId, string description, params string[] parameters)
|
|
{
|
|
CommandId = commandId;
|
|
Description = description;
|
|
Parameters = new List<string>();
|
|
|
|
if (parameters != null)
|
|
{
|
|
Parameters.AddRange(parameters);
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// A utility class to programmatically generate the System Instructions prompt for the AI,
|
|
/// injecting custom SCL commands dynamically.
|
|
/// </summary>
|
|
public class SclPromptBuilder
|
|
{
|
|
private readonly List<SclCommandDefinition> _commands;
|
|
private string _agentRole;
|
|
|
|
public SclPromptBuilder()
|
|
{
|
|
_commands = new List<SclCommandDefinition>();
|
|
_agentRole = "You are a strict, machine-to-machine execution engine equipped with the Synapse Command Language (SCL). SCL allows you to interact directly with the user's local system via a client program that parses your output.";
|
|
}
|
|
|
|
/// <summary>
|
|
/// Overrides the default agent persona/role at the very beginning of the prompt.
|
|
/// </summary>
|
|
/// <param name="roleDescription">The custom role description.</param>
|
|
public void SetAgentRole(string roleDescription)
|
|
{
|
|
if (!string.IsNullOrWhiteSpace(roleDescription))
|
|
{
|
|
_agentRole = roleDescription;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Registers a command definition to be included in the generated prompt.
|
|
/// </summary>
|
|
/// <param name="commandId">The command identifier (e.g., "ls").</param>
|
|
/// <param name="description">What the command does.</param>
|
|
/// <param name="parameters">The names of the parameters (e.g., "file_path", "content").</param>
|
|
public void AddCommand(string commandId, string description, params string[] parameters)
|
|
{
|
|
_commands.Add(new SclCommandDefinition(commandId, description, parameters));
|
|
}
|
|
|
|
/// <summary>
|
|
/// Generates the complete System Instructions prompt text.
|
|
/// </summary>
|
|
/// <returns>A formatted string ready to be sent to the AI as System Instructions.</returns>
|
|
public string GeneratePrompt()
|
|
{
|
|
StringBuilder sb = new StringBuilder();
|
|
|
|
// 1. Agent Role
|
|
sb.AppendLine(_agentRole);
|
|
sb.AppendLine();
|
|
|
|
// 2. Core SCL Protocol Rules
|
|
sb.AppendLine("### SCL Protocol Rules (CRITICAL)");
|
|
sb.AppendLine("You MUST use SCL to perform actions. SCL is designed to be extremely token-efficient.");
|
|
sb.AppendLine("ABSOLUTELY NO JSON, XML, MARKDOWN, OR RAW SHELL COMMANDS ARE ALLOWED. You must use the exact syntax below.");
|
|
sb.AppendLine();
|
|
sb.AppendLine("1. ISSUING COMMANDS (Action Trigger: ~)");
|
|
sb.AppendLine("Syntax: ~command_name[parameter1|parameter2]");
|
|
sb.AppendLine("* Commands start with a tilde (~).");
|
|
sb.AppendLine("* Parameters are enclosed in square brackets [ ].");
|
|
sb.AppendLine("* Multiple parameters are separated by a pipe (|).");
|
|
sb.AppendLine("* If a parameter contains a literal ], |, or \\, you must escape it with a backslash (e.g., \\], \\|, \\\\).");
|
|
sb.AppendLine();
|
|
sb.AppendLine("2. RECEIVING RESULTS (Result Trigger: ^)");
|
|
sb.AppendLine("The client program will reply to your commands in the next prompt using this syntax:");
|
|
sb.AppendLine("Syntax: ^command_name[status_code|output_data]");
|
|
sb.AppendLine("* Status 0 means success. Status 1 means error.");
|
|
sb.AppendLine("* You must wait for the ^ result before assuming a command succeeded, UNLESS the command launches a background/GUI application, in which case the client may omit the response to save tokens and end the interaction.");
|
|
sb.AppendLine();
|
|
|
|
// 3. Dynamic Available Commands
|
|
sb.AppendLine("### Available Client Commands");
|
|
sb.AppendLine("(Note: The client program currently supports the following commands. You may use them at any time to fulfill the user's requests.)");
|
|
sb.AppendLine();
|
|
|
|
if (_commands.Count == 0)
|
|
{
|
|
sb.AppendLine("* (No commands are currently registered by the client program.)");
|
|
}
|
|
else
|
|
{
|
|
foreach (var cmd in _commands)
|
|
{
|
|
string paramString = string.Join("|", cmd.Parameters);
|
|
sb.AppendLine($"* ~{cmd.CommandId}[{paramString}] : {cmd.Description}");
|
|
}
|
|
}
|
|
sb.AppendLine();
|
|
|
|
// 4. Execution Guidelines & Strict Constraints
|
|
sb.AppendLine("### Execution Guidelines & CRITICAL CONSTRAINTS");
|
|
sb.AppendLine("* ALL INPUT PROMPT WILL BE ENCODED AS BASE64 STRINGS: Any input prompt you receive will be encoded as a base64 string. Make sure you decode the base64 string before processing it.");
|
|
sb.AppendLine("* STOP AFTER ISSUING A COMMAND: If you issue a command that expects an output result, you MUST STOP generating text and wait for the program to reply with the `^` result.");
|
|
sb.AppendLine("* NO RAW COMMANDS: NEVER output raw shell commands like `start notepad.exe` or `EXECUTE(notepad)`. You MUST wrap them in the appropriate SCL command, e.g., `~cmd[start notepad.exe]`.");
|
|
sb.AppendLine("* NO MARKDOWN: NEVER wrap your SCL commands in backticks (`) or markdown code blocks (```).");
|
|
sb.AppendLine("* NO CONVERSATION: You may NOT output conversational text alongside an SCL command to explain your thought process to the user. ONLY output the SCL command by itself and nothing else.");
|
|
sb.AppendLine("* Do NOT chain multiple commands together (e.g., do not issue an `ls` and an `rd` in the same response). Issue the first command, wait for the result, and then issue the next.");
|
|
sb.AppendLine("* If a command fails (returns status 1), analyze the error data provided in the result and attempt to fix the issue or notify the user.");
|
|
sb.AppendLine();
|
|
|
|
// 5. Example Scenario
|
|
sb.AppendLine("### Example Scenario");
|
|
sb.AppendLine("User: \"Open notepad\"");
|
|
sb.AppendLine("WRONG: start notepad.exe");
|
|
sb.AppendLine("WRONG: ```~cmd[start notepad.exe]```");
|
|
sb.AppendLine("WRONG: EXECUTE(notepad.exe)");
|
|
sb.AppendLine("CORRECT: ~cmd[start notepad.exe]");
|
|
sb.AppendLine();
|
|
sb.AppendLine("User: \"Check what is in C:\\Temp and delete old.txt\"");
|
|
sb.AppendLine("You: ~cmd[dir C:\\Temp]");
|
|
sb.AppendLine("Program: ^cmd[0|old.txt\\nnew.txt\\nconfig.ini]");
|
|
sb.AppendLine("You: ~cmd[del C:\\Temp\\old.txt]");
|
|
sb.AppendLine("Program: ^cmd[0|Success]");
|
|
sb.AppendLine("You: The file old.txt has been successfully deleted.");
|
|
|
|
return sb.ToString();
|
|
}
|
|
}
|
|
} |