From bcca2127eb7f8f75ac53dcb8b3f67f27fe2cb7c9 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Sun, 8 Feb 2026 19:12:46 +0100 Subject: [PATCH 01/17] wip: broken --- AGENTS.md | 6 ---- changes/unreleased.md | 5 +++ donna/cli/commands/workspaces.py | 29 ++++++++++++---- donna/cli/types.py | 8 +++++ donna/fixtures/skills/donna-do/SKILL.md | 12 +++++++ donna/fixtures/skills/donna-start/SKILL.md | 13 +++++++ donna/fixtures/skills/donna-stop/SKILL.md | 6 ++++ donna/fixtures/skills/donna/SKILL.md | 12 +++++++ donna/workspaces/initialization.py | 40 +++++++++++++++++++++- 9 files changed, 117 insertions(+), 14 deletions(-) create mode 100644 donna/fixtures/skills/donna-do/SKILL.md create mode 100644 donna/fixtures/skills/donna-start/SKILL.md create mode 100644 donna/fixtures/skills/donna-stop/SKILL.md create mode 100644 donna/fixtures/skills/donna/SKILL.md diff --git a/AGENTS.md b/AGENTS.md index e2f202f..ca72014 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -9,9 +9,3 @@ Every agent MUST follow the rules and guidelines outlined in this document when **You MUST use `donna` tool to work on this project.** Since this is the repository that contains the Donna project itself, you have direct access to the Donna CLI tool via `./bin/donna.sh` script. I.e. you develop Donna using Donna. - -**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. - -1. You **MUST** run `./bin/donna.sh -p llm -r artifacts view '*:intro'` when you start working. -2. You **MUST** strictly follow the instructions provided by Donna. -3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. diff --git a/changes/unreleased.md b/changes/unreleased.md index ef13857..8ed3361 100644 --- a/changes/unreleased.md +++ b/changes/unreleased.md @@ -1,2 +1,7 @@ +### Changes - Improved template for RFC draft artifact — added the `kind` config to the header section. +- Added workspace skill synchronization for `donna workspaces init` and `donna workspaces update`. + - Added `donna workspaces update` command. + - Added `--no-skills` and `--no-skils` options for `init` and `update` to skip skill updates. + - Added Donna skill fixture copy from `donna/fixtures/skills/donna` to `/.agents/skills/donna`. diff --git a/donna/cli/commands/workspaces.py b/donna/cli/commands/workspaces.py index d513a16..53367e8 100644 --- a/donna/cli/commands/workspaces.py +++ b/donna/cli/commands/workspaces.py @@ -4,28 +4,43 @@ import typer from donna.cli.application import app +from donna.cli.types import SkillsOption from donna.cli.utils import cells_cli from donna.protocol.cell_shortcuts import operation_succeeded from donna.protocol.cells import Cell from donna.workspaces import config as workspace_config -from donna.workspaces.initialization import initialize_workspace +from donna.workspaces.initialization import initialize_workspace, update_workspace workspaces_cli = typer.Typer() +def _resolve_target_dir() -> pathlib.Path: + if workspace_config.project_dir.is_set(): + return workspace_config.project_dir() + + return pathlib.Path.cwd() + + @workspaces_cli.command(help="Initialize Donna workspace.") @cells_cli -def init() -> Iterable[Cell]: - if workspace_config.project_dir.is_set(): - target_dir = workspace_config.project_dir() - else: - target_dir = pathlib.Path.cwd() +def init(skills: SkillsOption = True) -> Iterable[Cell]: + target_dir = _resolve_target_dir() - initialize_workspace(target_dir).unwrap() + initialize_workspace(target_dir, install_skills=skills).unwrap() return [operation_succeeded("Workspace initialized successfully")] +@workspaces_cli.command(help="Update Donna workspace files.") +@cells_cli +def update(skills: SkillsOption = True) -> Iterable[Cell]: + target_dir = _resolve_target_dir() + + update_workspace(target_dir, install_skills=skills).unwrap() + + return [operation_succeeded("Workspace updated successfully")] + + app.add_typer( workspaces_cli, name="workspaces", diff --git a/donna/cli/types.py b/donna/cli/types.py index e8fb766..c1df81b 100644 --- a/donna/cli/types.py +++ b/donna/cli/types.py @@ -126,6 +126,14 @@ def _parse_protocol_mode(value: str) -> Mode: ), ] +SkillsOption = Annotated[ + bool, + typer.Option( + "--skills/--no-skills", + help="Enable or disable skills updates in `.agents/skills`.", + ), +] + InputPathArgument = Annotated[ pathlib.Path, diff --git a/donna/fixtures/skills/donna-do/SKILL.md b/donna/fixtures/skills/donna-do/SKILL.md new file mode 100644 index 0000000..e0419eb --- /dev/null +++ b/donna/fixtures/skills/donna-do/SKILL.md @@ -0,0 +1,12 @@ +--- +name: donna-do +description: Use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +--- + +**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. + +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +2. You **MUST** strictly follow all instructions provided by Donna. +3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. +4. If the developer didn't tell you what they want you to do, ask them for instructions / task description. +5. Select most suitable Donna workflow to perform the requested work and run it. diff --git a/donna/fixtures/skills/donna-start/SKILL.md b/donna/fixtures/skills/donna-start/SKILL.md new file mode 100644 index 0000000..35b23a5 --- /dev/null +++ b/donna/fixtures/skills/donna-start/SKILL.md @@ -0,0 +1,13 @@ +--- +name: donna-start +description: Start new Donna session and use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +--- + +**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. + +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +2. You **MUST** strictly follow all instructions provided by Donna. +3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. +4. Run `donna -p llm -r sessions start` to start a new Donna session. +5. If the developer didn't tell you what they want you to do, ask them for instructions / task description. +6. Use Donna to perform the requested work: select most suitable Donna workflow to perform the requested work and run it. diff --git a/donna/fixtures/skills/donna-stop/SKILL.md b/donna/fixtures/skills/donna-stop/SKILL.md new file mode 100644 index 0000000..5aeb33f --- /dev/null +++ b/donna/fixtures/skills/donna-stop/SKILL.md @@ -0,0 +1,6 @@ +--- +name: donna-stop +description: Stop using Donna to perform work. +--- + +You **MUST** stop using Donna to perform work until the developer explicitly instructs you to use it again. diff --git a/donna/fixtures/skills/donna/SKILL.md b/donna/fixtures/skills/donna/SKILL.md new file mode 100644 index 0000000..dffed74 --- /dev/null +++ b/donna/fixtures/skills/donna/SKILL.md @@ -0,0 +1,12 @@ +--- +name: donna +description: Use Donna as a work orchestration tool. Follow Donna's instructions, run Donna's workflows and access Donna's artifacts to perform your work. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +--- + +**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. + +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +2. You **MUST** strictly follow all instructions provided by Donna. +3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. +4. If the developer told you what they want you to do, do it using Donna. +5. If you have no instructions from the developer, ask them for instructions / task description and then do it using Donna. diff --git a/donna/workspaces/initialization.py b/donna/workspaces/initialization.py index d04952f..39d6b88 100644 --- a/donna/workspaces/initialization.py +++ b/donna/workspaces/initialization.py @@ -1,4 +1,6 @@ +import importlib.resources import pathlib +import shutil import tomllib import tomli_w @@ -11,6 +13,23 @@ from donna.workspaces import config from donna.workspaces import errors as world_errors +SKILLS_ROOT_DIR = pathlib.Path(".agents") / "skills" +DONNA_SKILL_ID = "donna" +DONNA_SKILL_FIXTURE_DIR = pathlib.Path("fixtures") / "skills" / DONNA_SKILL_ID + + +def _sync_donna_skill(project_dir: pathlib.Path) -> None: + source = importlib.resources.files("donna").joinpath(*DONNA_SKILL_FIXTURE_DIR.parts) + + with importlib.resources.as_file(source) as source_dir: + target_dir = project_dir / SKILLS_ROOT_DIR / DONNA_SKILL_ID + target_dir.parent.mkdir(parents=True, exist_ok=True) + + if target_dir.exists(): + shutil.rmtree(target_dir) + + shutil.copytree(source_dir, target_dir, dirs_exist_ok=True) + @unwrap_to_error def initialize_runtime( # noqa: CCR001 @@ -59,7 +78,9 @@ def initialize_runtime( # noqa: CCR001 @unwrap_to_error -def initialize_workspace(project_dir: pathlib.Path) -> Result[None, core_errors.ErrorsList]: +def initialize_workspace( + project_dir: pathlib.Path, install_skills: bool = True +) -> Result[None, core_errors.ErrorsList]: """Initialize the physical workspace for the project (`.donna` directory).""" project_dir = project_dir.resolve() workspace_dir = project_dir / config.DONNA_DIR_NAME @@ -89,4 +110,21 @@ def initialize_workspace(project_dir: pathlib.Path) -> Result[None, core_errors. session_world = default_config.get_world(WorldId(config.DONNA_WORLD_SESSION_DIR_NAME)).unwrap() session_world.initialize() + if install_skills: + _sync_donna_skill(project_dir) + + return Ok(None) + + +@unwrap_to_error +def update_workspace(project_dir: pathlib.Path, install_skills: bool = True) -> Result[None, core_errors.ErrorsList]: + project_dir = project_dir.resolve() + workspace_dir = project_dir / config.DONNA_DIR_NAME + + if not workspace_dir.exists(): + return Err([core_errors.ProjectDirNotFound(donna_dir_name=config.DONNA_DIR_NAME)]) + + if install_skills: + _sync_donna_skill(project_dir) + return Ok(None) From 79c7f80f74bf36718ad5fa537fcba19c6c5569cf Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Sun, 8 Feb 2026 19:50:04 +0100 Subject: [PATCH 02/17] wip --- .agents/skills/donna-do/SKILL.md | 12 ++++++++++++ .agents/skills/donna-start/SKILL.md | 13 +++++++++++++ .agents/skills/donna-stop/SKILL.md | 6 ++++++ .agents/skills/donna/SKILL.md | 12 ++++++++++++ donna/workspaces/initialization.py | 19 ++++++++++++------- 5 files changed, 55 insertions(+), 7 deletions(-) create mode 100644 .agents/skills/donna-do/SKILL.md create mode 100644 .agents/skills/donna-start/SKILL.md create mode 100644 .agents/skills/donna-stop/SKILL.md create mode 100644 .agents/skills/donna/SKILL.md diff --git a/.agents/skills/donna-do/SKILL.md b/.agents/skills/donna-do/SKILL.md new file mode 100644 index 0000000..e0419eb --- /dev/null +++ b/.agents/skills/donna-do/SKILL.md @@ -0,0 +1,12 @@ +--- +name: donna-do +description: Use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +--- + +**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. + +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +2. You **MUST** strictly follow all instructions provided by Donna. +3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. +4. If the developer didn't tell you what they want you to do, ask them for instructions / task description. +5. Select most suitable Donna workflow to perform the requested work and run it. diff --git a/.agents/skills/donna-start/SKILL.md b/.agents/skills/donna-start/SKILL.md new file mode 100644 index 0000000..35b23a5 --- /dev/null +++ b/.agents/skills/donna-start/SKILL.md @@ -0,0 +1,13 @@ +--- +name: donna-start +description: Start new Donna session and use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +--- + +**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. + +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +2. You **MUST** strictly follow all instructions provided by Donna. +3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. +4. Run `donna -p llm -r sessions start` to start a new Donna session. +5. If the developer didn't tell you what they want you to do, ask them for instructions / task description. +6. Use Donna to perform the requested work: select most suitable Donna workflow to perform the requested work and run it. diff --git a/.agents/skills/donna-stop/SKILL.md b/.agents/skills/donna-stop/SKILL.md new file mode 100644 index 0000000..5aeb33f --- /dev/null +++ b/.agents/skills/donna-stop/SKILL.md @@ -0,0 +1,6 @@ +--- +name: donna-stop +description: Stop using Donna to perform work. +--- + +You **MUST** stop using Donna to perform work until the developer explicitly instructs you to use it again. diff --git a/.agents/skills/donna/SKILL.md b/.agents/skills/donna/SKILL.md new file mode 100644 index 0000000..dffed74 --- /dev/null +++ b/.agents/skills/donna/SKILL.md @@ -0,0 +1,12 @@ +--- +name: donna +description: Use Donna as a work orchestration tool. Follow Donna's instructions, run Donna's workflows and access Donna's artifacts to perform your work. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +--- + +**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. + +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +2. You **MUST** strictly follow all instructions provided by Donna. +3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. +4. If the developer told you what they want you to do, do it using Donna. +5. If you have no instructions from the developer, ask them for instructions / task description and then do it using Donna. diff --git a/donna/workspaces/initialization.py b/donna/workspaces/initialization.py index 39d6b88..0303c43 100644 --- a/donna/workspaces/initialization.py +++ b/donna/workspaces/initialization.py @@ -14,21 +14,26 @@ from donna.workspaces import errors as world_errors SKILLS_ROOT_DIR = pathlib.Path(".agents") / "skills" -DONNA_SKILL_ID = "donna" -DONNA_SKILL_FIXTURE_DIR = pathlib.Path("fixtures") / "skills" / DONNA_SKILL_ID +DONNA_SKILL_FIXTURE_DIR = pathlib.Path("fixtures") / "skills" + +# this list must only increase in size, +# do not remove old items from it, since users may upgrade from older versions of Donna +# where these skills were installed +DONNA_SKILL_CLEANUP_LIST = ["donna", "donna-do", "donna-start", "donna-stop"] def _sync_donna_skill(project_dir: pathlib.Path) -> None: source = importlib.resources.files("donna").joinpath(*DONNA_SKILL_FIXTURE_DIR.parts) - with importlib.resources.as_file(source) as source_dir: - target_dir = project_dir / SKILLS_ROOT_DIR / DONNA_SKILL_ID - target_dir.parent.mkdir(parents=True, exist_ok=True) - + # cleanup + for skill_id in DONNA_SKILL_CLEANUP_LIST: + target_dir = project_dir / SKILLS_ROOT_DIR / skill_id if target_dir.exists(): shutil.rmtree(target_dir) - shutil.copytree(source_dir, target_dir, dirs_exist_ok=True) + # copy all content of fixtures/skills to the skills directory + with importlib.resources.as_file(source) as source_dir: + shutil.copytree(source_dir, project_dir / SKILLS_ROOT_DIR, dirs_exist_ok=True) @unwrap_to_error From 32f4c98ef176b7b8fe2e5e7d8788438442f320f3 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Sun, 8 Feb 2026 19:55:45 +0100 Subject: [PATCH 03/17] wip --- .agents/skills/donna-do/SKILL.md | 9 +++++---- .agents/skills/donna-start/SKILL.md | 14 +++++--------- .agents/skills/donna-stop/SKILL.md | 2 +- .agents/skills/donna/SKILL.md | 12 ------------ donna/fixtures/skills/donna-do/SKILL.md | 9 +++++---- donna/fixtures/skills/donna-start/SKILL.md | 14 +++++--------- donna/fixtures/skills/donna-stop/SKILL.md | 2 +- donna/fixtures/skills/donna/SKILL.md | 12 ------------ donna/workspaces/initialization.py | 2 +- 9 files changed, 23 insertions(+), 53 deletions(-) delete mode 100644 .agents/skills/donna/SKILL.md delete mode 100644 donna/fixtures/skills/donna/SKILL.md diff --git a/.agents/skills/donna-do/SKILL.md b/.agents/skills/donna-do/SKILL.md index e0419eb..2f34bfc 100644 --- a/.agents/skills/donna-do/SKILL.md +++ b/.agents/skills/donna-do/SKILL.md @@ -1,12 +1,13 @@ --- name: donna-do -description: Use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +description: Use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. --- **The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. -1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command gives you an introduction to the project and to the Donna tool. 2. You **MUST** strictly follow all instructions provided by Donna. 3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. -4. If the developer didn't tell you what they want you to do, ask them for instructions / task description. -5. Select most suitable Donna workflow to perform the requested work and run it. +4. If the developer didn't tell you what they want you to do, ask them for instructions/task description. +5. Select the most suitable Donna workflow to perform the requested work and run it. +6. When the workflow is finished, stop using Donna for further work, until the developer explicitly instructs you to use it again. diff --git a/.agents/skills/donna-start/SKILL.md b/.agents/skills/donna-start/SKILL.md index 35b23a5..ca7f760 100644 --- a/.agents/skills/donna-start/SKILL.md +++ b/.agents/skills/donna-start/SKILL.md @@ -1,13 +1,9 @@ --- name: donna-start -description: Start new Donna session and use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +description: Start a new Donna session, do nothing else. Use this skill when the developer explicitly told you to use it. --- -**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. - -1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. -2. You **MUST** strictly follow all instructions provided by Donna. -3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. -4. Run `donna -p llm -r sessions start` to start a new Donna session. -5. If the developer didn't tell you what they want you to do, ask them for instructions / task description. -6. Use Donna to perform the requested work: select most suitable Donna workflow to perform the requested work and run it. +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command provides an introduction to the project and the Donna tool. +2. Run `donna -p llm -r sessions start` to start a new Donna session. +3. Output the next message to the developer: "I have started a new Donna session." +4. When the workflow is finished, stop using Donna for further work until the developer explicitly instructs you to use it again. diff --git a/.agents/skills/donna-stop/SKILL.md b/.agents/skills/donna-stop/SKILL.md index 5aeb33f..bbbff9e 100644 --- a/.agents/skills/donna-stop/SKILL.md +++ b/.agents/skills/donna-stop/SKILL.md @@ -1,6 +1,6 @@ --- name: donna-stop -description: Stop using Donna to perform work. +description: Stop using Donna to perform work, do nothing else. Use this skill when the developer explicitly told you to use it. --- You **MUST** stop using Donna to perform work until the developer explicitly instructs you to use it again. diff --git a/.agents/skills/donna/SKILL.md b/.agents/skills/donna/SKILL.md deleted file mode 100644 index dffed74..0000000 --- a/.agents/skills/donna/SKILL.md +++ /dev/null @@ -1,12 +0,0 @@ ---- -name: donna -description: Use Donna as a work orchestration tool. Follow Donna's instructions, run Donna's workflows and access Donna's artifacts to perform your work. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. ---- - -**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. - -1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. -2. You **MUST** strictly follow all instructions provided by Donna. -3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. -4. If the developer told you what they want you to do, do it using Donna. -5. If you have no instructions from the developer, ask them for instructions / task description and then do it using Donna. diff --git a/donna/fixtures/skills/donna-do/SKILL.md b/donna/fixtures/skills/donna-do/SKILL.md index e0419eb..2f34bfc 100644 --- a/donna/fixtures/skills/donna-do/SKILL.md +++ b/donna/fixtures/skills/donna-do/SKILL.md @@ -1,12 +1,13 @@ --- name: donna-do -description: Use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +description: Use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. --- **The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. -1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command gives you an introduction to the project and to the Donna tool. 2. You **MUST** strictly follow all instructions provided by Donna. 3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. -4. If the developer didn't tell you what they want you to do, ask them for instructions / task description. -5. Select most suitable Donna workflow to perform the requested work and run it. +4. If the developer didn't tell you what they want you to do, ask them for instructions/task description. +5. Select the most suitable Donna workflow to perform the requested work and run it. +6. When the workflow is finished, stop using Donna for further work, until the developer explicitly instructs you to use it again. diff --git a/donna/fixtures/skills/donna-start/SKILL.md b/donna/fixtures/skills/donna-start/SKILL.md index 35b23a5..ca7f760 100644 --- a/donna/fixtures/skills/donna-start/SKILL.md +++ b/donna/fixtures/skills/donna-start/SKILL.md @@ -1,13 +1,9 @@ --- name: donna-start -description: Start new Donna session and use Donna as a work orchestration tool and execute a workflow suitable for the developer request. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. +description: Start a new Donna session, do nothing else. Use this skill when the developer explicitly told you to use it. --- -**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. - -1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. -2. You **MUST** strictly follow all instructions provided by Donna. -3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. -4. Run `donna -p llm -r sessions start` to start a new Donna session. -5. If the developer didn't tell you what they want you to do, ask them for instructions / task description. -6. Use Donna to perform the requested work: select most suitable Donna workflow to perform the requested work and run it. +1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command provides an introduction to the project and the Donna tool. +2. Run `donna -p llm -r sessions start` to start a new Donna session. +3. Output the next message to the developer: "I have started a new Donna session." +4. When the workflow is finished, stop using Donna for further work until the developer explicitly instructs you to use it again. diff --git a/donna/fixtures/skills/donna-stop/SKILL.md b/donna/fixtures/skills/donna-stop/SKILL.md index 5aeb33f..bbbff9e 100644 --- a/donna/fixtures/skills/donna-stop/SKILL.md +++ b/donna/fixtures/skills/donna-stop/SKILL.md @@ -1,6 +1,6 @@ --- name: donna-stop -description: Stop using Donna to perform work. +description: Stop using Donna to perform work, do nothing else. Use this skill when the developer explicitly told you to use it. --- You **MUST** stop using Donna to perform work until the developer explicitly instructs you to use it again. diff --git a/donna/fixtures/skills/donna/SKILL.md b/donna/fixtures/skills/donna/SKILL.md deleted file mode 100644 index dffed74..0000000 --- a/donna/fixtures/skills/donna/SKILL.md +++ /dev/null @@ -1,12 +0,0 @@ ---- -name: donna -description: Use Donna as a work orchestration tool. Follow Donna's instructions, run Donna's workflows and access Donna's artifacts to perform your work. Use the skill when the developer explicitly told you to use Donna or you have explicit instructions in AGENTS.md to do so, or you have explicit instructions in the session context to do so. ---- - -**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. - -1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command give you an introduction to the project and to the Donna tool. -2. You **MUST** strictly follow all instructions provided by Donna. -3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. -4. If the developer told you what they want you to do, do it using Donna. -5. If you have no instructions from the developer, ask them for instructions / task description and then do it using Donna. diff --git a/donna/workspaces/initialization.py b/donna/workspaces/initialization.py index 0303c43..08e25f9 100644 --- a/donna/workspaces/initialization.py +++ b/donna/workspaces/initialization.py @@ -19,7 +19,7 @@ # this list must only increase in size, # do not remove old items from it, since users may upgrade from older versions of Donna # where these skills were installed -DONNA_SKILL_CLEANUP_LIST = ["donna", "donna-do", "donna-start", "donna-stop"] +DONNA_SKILL_CLEANUP_LIST = ["donna-do", "donna-start", "donna-stop"] def _sync_donna_skill(project_dir: pathlib.Path) -> None: From 21a4057c775fd16ec4a92958d116debd7d12a298 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Sun, 8 Feb 2026 20:06:40 +0100 Subject: [PATCH 04/17] wip --- AGENTS.md | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/AGENTS.md b/AGENTS.md index ca72014..c637849 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -4,8 +4,10 @@ This document provides instructions and guidelines for the AI agents working on Every agent MUST follow the rules and guidelines outlined in this document when performing their work. -## First actions - -**You MUST use `donna` tool to work on this project.** +## Donna tool Since this is the repository that contains the Donna project itself, you have direct access to the Donna CLI tool via `./bin/donna.sh` script. I.e. you develop Donna using Donna. + +In all commands that use `donna`, you MUST replace `donna` with `./bin/donna.sh` when you run the command. + +For example, instead of `donna artifacts view '*:intro'` you MUST run `./bin/donna.sh artifacts view '*:intro'`. From ba36d939990c19eb01b9a264878fa86bbc3e7751 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Sun, 8 Feb 2026 20:09:29 +0100 Subject: [PATCH 05/17] wip --- .donna/project/intro.md | 7 ------- donna/artifacts/intro.md | 8 +++----- 2 files changed, 3 insertions(+), 12 deletions(-) diff --git a/.donna/project/intro.md b/.donna/project/intro.md index 22d7cfb..4495691 100644 --- a/.donna/project/intro.md +++ b/.donna/project/intro.md @@ -22,13 +22,6 @@ The core idea is that most high-level workflows are more algorithmic than it may We may need coding agents on each step of the process, but there is no reason for agents to manage the whole grooming loop by themselves — it takes longer time, spends tokens and may lead to confusion of agents. -## Primary rules - -1. If you need to perform a work with Donna, you **MUST** select an appropriate Donna workflow to perform the work and run it. -2. If there is no appropriate workflow, ask the developer for a precise instructions on what to do. -3. List all workflows: `{{ donna.lib.list("**", tags=["workflow"]) }}` -4. List all specifications: `{{ donna.lib.list("**", tags=["specification"]) }}` - ## Dictionary - **Action request** — an instruction to the agent (who runs Donna) to perform the specified operations. Action requests are created by operations, like `donna.lib.request_action`. After finishing following the instructions of an action request, the agent MUST report back to Donna specifying the next operation to continue with. The list of next operations is specified in the action request itself. diff --git a/donna/artifacts/intro.md b/donna/artifacts/intro.md index 4f28492..8caf4d8 100644 --- a/donna/artifacts/intro.md +++ b/donna/artifacts/intro.md @@ -28,13 +28,11 @@ Artifact type tags: - `workflow` — workflow artifact — is set automatically by Donna. - `specification` — specification artifact — is set automatically by Donna. -{# We recommend using those tags in `project:` and `session:` worlds as well to keep consistency. #} - ## Instructions 1. On start of the YOUR session you **MUST** read and understand instruction on using the Donna tool `{{ donna.lib.view("donna:usage:cli") }}`. It **MUST** be a one time operation. Do not repeat it unless you forget how to use the tool. 2. If you need to perform a work with Donna, you **MUST** select an appropriate Donna workflow to perform the work and run it. 3. If there is no appropriate workflow, ask the developer for a precise instructions on what to do. -4. If you are executing a workflow operation and need to perform a complex action or changes, you SHOULD search for an appropriate workflow and run it (as a child workflow) — it is the intended way to use Donna. -5. List all workflows: `{{ donna.lib.list("**", tags=["workflow"]) }}` -6. List all specifications: `{{ donna.lib.list("**", tags=["specification"]) }}` +4. If you are executing a workflow operation and need to perform a complex action or changes, you SHOULD search for an appropriate workflow and run it as a child workflow — it is the intended way to use Donna. +5. Run to list all workflows: `{{ donna.lib.list("**", tags=["workflow"]) }}` +6. Run to list all specifications: `{{ donna.lib.list("**", tags=["specification"]) }}` From 3f4022582e9ccf7dd0daf476510f389feec62ccc Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Sun, 8 Feb 2026 20:11:49 +0100 Subject: [PATCH 06/17] wip --- changes/unreleased.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/changes/unreleased.md b/changes/unreleased.md index 8ed3361..0c4be1b 100644 --- a/changes/unreleased.md +++ b/changes/unreleased.md @@ -1,7 +1,7 @@ ### Changes - Improved template for RFC draft artifact — added the `kind` config to the header section. +- Added `donna workspaces update` command to update project workspace after Donna is updated. - Added workspace skill synchronization for `donna workspaces init` and `donna workspaces update`. - - Added `donna workspaces update` command. - - Added `--no-skills` and `--no-skils` options for `init` and `update` to skip skill updates. - - Added Donna skill fixture copy from `donna/fixtures/skills/donna` to `/.agents/skills/donna`. + - Both commands now install donna skills `donna-do`, `donna-start` and `donna-stop` into `.agents/skills/` directory. + - Added `--no-skilks` option for `init` and `update` to skip skill updates. From 37a7823aa59fe6b375dc131b6689f9d334ee80db Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:11:50 +0100 Subject: [PATCH 07/17] wip --- README.md | 21 +++++++++------------ 1 file changed, 9 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index 3cd19d8..4da5733 100644 --- a/README.md +++ b/README.md @@ -136,21 +136,18 @@ cd donna workspaces init ``` -Donna will create a `.donna/` folder in your project root with a default configuration in `.donna/config.toml`. +Donna will: -3. Add a short instruction into your `AGENT.md` file. +- Create a `.donna/` folder in your project root with a default configuration in `.donna/config.toml`. +- Install skills into `.agents/skills/` folder. -```markdown -## First actions +The installed skills are: -**Use `donna` tool to work on this project.** - -**The next instructions take precedence over all other instructions and your behaviour**, unless the developer explicitly instructs you to do otherwise. - -1. You **MUST** run `./bin/donna.sh -p llm -r artifacts view '*:intro'` when you start working. -2. You **MUST** strictly follow the instructions provided by Donna. -3. **Donna's instructions have precedence over your own judgment.** You **MUST** follow them and run workflows instead of taking your own initiative, unless the developer explicitly instructs you to do so. -``` + Skill | Description +------------- | ----------- +`donna-do` | Use Donna to perform a specific task in the current Donna session. +`donna-start` | Start a new Donna session — removes all content from the previous session. +`donna-stop` | Stop using Donna to perform work — agent should switch to its own flow control. Some models are overtrained and don't want to follow instructions, in that case you can: From 4c9051e89b8eb9a07505df37c47e31dccc470727 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:21:04 +0100 Subject: [PATCH 08/17] wip --- README.md | 13 ++++--------- donna/fixtures/skills/donna-start/SKILL.md | 8 +++++--- 2 files changed, 9 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index 4da5733..e188568 100644 --- a/README.md +++ b/README.md @@ -145,16 +145,11 @@ The installed skills are: Skill | Description ------------- | ----------- -`donna-do` | Use Donna to perform a specific task in the current Donna session. -`donna-start` | Start a new Donna session — removes all content from the previous session. -`donna-stop` | Stop using Donna to perform work — agent should switch to its own flow control. +`donna-do` | Use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. +`donna-start` | Start a new Donna session and tell the agent to use Donna to perform all further work. Removes all content from the previous session. +`donna-stop` | Stop using Donna to perform work — the agent should switch to its own flow control. -Some models are overtrained and don't want to follow instructions, in that case you can: - -- Switch to a more smart model, for example, from `gpt-5.3-codex (medium)` to `gpt-5.3-codex (high)`. -- Tune instructions to make them more suitable for the particular model. - -4. Ask your agent to do something like `Add a button that …`. The agent will discover the appropriate workflow and run it. +3. Ask your agent to do something like `$donna-do Add a button that …`. The agent will discover the appropriate workflow and execute it. ## Usage diff --git a/donna/fixtures/skills/donna-start/SKILL.md b/donna/fixtures/skills/donna-start/SKILL.md index ca7f760..409b311 100644 --- a/donna/fixtures/skills/donna-start/SKILL.md +++ b/donna/fixtures/skills/donna-start/SKILL.md @@ -1,9 +1,11 @@ --- name: donna-start -description: Start a new Donna session, do nothing else. Use this skill when the developer explicitly told you to use it. +description: Start a new Donna session and use Donna to perform all further work. Use this skill when the developer explicitly told you to use it. --- 1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command provides an introduction to the project and the Donna tool. 2. Run `donna -p llm -r sessions start` to start a new Donna session. -3. Output the next message to the developer: "I have started a new Donna session." -4. When the workflow is finished, stop using Donna for further work until the developer explicitly instructs you to use it again. +3. Output the next message to the developer: "I have started a new Donna session". +4. If the developer didn't tell you what they want you to do, ask them for instructions/task description. +5. Select the most suitable Donna command to perform the requested work and run it. +6. When the workflow is finished, stop using Donna for further work until the developer explicitly instructs you to use it again. From 739a0cddfc11f323ab835bbfd42b6536a3ca3872 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:21:46 +0100 Subject: [PATCH 09/17] wip --- .agents/skills/donna-start/SKILL.md | 8 +++++--- README.md | 2 -- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.agents/skills/donna-start/SKILL.md b/.agents/skills/donna-start/SKILL.md index ca7f760..409b311 100644 --- a/.agents/skills/donna-start/SKILL.md +++ b/.agents/skills/donna-start/SKILL.md @@ -1,9 +1,11 @@ --- name: donna-start -description: Start a new Donna session, do nothing else. Use this skill when the developer explicitly told you to use it. +description: Start a new Donna session and use Donna to perform all further work. Use this skill when the developer explicitly told you to use it. --- 1. You **MUST** run `donna -p llm -r artifacts view '*:intro'` when you start executing this skill, if you haven't done it yet. This command provides an introduction to the project and the Donna tool. 2. Run `donna -p llm -r sessions start` to start a new Donna session. -3. Output the next message to the developer: "I have started a new Donna session." -4. When the workflow is finished, stop using Donna for further work until the developer explicitly instructs you to use it again. +3. Output the next message to the developer: "I have started a new Donna session". +4. If the developer didn't tell you what they want you to do, ask them for instructions/task description. +5. Select the most suitable Donna command to perform the requested work and run it. +6. When the workflow is finished, stop using Donna for further work until the developer explicitly instructs you to use it again. diff --git a/README.md b/README.md index e188568..d520d65 100644 --- a/README.md +++ b/README.md @@ -141,8 +141,6 @@ Donna will: - Create a `.donna/` folder in your project root with a default configuration in `.donna/config.toml`. - Install skills into `.agents/skills/` folder. -The installed skills are: - Skill | Description ------------- | ----------- `donna-do` | Use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. From f56f99921cd777d0d454adbbd05286f3f8e30c6c Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:24:53 +0100 Subject: [PATCH 10/17] wip --- README.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index d520d65..0f57613 100644 --- a/README.md +++ b/README.md @@ -141,11 +141,11 @@ Donna will: - Create a `.donna/` folder in your project root with a default configuration in `.donna/config.toml`. - Install skills into `.agents/skills/` folder. - Skill | Description -------------- | ----------- -`donna-do` | Use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. -`donna-start` | Start a new Donna session and tell the agent to use Donna to perform all further work. Removes all content from the previous session. -`donna-stop` | Stop using Donna to perform work — the agent should switch to its own flow control. +Skills: + +- `donna-do` — use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. +- `donna-start` — start a new Donna session and tell the agent to use Donna to perform all further work. Removes all content from the previous session. +- `donna-stop` — stop using Donna to perform work — the agent should switch to its own flow control. 3. Ask your agent to do something like `$donna-do Add a button that …`. The agent will discover the appropriate workflow and execute it. From 641811a96fa696d2c05f816e3a22c19c58198320 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:25:17 +0100 Subject: [PATCH 11/17] wip --- README.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 0f57613..f95afb2 100644 --- a/README.md +++ b/README.md @@ -141,11 +141,11 @@ Donna will: - Create a `.donna/` folder in your project root with a default configuration in `.donna/config.toml`. - Install skills into `.agents/skills/` folder. -Skills: - -- `donna-do` — use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. -- `donna-start` — start a new Donna session and tell the agent to use Donna to perform all further work. Removes all content from the previous session. -- `donna-stop` — stop using Donna to perform work — the agent should switch to its own flow control. + Skill | Description +------------- | ----------- +`donna-do` | Use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. +`donna-start` | Start a new Donna session and tell the agent to use Donna to perform all further work. Removes all content from the previous session. +`donna-stop` | Stop using Donna to perform work — the agent should switch to its own flow control. 3. Ask your agent to do something like `$donna-do Add a button that …`. The agent will discover the appropriate workflow and execute it. From 556250a1a75bef4ee9643c0a85705d4d96194114 Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:28:47 +0100 Subject: [PATCH 12/17] wip --- README.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index f95afb2..c8018bb 100644 --- a/README.md +++ b/README.md @@ -141,14 +141,14 @@ Donna will: - Create a `.donna/` folder in your project root with a default configuration in `.donna/config.toml`. - Install skills into `.agents/skills/` folder. - Skill | Description -------------- | ----------- -`donna-do` | Use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. -`donna-start` | Start a new Donna session and tell the agent to use Donna to perform all further work. Removes all content from the previous session. -`donna-stop` | Stop using Donna to perform work — the agent should switch to its own flow control. - 3. Ask your agent to do something like `$donna-do Add a button that …`. The agent will discover the appropriate workflow and execute it. +## Skills + +- `donna-do` — use Donna to perform a specific task in the current Donna session. Creates a new session if there is no one. +- `donna-start` — start a new Donna session and tell the agent to use Donna to perform all further work. Removes all content from the previous session. +- `donna-stop` — stop using Donna to perform work — the agent should switch to its own flow control. + ## Usage **Donna is a CLI tool for agents.** You rarely need to use it directly. From cd807246f241ac008cda8319e8fc9cfccd60977f Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:43:29 +0100 Subject: [PATCH 13/17] wip --- README.md | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index c8018bb..c872196 100644 --- a/README.md +++ b/README.md @@ -100,13 +100,15 @@ Polishing is complete. What you may notice: -1. The workflow has a loop. -2. The workflow is a Markdown file. -3. Each h1 and h2 section has a config block, which is a TOML in code fences with `donna` marker. Those configs are invisible to the agent, but Donna uses them to understand the artifact structure. -4. The workflow has two `donna.lib.request_action` operations (`run_black`, `run_mypy`) and one `donna.lib.finish` (`finish`). -5. Transitions between operations are defined via `{{ goto("operation_id") }}` Jinja2 calls in the body of operations. -6. `donna.lib.request_action` is an operation that tells Donna to display instructions to the agent and wait for the agent to complete them. That allows the agent to focus on short, precise instructions, perform them, and push workflow forward. -7. `kind` attributes of sections are valid Python import paths, so you can easily extend Donna with your own code. +- The workflow is described in a readable Markdown file. +- The workflow has a loop. +- Each H1 and H2 section has a config block, which is a TOML in code fences with `donna` marker. Those configs are invisible to the agent, but Donna uses them to understand the artifact structure. +- H1 section describes the workflow as a whole. +- H2 sections describe workflow operations. +- The workflow has two `donna.lib.request_action` operations (`run_black`, `run_mypy`) and one `donna.lib.finish` (`finish`). +- Transitions between operations are defined via `{{ goto("operation_id") }}` Jinja2 calls in the body of operations. +- `donna.lib.request_action` is an operation that tells Donna to display instructions to the agent and wait for the agent to complete them. That allows the agent to focus on short, precise instructions, execute them, and advance the workflow. +- `kind` attributes of sections are valid Python import paths, so you can easily extend Donna with your own code. Directives, like `{{ goto("operation_id") }}`, render itself depending on the context: From e5598fca3500f1df8d14e9af16dac0db301f912d Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 11:57:53 +0100 Subject: [PATCH 14/17] wip --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index c872196..426ef28 100644 --- a/README.md +++ b/README.md @@ -189,6 +189,8 @@ Additionally, Donna will: - find and run (if any) polishing workflow to ensure the codebase is in a good state after the changes; - find and run (if any) workflow to update your changelog. +Note that the default Donna workflows are designed to be reliable and useful for a wide range of projects. They may not be optimal in terms of token usage or speed for your particular project. The intended use of Donna is to implement your own workflows that account for your project's specifics. + Points of interest: - [donna:rfc:specs:request_for_change](./donna/artifacts/rfc/specs/request_for_change.md) — specification of the RFC document. From 27fc0cd21023bf1adb88d1ee3ca998e1ddc76b3b Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 12:32:59 +0100 Subject: [PATCH 15/17] wip --- changes/unreleased.md | 3 ++ donna/artifacts/usage/cli.md | 2 +- donna/cli/commands/artifacts.py | 30 +++++++++++++--- donna/cli/types.py | 52 +++++++++++++++++++++++---- donna/workspaces/artifacts.py | 64 +++++++++++++++++++++++++++------ 5 files changed, 130 insertions(+), 21 deletions(-) diff --git a/changes/unreleased.md b/changes/unreleased.md index 0c4be1b..55814ec 100644 --- a/changes/unreleased.md +++ b/changes/unreleased.md @@ -5,3 +5,6 @@ - Added workspace skill synchronization for `donna workspaces init` and `donna workspaces update`. - Both commands now install donna skills `donna-do`, `donna-start` and `donna-stop` into `.agents/skills/` directory. - Added `--no-skilks` option for `init` and `update` to skip skill updates. +- Added stdin and extension-aware updates for `donna artifacts update`. + - Added `--extension` option to explicitly select artifact source extension. + - Added `-` stdin input support. diff --git a/donna/artifacts/usage/cli.md b/donna/artifacts/usage/cli.md index f7a4ae5..6d71775 100644 --- a/donna/artifacts/usage/cli.md +++ b/donna/artifacts/usage/cli.md @@ -145,7 +145,7 @@ Use the next commands to work with artifacts: - `donna -p artifacts view ` — get the meaningful (rendered) content of all matching artifacts. This command shows the rendered information about each artifact. Use this command when you need to read artifact content. - `donna -p artifacts fetch :` — download the original source of the artifact content, outputs the file path to the artifact's copy, you can change. Use this command when you need to change the content of the artifact. - `donna -p artifacts tmp .` — create a temporary file for artifact-related work and output its path. -- `donna -p artifacts update : ` — upload the given file as the artifact. Use this command when you finished changing the content of the artifact. +- `donna -p artifacts update : [--extension ]` — upload content from a file path or from stdin (`-`) as the artifact. If `--extension` is omitted, Donna infers it from the existing target artifact. - `donna -p artifacts copy ` — copy an artifact source to another artifact ID (can be in a different world). This overwrites the destination if it exists. - `donna -p artifacts move ` — copy an artifact source to another artifact ID and remove the original. This overwrites the destination if it exists. - `donna -p artifacts remove ` — remove artifacts matching a pattern. Use this command when you need to delete artifacts. diff --git a/donna/cli/commands/artifacts.py b/donna/cli/commands/artifacts.py index 19c47d2..1c10d34 100644 --- a/donna/cli/commands/artifacts.py +++ b/donna/cli/commands/artifacts.py @@ -1,4 +1,6 @@ import builtins +import pathlib +import sys from collections.abc import Iterable import typer @@ -6,6 +8,7 @@ from donna.cli import errors as cli_errors from donna.cli.application import app from donna.cli.types import ( + ExtensionOption, FullArtifactIdArgument, FullArtifactIdPatternArgument, InputPathArgument, @@ -98,11 +101,30 @@ def tmp( ] -@artifacts_cli.command(help="Create or replace the artifact with the contents of a file.") +@artifacts_cli.command(help="Create or replace an artifact from a file path or stdin.") @cells_cli -def update(id: FullArtifactIdArgument, input: InputPathArgument) -> Iterable[Cell]: - world_artifacts.update_artifact(id, input).unwrap() - return [operation_succeeded(f"Artifact `{id}` updated from '{input}'", artifact_id=str(id), input_path=str(input))] +def update( + id: FullArtifactIdArgument, + input: InputPathArgument, + extension: ExtensionOption = None, +) -> Iterable[Cell]: + if input == pathlib.Path("-"): + tmp_extension = extension or "tmp" + input_path = world_tmp.file_for_artifact(id, tmp_extension) + input_path.write_bytes(sys.stdin.buffer.read()) + input_display = "stdin" + else: + input_path = input + input_display = str(input) + + world_artifacts.update_artifact(id, input_path, extension=extension).unwrap() + return [ + operation_succeeded( + f"Artifact `{id}` updated from '{input_display}'", + artifact_id=str(id), + input_path=str(input_path), + ) + ] @artifacts_cli.command(help="Copy an artifact to another artifact ID (possibly across worlds).") diff --git a/donna/cli/types.py b/donna/cli/types.py index c1df81b..d16ad39 100644 --- a/donna/cli/types.py +++ b/donna/cli/types.py @@ -1,4 +1,5 @@ import pathlib +import re from typing import Annotated import typer @@ -55,6 +56,36 @@ def _parse_protocol_mode(value: str) -> Mode: raise typer.BadParameter(f"Unsupported protocol mode '{value}'. Expected one of: {allowed}.") from exc +def _parse_extension(value: str) -> str: + normalized = value.strip().lower().lstrip(".") + if not normalized: + raise typer.BadParameter("Extension must not be empty.") + + if re.fullmatch(r"[a-z0-9][a-z0-9_-]*", normalized) is None: + raise typer.BadParameter( + "Invalid extension format. Use letters, digits, underscore, and dash (for example: md, yaml)." + ) + + return normalized + + +def _parse_input_path(value: str) -> pathlib.Path: + normalized = value.strip() + if normalized == "-": + return pathlib.Path("-") + + path = pathlib.Path(normalized).expanduser() + if not path.exists(): + raise typer.BadParameter(f"Input path '{value}' does not exist.") + if not path.is_file(): + raise typer.BadParameter(f"Input path '{value}' is not a file.") + + if not path.is_absolute(): + path = path.resolve() + + return path + + ActionRequestIdArgument = Annotated[ ActionRequestId, typer.Argument( @@ -135,15 +166,24 @@ def _parse_protocol_mode(value: str) -> Mode: ] +ExtensionOption = Annotated[ + str | None, + typer.Option( + "--extension", + parser=_parse_extension, + help=( + "Optional artifact source extension to use for update " + "(for example: md, yaml). Accepts values with or without leading dot." + ), + ), +] + + InputPathArgument = Annotated[ pathlib.Path, typer.Argument( - exists=True, - file_okay=True, - dir_okay=False, - readable=True, - resolve_path=True, - help="Path to an existing local file used as input.", + parser=_parse_input_path, + help="Path to an existing local file used as input, or '-' to read from stdin.", ), ] diff --git a/donna/workspaces/artifacts.py b/donna/workspaces/artifacts.py index 3ed44f8..969ee52 100644 --- a/donna/workspaces/artifacts.py +++ b/donna/workspaces/artifacts.py @@ -46,9 +46,27 @@ class CanNotRemoveReadonlyWorld(ArtifactRemoveError): world_id: WorldId -class InputPathHasNoExtension(ArtifactUpdateError): - code: str = "donna.workspaces.input_path_has_no_extension" - message: str = "Input path has no extension to determine artifact source type" +class ArtifactExtensionCannotBeInferred(ArtifactUpdateError): + code: str = "donna.workspaces.artifact_extension_cannot_be_inferred" + message: str = "Cannot infer artifact extension. Provide `--extension` or update an existing artifact." + ways_to_fix: list[str] = [ + "Pass `--extension ` when updating the artifact.", + "Create/update an artifact that already exists and has a known extension.", + ] + + +class ArtifactExtensionMismatch(ArtifactUpdateError): + code: str = "donna.workspaces.artifact_extension_mismatch" + message: str = ( + "Provided extension `{error.provided_extension}` does not match existing artifact extension " + "`{error.existing_extension}`" + ) + provided_extension: str + existing_extension: str + ways_to_fix: list[str] = [ + "Use the existing artifact extension.", + "Omit `--extension` to use extension inferred from the existing artifact.", + ] class NoSourceForArtifactExtension(ArtifactUpdateError): @@ -95,28 +113,54 @@ def fetch_artifact(full_id: FullArtifactId, output: pathlib.Path) -> Result[None @unwrap_to_error -def update_artifact(full_id: FullArtifactId, input: pathlib.Path) -> Result[None, ErrorsList]: +def update_artifact( # noqa: CCR001 + full_id: FullArtifactId, input: pathlib.Path, extension: str | None = None +) -> Result[None, ErrorsList]: world = config().get_world(full_id.world_id).unwrap() if world.readonly: return Err([CanNotUpdateReadonlyWorld(artifact_id=full_id, path=input, world_id=world.id)]) - source_suffix = input.suffix.lower() content_bytes = input.read_bytes() - if not source_suffix: - return Err([InputPathHasNoExtension(artifact_id=full_id, path=input)]) + expected_extension = artifact_file_extension(full_id).unwrap_or(None) - source_config = config().find_source_for_extension(source_suffix) + requested_extension = extension.lstrip(".").lower() if extension is not None else None + + if expected_extension is None and requested_extension is None: + return Err([ArtifactExtensionCannotBeInferred(artifact_id=full_id, path=input)]) + + if expected_extension is None and requested_extension is not None: + source_suffix = requested_extension + elif expected_extension is not None and requested_extension is None: + source_suffix = expected_extension + elif expected_extension != requested_extension: + return Err( + [ + ArtifactExtensionMismatch( + artifact_id=full_id, + path=input, + provided_extension=requested_extension or "", + existing_extension=expected_extension or "", + ) + ] + ) + else: + assert expected_extension is not None + source_suffix = expected_extension + + normalized_source_suffix = f".{source_suffix}" + + source_config = config().find_source_for_extension(normalized_source_suffix) if source_config is None: - return Err([NoSourceForArtifactExtension(artifact_id=full_id, path=input, extension=source_suffix)]) + return Err([NoSourceForArtifactExtension(artifact_id=full_id, path=input, extension=normalized_source_suffix)]) render_context = ArtifactRenderContext(primary_mode=RenderMode.view) test_artifact = source_config.construct_artifact_from_bytes(full_id, content_bytes, render_context).unwrap() validation_result = test_artifact.validate_artifact() validation_result.unwrap() - world.update(full_id.artifact_id, content_bytes, source_suffix).unwrap() + world.update(full_id.artifact_id, content_bytes, normalized_source_suffix).unwrap() return Ok(None) From ff667acb5302850b254b80b1295eee7d5ca8d12d Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 12:37:32 +0100 Subject: [PATCH 16/17] wip --- README.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/README.md b/README.md index 426ef28..6e045dc 100644 --- a/README.md +++ b/README.md @@ -437,3 +437,7 @@ How to reach me: - Create an [issue](https://github.com/Tiendil/donna/issues). Any format and theme is welcome. - Comment on one of the existing issues. Feedback, especially on [proposals](https://github.com/Tiendil/donna/issues?q=is%3Aissue%20state%3Aopen%20label%3Aproposal). - Start a [discussion](https://github.com/Tiendil/donna/discussions). + +## Projects that use Donna + +- [Feeds Fun](https://github.com/Tiendil/feeds.fun) — news reader with tags, scoring, and AI. From 27f34eb5d673bd9508aa4baa970199a24ca2838e Mon Sep 17 00:00:00 2001 From: "Aliaksei Yaletski (Tiendil)" Date: Mon, 9 Feb 2026 12:41:13 +0100 Subject: [PATCH 17/17] wip --- changes/{unreleased.md => next_release.md} | 0 docker-compose.yml | 2 +- 2 files changed, 1 insertion(+), 1 deletion(-) rename changes/{unreleased.md => next_release.md} (100%) diff --git a/changes/unreleased.md b/changes/next_release.md similarity index 100% rename from changes/unreleased.md rename to changes/next_release.md diff --git a/docker-compose.yml b/docker-compose.yml index fa85d9b..45a5721 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -8,4 +8,4 @@ services: dockerfile: ./docker/Dockerfile volumes: - - ${PWD}/donna:/repository/donna + - ${PWD}:/repository