No description
  • TypeScript 94.4%
  • JavaScript 3.5%
  • CSS 2%
  • HTML 0.1%
Find a file
Repository files (latest commit first)
Filename Latest commit message Latest commit date
2026-09-10 12:21:46 +00:00
demo Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
e2e add live two-way architecture editing 2026-09-09 19:56:16 -05:00
fixture Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
packages keep generated LikeC4 files out of workspace loading 2026-09-10 07:20:09 -05:00
scripts Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
.gitignore prepare the CLI package for npm publication 2026-09-10 06:12:08 -05:00
.npmrc Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
.tool-versions Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
AGENTS.md prepare the CLI package for npm publication 2026-09-10 06:12:08 -05:00
biome.json Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
LICENSE prepare the CLI package for npm publication 2026-09-10 06:12:08 -05:00
package.json prepare the CLI package for npm publication 2026-09-10 06:12:08 -05:00
pnpm-lock.yaml prepare the CLI package for npm publication 2026-09-10 06:12:08 -05:00
pnpm-workspace.yaml Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
prompt.md Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
README.md prepare the CLI package for npm publication 2026-09-10 06:12:08 -05:00
tsconfig.base.json Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
tsconfig.json Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00
vitest.config.ts Add an Excalidraw editor for LikeC4 architecture projects. 2026-09-09 13:03:45 -05:00

likec4-excalidraw

Excalidraw-based visual editor for LikeC4 architecture projects. MIT licensed.

npm install -g likec4-excalidraw
likec4-excalidraw ./architecture

or without a global install:

npx likec4-excalidraw ./architecture

The command starts a local web server and prints:

LikeC4 Excalidraw editor
Project: /home/user/project/architecture
Listening: http://localhost:4242

Opening that URL launches an Excalidraw canvas backed by the supplied LikeC4 project.

CLI

likec4-excalidraw [architecture-directory]
Option Description
--host <host> Bind address. Default: 127.0.0.1 (localhost only unless you pass another host)
--port <port> Preferred port. Default: 4242. Falls back to a free port if busy
--open Open the editor in a browser
--readonly Disable scene writes and generated DSL export
--help Show help
--version Show version

Default architecture directory is ..

MCP server

The editor exposes a project-aware Streamable HTTP MCP endpoint on the same network server:

http://127.0.0.1:4242/mcp

Configure an MCP client with that URL after starting likec4-excalidraw. Pass mcpToken when embedding startServer to require Authorization: Bearer <token>.

Available tools:

  • get_architecture, get_scene, and get_diagnostics
  • create_element, update_element, and delete_element
  • create_relationship and create_view
  • validate
  • get_canvas_screenshot for a whole-canvas PNG or a scene-coordinate area

Mutating tools update .likec4/excalidraw.json and the validated editor-owned excalidraw.generated.c4 source.

How it works

Excalidraw canvas
    ↓
semantic projection
    ↓
LikeC4 model
    ↓
validation / DSL export

Excalidraw is the editing surface. LikeC4 remains the semantic model and validator. The editor does not infer an architecture from arbitrary drawing appearance.

Once a shape is promoted to a LikeC4-managed object, identity lives in namespaced customData, not in position, label, or style.

Object states

Managed

Explicitly mapped to a LikeC4 element, relationship, or view. Identity is stored in customData.likec4.

Candidate

Looks like it could become a LikeC4 object (for example an arrow between two managed elements) but has not been promoted. Candidates never silently change the model. Use Convert to LikeC4 element / Convert to LikeC4 relationship.

Decoration

Normal Excalidraw content: notes, freedraw, screenshots, headings, icons. Decorations stay fully usable and are ignored during LikeC4 export.

Semantic vs visual containment

Moving a managed child outside its parent does not rewrite FQN or parent. The editor warns, then offers:

  • Move back inside
  • Change semantic parent
  • Ignore mismatch

Dropping a new candidate inside a managed container may suggest that parent. Silent semantic mutation does not happen.

Persistence

Scene state is stored next to the architecture project:

architecture/
  existing-model.c4
  .likec4/excalidraw.json
  excalidraw.generated.c4

.likec4/excalidraw.json is the Excalidraw presentation: geometry, decorations, unmanaged objects, and semantic references. Schema version is 1.

LikeC4 source files are not rewritten when you drag a shape. Semantic canvas edits are written to the editor-owned excalidraw.generated.c4 file.

Export and source ownership

Semantic canvas edits update excalidraw.generated.c4 live after validation. Existing project files are imported as context and are never destructively rewritten; the editor-owned file contains the merged architecture snapshot.

Export LikeC4 also validates and writes an explicit snapshot. An empty architecture directory is bootstrapped with actor, system, and service kinds plus a Landscape view.

customData.likec4 schema

All metadata is namespaced:

{
  "customData": {
    "likec4": {
      "version": 1,
      "role": "element",
      "fqn": "cloud.backend.api",
      "kind": "service"
    }
  }
}

Relationships:

{
  "customData": {
    "likec4": {
      "version": 1,
      "role": "relationship",
      "relationId": "rel_1",
      "source": "cloud.frontend",
      "target": "cloud.backend.api"
    }
  }
}

Views / frames:

{
  "customData": {
    "likec4": {
      "version": 1,
      "role": "view",
      "viewId": "backend"
    }
  }
}

role may also be candidate. Identity is never inferred from visible text.

Development

Requires Node 22+ and pnpm.

pnpm install
pnpm test
pnpm typecheck
pnpm lint
pnpm build
pnpm --filter likec4-excalidraw start -- ./fixture
pnpm publish:check
pnpm pack

The published package is likec4-excalidraw. Workspace libraries stay private; the CLI build bundles them and copies the app into packages/cli. Run pnpm build before pnpm pack or pnpm --filter likec4-excalidraw publish.

The fixture under fixture/ is a small LikeC4 project used by tests and local smoke runs.

For a larger walkthrough, use demo/:

pnpm --filter likec4-excalidraw start -- ./demo

Current limitations

  • Deployment model editing, dynamic views, and advanced predicate editing are deferred.
  • Export uses explicit view membership (include cloud.backend) rather than reconstructing include cloud.backend.**.
  • LikeC4 manual-layout round-trip is not written back. Excalidraw geometry is authoritative inside this app. Layouted coordinates are used only for the initial import when available.
  • Duplication is handled after the fact: copy/paste of a managed object becomes a candidate instead of a second identity. Use Add existing element to this view for another presentation of the same FQN.
  • The UI follows Excalidraw's own look rather than a separate design system.

Library notes

Current integrations (LikeC4 1.59.x, @excalidraw/excalidraw 0.18.x):

  • Load with LikeC4.fromWorkspace / fromSource
  • Query with computedModel(), layoutedModel(), getErrors()
  • Export prefers @likec4/core Builder + @likec4/generators when available, with a deterministic DSL serializer fallback
  • Manual LikeC4 layout snapshots exist but are not a stable write API here, so they are read-only via layoutedModel()