@daedalus-ai/cli
v1.0.0
Published
Daedalus is an engineering framework that standardizes AI-assisted software development.
Maintainers
Readme
Daedalus
Daedalus is an engineering framework that standardizes AI-assisted software development, delivered as an npm CLI.
Daedalus is a CLI framework. It is not an SDK, not a VS Code extension, and not tied to any single AI provider.
Status: complete. Every command listed below is implemented — the deterministic core (
init/update/graph/context/doctor/plugin) works with zero AI configured, and the engineering workflow (investigate/implement/review/qa/learn) runs its deterministic steps unconditionally and its AI steps once a provider is configured viadaedalus provider login. See docs/ARCHITECTURE.md for how the pieces fit together.
Install
The npm package is @daedalus-ai/cli (published under the daedalus-ai
organization); the CLI executable it installs is daedalus.
npm install -g @daedalus-ai/clidaedalus initOr run without installing:
npx @daedalus-ai/cli initOnce installed (globally, or invoked via npx @daedalus-ai/cli), every
example below uses the daedalus executable directly.
Commands
| Command | Purpose |
| ----------------------- | --------------------------------------------------------------------------------------------- |
| daedalus init | Initialize a new Daedalus project |
| daedalus update | Incrementally regenerate .ai/indexes/ |
| daedalus graph | Sync the local knowledge graph (.ai/database.db) |
| daedalus context | Retrieve the minimal relevant context for a request/ticket |
| daedalus investigate | Investigate a ticket/request; writes .ai/tickets/<id>/INVESTIGATION.md |
| daedalus implement | Guided planning + implementation guidance; writes PLAN.md/IMPLEMENTATION.md |
| daedalus review | Deterministic static checks + AI code review; writes REVIEW.md (BLOCKING/WARNING/SUGGESTION/PASS) |
| daedalus qa | Runs the project's test/lint/typecheck/build scripts + AI QA pass; writes QA.md |
| daedalus learn | Extracts candidate knowledge from a session into .ai/knowledge/ (list/approve/reject) |
| daedalus doctor | Diagnoses workspace/environment health (PASS/WARNING/ERROR) |
| daedalus plugin | Manage daedalus-plugin-* packages (list/enable/disable) |
| daedalus provider | Manage AI provider configuration (list/login/switch/models/test) |
| daedalus version | Show detailed version information |
| daedalus help | List every registered command (built-in or plugin) with its options |
The standard -h/--help and -v/--version flags also work and are
provided by the CLI framework itself.
Every AI-assisted command works with zero AI provider configured —
investigate/review/qa always run their deterministic parts (static
checks, git diff, project context) and clearly say "No AI provider is
configured" instead of silently skipping or faking the AI-assisted part.
implement/learn require a provider (there is no deterministic
substitute for "write a plan" or "extract knowledge") and say so plainly
rather than writing a fake plan.
daedalus init
Analyzes the current directory and creates the standard Daedalus workspace
(.ai/) if it isn't already there.
npx daedalus initWhat it does, in order:
- Detects the workspace — empty directory, existing Git repository,
existing project (via manifest files like
package.json,pyproject.toml,go.mod, ...), an existing.ai/folder, or an existing Daedalus installation (.ai/project.json) — and prints what it found. - Scaffolds
.ai/with its fixed set of subdirectories (config,indexes,knowledge,patterns,tickets,reports,logs,cache,history,memory,agents,plugins,providers,temp). - Writes
.ai/project.json— a versioned config recording framework version, timestamps, and workspace type. Detected languages/frameworks are left as empty placeholders; populating them is a future indexing command's job, notinit's. - Writes
.ai/MEMORY.mdwith empty section headings (Project Summary, Business Domain, Architecture, Coding Standards, Known Patterns, Lessons, Decisions, Frequently Changed Files, Business Rules, Ticket History) for future workflows and humans to fill in. - Writes
.ai/README.mdexplaining what was generated. - Updates
.gitignore(only if a Git repository is present) to exclude.ai/cache/,.ai/logs/, and.ai/temp/— the only.ai/subdirectories considered ephemeral. Everything else under.ai/is meant to be committed and shared with the team.
Safety guarantees:
- Idempotent — running
daedalus initagain never corrupts or deletes existing data. Directories and files that already exist are left untouched and reported as skipped. .ai/project.jsonis the one exception: on re-run, only itsupdatedAt/frameworkVersionfields are refreshed; every other field (repositories, plugins, providers, settings, detected languages/ frameworks) is preserved exactly as found.- Nothing outside
.ai/and.gitignoreis ever modified, and existing.gitignorecontent is only appended to, never rewritten.
See src/core/init/ for the implementation: WorkspaceDetector,
DirectoryScaffolder, ProjectConfigService, MemoryFileService,
AiReadmeService, and GitignoreService each own one responsibility, and
InitService sequences them.
daedalus update
Scans the workspace (via the Workspace Intelligence
Engine), runs the Project Indexing
Engine, and (re)writes 15 Markdown documents plus
a fingerprint manifest into .ai/indexes/ — routes, API endpoints,
databases, modules, components, services, dependencies, an in-memory
architecture graph, and statistics. Requires daedalus init to have run
first.
npx daedalus updateBoth daedalus update and daedalus graph run through the Incremental
Indexing Engine automatically: only the
projects actually affected by a change are re-indexed, everything else is
reused from .ai/cache/. Pass --full to force a complete rebuild:
npx daedalus update --fullDetection is entirely deterministic and manifest/convention-based
(app.get(...), [HttpGet], @RequestMapping, Route::get(...), ORM
decorators, ...) — no AI, no LLM calls, and nothing outside .ai/indexes/
is ever written. Unlike daedalus init's MEMORY.md/README.md, every
file under .ai/indexes/ is regenerated (overwritten) on every run — it's
generated knowledge, not user-authored content.
Framework/language support is plugin-ready: Angular, React, Vue, Node
(Express/NestJS), .NET (ASP.NET Core), Spring Boot, Laravel, Flutter, and
Python each have a dedicated IIndexProvider in src/core/indexing/providers/,
registered via IndexProviderRegistry — the core IndexCoordinator never
hardcodes framework logic.
daedalus graph
Runs the same scan-and-index pipeline as daedalus update, then syncs the
result into a local SQLite database at .ai/database.db instead of (or
alongside) Markdown — the central, queryable knowledge graph every future
subsystem is meant to read from rather than re-scanning the filesystem.
Requires daedalus init to have run first.
npx daedalus graph
# npx daedalus graph --full # force a complete rebuildReports schema version, per-table node counts, relationship count, and a
health/integrity check (PRAGMA integrity_check/foreign_key_check) —
never raw SQL. Every write goes through GraphRepository
(src/core/knowledge-graph/), the only class in the codebase allowed to
write SQL; everything else uses GraphService. See
docs/KNOWLEDGE_GRAPH.md for the schema,
relationship model, and migration strategy — including why this module
uses Node's built-in node:sqlite instead of a third-party native
dependency, and two real bundler/transform bugs that surfaced from doing
so.
daedalus context
Deterministically retrieves the minimal relevant slice of the workspace
for a natural-language request or ticket — no AI, no LLM, no embeddings.
Reads only already-persisted artifacts (.ai/database.db +
.ai/cache/workspace.snapshot.json); requires daedalus graph to have
run first.
daedalus context --query "Add a payment method to the debtor profile"
daedalus context --ticket DC-245
daedalus context --query "..." --budget large # small | medium | large | unlimitedWrites a ranked, budget-trimmed .ai/cache/context.json and a
human-readable .ai/reports/context.md on every run (served from cache
when nothing relevant has changed). See
docs/CONTEXT_ENGINE.md for the resolver
architecture, ranking model, budget tiers, and the .ai/knowledge//
.ai/tickets/ file format this phase defines.
daedalus provider
Manages AI provider configuration. Daedalus never calls Claude/OpenAI/
Gemini/Ollama directly from a command — every generation goes through
ProviderManager.generate(), which routes to whichever provider is
currently configured.
daedalus provider list
daedalus provider login claude --api-key sk-...
daedalus provider login ollama --base-url http://localhost:11434
daedalus provider switch claude
daedalus provider models
daedalus provider testSix adapters ship today: Claude, OpenAI, Gemini, OpenRouter, Ollama, and
LM Studio — all behind the identical IProvider interface, with retry,
rate limiting, and token/cost tracking handled once in ProviderManager,
never duplicated per adapter. Credentials never land in
.ai/config/providers.json in plain text — they go through a separate,
OS-keychain-ready ICredentialStore. See
docs/PROVIDER_ENGINE.md for the full
architecture, streaming, and the PromptBuilder that automatically
injects workspace/index/context/workflow-state into a request.
The engineering workflow: investigate / implement / review / qa / learn
These five commands are Daedalus's core value proposition: keep the project's brain available to every AI-assisted session, instead of the AI rediscovering the repository from scratch every time.
npx daedalus investigate --query "Add payment history to debtor profile"
npx daedalus implement --ticket DC-245 # after investigate, or standalone
npx daedalus review --ticket DC-245
npx daedalus qa --ticket DC-245
npx daedalus learn # extracts candidates from every ticket sessionEvery artifact lands under .ai/tickets/<ticketId>/ — INVESTIGATION.md,
PLAN.md, IMPLEMENTATION.md, REVIEW.md, QA.md, plus a STATUS.json
recording the last step, status, and (on failure) a nextAction — so a
failed or interrupted session leaves useful state to resume from, rather
than losing the whole run.
investigateruns theinvestigateworkflow (src/workflows/investigate.workflow.ts): gathers project context, then (with a provider configured) aninvestigatoragent step produces the report body. Without a provider, it still writes a deterministic report from the ticket/request/detected projects and says so.implementruns the existingimplementworkflow'splanneranddeveloperagent steps, writingPLAN.md/IMPLEMENTATION.md. It never edits the target project's source files itself — no file-editing tool loop exists in this framework —IMPLEMENTATION.mdis guidance for a human (or a future execution agent) to apply, followed byreview/qa.reviewalways runs the target project's ownlint/typechecknpm scripts (whichever exist) and gathers a git diff (core/quality/GitDiffService); with a provider configured, it also runs an AI review of that diff. The final verdict (core/quality/classifyReview) is exactly one ofBLOCKING/WARNING/SUGGESTION/PASS— a failed static check always wins, and a clean run with no diff evidence or no provider is reported asWARNING, neverPASS— "never report a clean review when the evidence you were given is incomplete."qaalways runs the target project's owntest/lint/typecheck/buildscripts; with a provider configured, it also runs an AI pass assessing regression risk, edge cases, and suggested manual test cases. Final status is never "done" if a required script failed.learnreads every ticket's artifacts under.ai/tickets/, and (requires a provider) asks alearneragent step to extract candidate knowledge, parsed from- [kind] Title: contentlines into.ai/knowledge/*.mdwithapproved: false. Nothing an AI session produces becomes trusted project truth automatically —daedalus learn list/daedalus learn approve <file>/daedalus learn reject <file>are the only way a candidate is promoted or discarded, and that's always a human decision.
daedalus doctor
Diagnoses workspace and environment health — Node/npm/git availability,
.ai/ structure integrity, project.json validity, writable directories,
knowledge-graph health, index cache freshness, provider configuration, and
workflow-engine readiness. Every check is deterministic; nothing here calls
an AI provider.
npx daedalus doctorEach check reports PASS, WARNING, or ERROR with an actionable
remediation line. See src/core/doctor/DoctorService.ts.
daedalus plugin
Discovers and manages daedalus-plugin-* npm packages installed in the
current project's node_modules (top-level or scoped, e.g.
@acme/daedalus-plugin-foo). A plugin's default export is validated
structurally ({ name, version, createCommands?, capabilities? }) before
it's trusted; a plugin that fails to load or throws while registering its
commands is reported and skipped — it never takes down the core CLI.
npx daedalus plugin list
npx daedalus plugin disable daedalus-plugin-example
npx daedalus plugin enable daedalus-plugin-examplecreateCommands(output) lets a plugin add new CLI commands;
capabilities are named functions a plugin-typed workflow step (see
docs/WORKFLOW_ENGINE.md) can invoke by name.
See src/core/plugins/.
Development
Requires Node.js 22.5+ (for the built-in node:sqlite module used by
daedalus graph) and npm.
npm install # install dependencies
npm run dev # run the CLI from source (tsx), e.g. `npm run dev -- init`
npm run build # bundle to dist/ with tsup
npm test # run the Vitest suite
npm run lint # ESLint
npm run typecheck # tsc --noEmit
npm run format # Prettier --writeAfter npm run build, you can run the built CLI directly:
node ./bin/daedalus.js initOr link it locally:
npm link
daedalus initProject structure
src/
index.ts Executable entry point
cli.ts Bootstrap: wires the DI container, builds the program, handles errors
commands/ One file per CLI command, all implementing ICommand
core/ CommandRegistry, CommandLoader, ProgramFactory (Commander adapter), DI container
core/init/ The daedalus init engine: detection, scaffolding, config, memory/readme, .gitignore
core/workspace-intelligence/ Scans a workspace into an in-memory WorkspaceModel (see docs/WORKSPACE_INTELLIGENCE.md)
core/indexing/ Builds .ai/indexes/ from a WorkspaceModel (see docs/INDEXING_ENGINE.md)
core/incremental/ Decides what changed and re-indexes only that (see docs/INCREMENTAL_INDEXING.md)
core/knowledge-graph/ Syncs .ai/database.db (SQLite) from an IndexModel (see docs/KNOWLEDGE_GRAPH.md)
core/context/ Deterministic context retrieval for a request/ticket (see docs/CONTEXT_ENGINE.md)
core/workflows/ Execution framework for multi-step AI workflows, incl. agent/provider/plugin
step handlers (see docs/WORKFLOW_ENGINE.md)
workflows/ Built-in WorkflowDefinitions (*.workflow.ts) consumed by core/workflows/
core/providers/ Provider-independent AI layer: IProvider adapters behind
one ProviderManager.generate() (see docs/PROVIDER_ENGINE.md)
core/plugins/ Plugin discovery/loading (daedalus-plugin-*) (see docs/PLUGIN_SYSTEM.md)
core/tickets/ .ai/tickets/<id>/ artifact I/O + external ticket adapters (see docs/TICKETS.md)
core/knowledge/ Knowledge candidate lifecycle (.ai/knowledge/) (see docs/KNOWLEDGE_ENGINE.md)
core/quality/ Deterministic review/QA evidence gathering (git diff, npm scripts) (see docs/QUALITY_ENGINE.md)
core/doctor/ Deterministic health checks behind `daedalus doctor`
services/ Reusable core infrastructure every command depends on (see docs/CORE_INFRASTRUCTURE.md)
utils/ OutputService (user-facing CLI messages), DaedalusError hierarchy
config/ Package metadata resolution
types/ Shared TypeScript contracts (ICommand, CommandMetadata)
templates/workflows/ The six built-in workflows in YAML form, loaded by core/workflows/WorkflowLoader
tests/ Vitest unit tests, mirroring src/
docs/ Architecture and design notesSee docs/ARCHITECTURE.md for the reasoning behind
this layout, the choice of Commander as the parsing layer, and the seams
reserved for the plugin system and future workflows. See
docs/CORE_INFRASTRUCTURE.md for the
services/ layer specifically: FileSystemService, WorkspaceService,
ConfigurationService, LoggerService, ProgressService,
TemplateService, JsonService, MarkdownService, EnvironmentService,
and PathService. See
docs/WORKSPACE_INTELLIGENCE.md for the
Workspace Intelligence Engine — the scanner and detectors that build an
in-memory model of a workspace's projects, languages, frameworks, and
repository structure, used by every future command that needs to
understand "what is this project" before doing anything else. See
docs/INDEXING_ENGINE.md for the Project
Indexing Engine (routes/APIs/databases/modules → .ai/indexes/*.md) and
docs/KNOWLEDGE_GRAPH.md for the Knowledge
Graph Engine (the same facts, persisted to SQLite at .ai/database.db).
See docs/INCREMENTAL_INDEXING.md for the
Incremental Indexing Engine that both daedalus update and daedalus
graph run through automatically — fingerprinting, git-assisted change
detection, dependency-impact analysis, and the --full escape hatch. See
docs/CONTEXT_ENGINE.md for the Context
Retrieval Engine daedalus context runs — deterministic ranking of
files/APIs/routes/entities/tickets/knowledge relevant to a request,
budget-trimmed for an LLM's limited context window.
See docs/WORKFLOW_ENGINE.md for the Workflow
Engine — execution orchestration (dependency resolution, retry, timeout,
conditional/skip execution, progress reporting) plus the agent/
provider/plugin step handlers every AI-assisted command runs through.
See docs/PROVIDER_ENGINE.md for the AI Provider
Layer daedalus provider manages — six adapters (Claude/OpenAI/Gemini/
OpenRouter/Ollama/LM Studio) behind one provider-agnostic
ProviderManager.generate(), with retry/rate-limiting/usage-tracking
handled once, never per adapter, and a PromptBuilder that automatically
injects workspace/index/context/workflow state into a request. See
docs/PLUGIN_SYSTEM.md for how daedalus-plugin-*
packages are discovered, validated, and loaded. See
docs/KNOWLEDGE_ENGINE.md for the candidate ->
approved knowledge lifecycle behind daedalus learn. See
docs/QUALITY_ENGINE.md for the deterministic
evidence-gathering (PackageScriptRunner, GitDiffService,
classifyReview) behind daedalus review/daedalus qa. See
docs/TICKETS.md for the .ai/tickets/<id>/ artifact
layout and the TicketAdapter extension point for external trackers.
Adding a command (contributor note)
Every built-in command follows the same pattern:
- Create
src/commands/<name>.command.tsexporting a class extendingBaseCommandwith itsmetadata. - Add it to the list in
src/commands/index.ts.
No other file needs to change — there is no switch statement mapping names to behavior.
Contributing
Issues and pull requests are welcome. Please run npm run lint,
npm run typecheck, and npm test before submitting.
