Merge pull request #310 from oraios/feature/system_prompt_on_cli/cc_serena

Add print-system-prompt command - PR by CC with Serena
This commit is contained in:
Michael Panchenko authored and GitHub committed 2025-07-16 16:42:57 +02:00
commit cf866bb168
4 files changed
+43 -5

No files matched your search

+6 -2
View File
@@ -354,8 +354,12 @@ For example, when using `uvx`, you would run
claude mcp add serena -- uvx --from git+https://github.com/oraios/serena serena-mcp-server --context ide-assistant --project $(pwd)
```
ℹ️ Once in Claude Code, run `/mcp__serena__initial_instructions` to load instructions for using Serena's tools. Run this command
whenever you start a new conversation and after any compacting operation to ensure Claude remains properly configured to use Serena's tools.
ℹ️ Serena comes with an instruction text, and Claude needs to read it to properly use Serena's tools.
Once in Claude Code, you can ask to "read Serena's initial instructions" or run `/mcp__serena__initial_instructions` to load the instruction text.
Do this whenever you start a new conversation and after any compacting operation to ensure Claude remains properly configured to use Serena's tools.
ℹ️ **NEW**: an alternative to the above is adding the instructions as part of the system prompt, then you will not need to run the command above or to remember re-running it after compacting.
This can be achieved through starting claude code with `claude --append-system-prompt $(uvx --from git+https://github.com/oraios/serena print-system-prompt)`. Note that this is **experimental**, Claude may not understand the instructions correctly in this way, and we haven't thoroughly tested the resulting behavior. Please report any issues you encounter.
### Claude Desktop
+1
View File
@@ -39,6 +39,7 @@ dependencies = [
[project.scripts]
serena-mcp-server = "serena.mcp:start_mcp_server"
index-project = "serena.agent:index_project"
print-system-prompt = "serena.agent:print_system_prompt"
[project.license]
text = "MIT"
+33
View File
@@ -124,6 +124,39 @@ def index_project(project: str, log_level: str = "INFO") -> None:
print(f"Symbols saved to {ls.cache_path}")
@click.command()
@click.argument("project", type=click.Path(exists=True), required=False, default=os.getcwd())
@click.option("--log-level", type=click.Choice(["DEBUG", "INFO", "WARNING", "ERROR", "CRITICAL"]), default="WARNING")
@click.option(
"--only-instructions",
is_flag=True,
help="If set, only print the initial instructions prompt (without prefix or postfix). The prefix and postfix are small additions that are used to"
"make the initial instructions more digestible for an LLM in the context of a system prompt, as opposed to their normal usage within a conversation.",
)
def print_system_prompt(project: str, log_level: str = "WARNING", only_instructions: bool = False) -> None:
"""
Print the system prompt (initial instructions with a potential pre/post-fix) for a project.
"""
prefix_to_instructions_prompt = (
"You will receive access to Serena's symbolic tools. Below are instructions for using them, take them into account."
)
postfix_to_instructions_prompt = "You begin the conversation by acknowledging that you understood the above instructions on the symbolic tools and are ready to receive a task. You will not need to call the tool on getting initial instructions."
from serena.tools.workflow_tools import InitialInstructionsTool
log_level_int = logging.getLevelNamesMapping()[log_level.upper()]
logging.configure(level=log_level_int)
agent = SerenaAgent(project=os.path.abspath(project), serena_config=SerenaConfig(web_dashboard=False, log_level=log_level_int))
initial_instructions_tool = agent.get_tool(InitialInstructionsTool)
initial_instructions = initial_instructions_tool.apply()
if only_instructions:
print(initial_instructions)
else:
system_prompt = f"{prefix_to_instructions_prompt}\n{initial_instructions}\n{postfix_to_instructions_prompt}"
print(system_prompt)
class SerenaAgent:
def __init__(
self,
+3 -3
View File
@@ -132,8 +132,8 @@ class InitialInstructionsTool(Tool, ToolMarkerDoesNotRequireActiveProject):
def apply(self) -> str:
"""
Get the initial instructions for the current coding project.
You should always call this tool before starting to work (including using any other tool) on any programming task!
The only exception is when a user asks you to activate a project, in which case you should call the `activate_project` first
instead and then call this tool.
If you haven't received instructions on how to use Serena's tools in the system prompt,
you should always call this tool before starting to work (including using any other tool) on any programming task,
the only exception being when you are asked to call `activate_project`, which you should then call before.
"""
return self.agent.create_system_prompt()