Skip to content
AtomUICommunityPublic

About

A native desktop client for AI coding agents, built with Avalonia and AtomUI. Multi-provider, MCP, integrated terminal, local resumable sessions, NativeAOT.

Resources

Stars

39 stars

Watchers

0 watching

Forks

Repository files navigation

TKCode

TKCode

A desktop AI agent client built with Avalonia and AtomUI.

简体中文 · English

.NET Avalonia NativeAOT Status


TKCode conversation view

TKCode is a native desktop client for working with AI coding agents. It runs its agent loop in a separate Agent Host process, talks to models through three wire protocols, and keeps every session as a local, append-only JSONL file. The whole client is designed to publish as a NativeAOT binary.

Status: early development. The core pieces (protocol adapters, agent loop, session store, Host process, desktop UI) exist, but the app is not yet a finished product, and APIs and file formats may change.

Features

  • Project- and session-centric UI. Dark-first design with light and system-following themes, Chinese and English UI, and a command palette (⌘K) with nested pages and keyboard navigation.
  • Multiple providers and models. Built-in provider catalog with one API key per provider, custom OpenAI-compatible and local endpoints, and hot-reloaded settings.
  • Three protocol adapters: OpenAI Chat Completions, OpenAI Responses, and Anthropic Messages, with thinking / reasoning replay and fast mode where the provider supports it.
  • Coding tools for the built-in agent: read, write, edit, ls, glob, grep, bash (with background tasks), task lists, web_fetch, web_search, and sub-agents.
  • External agent runtimes. Claude Code, Codex, and ACP agents found on the machine run inside TKCode and share its approval flow.
  • Approvals and permission modes. Read-only actions inside the workspace pass; everything else can ask the UI first, once or for the whole session.
  • Composer. @ file mentions, / commands and skills, Agent / Plan roles, and image attachments. Global assets live in ~/.tkcode, project assets in .agents/.
  • MCP. stdio and HTTP servers from settings.json or .mcp.json, with tools, resources, prompts, elicitation, and import / export.
  • Workbench. File tree, code and Markdown previews, and an integrated terminal (libghostty-vt, separate pty host that keeps sessions alive, search).
  • Resumable sessions. Sessions are stored as JSONL trees under ~/.tkcode/sessions/ and can be listed, renamed, pinned, reopened, and continued.
  • Streaming Markdown via StreamMark (code highlighting, Mermaid, LaTeX).
  • In-app updates from GitHub Releases, plus a system tray icon.

Screenshots

New chat
New chat. Pick a device, project, model, and role.
Workbench
Workbench. Conversation, code preview, and file tree side by side.
Command palette
Command palette (⌘K). Commands, projects, and chats.
Light theme
Light theme. Follows the system or set explicitly.

The screenshots are rendered headlessly from a sample project. Regenerate them with tools/readme-screenshots.sh.

Architecture

TKCode.Desktop ──(JSON-RPC 2.0 over stdio)──▶ TKCode.AgentHost
     │                                            │
     └──▶ TKCode.Rpc.Contracts ◀───────────────────┤
                                                  ▼
                                        TKCode.Agent.Coding   sessions, tools, system prompt, AGENTS.md
                                                  ▼
                                           TKCode.Agent       agent loop, tool contract, events
                                                  ▼
                                            TKCode.Ai         message model, streaming events, wire adapters
Project Responsibility
src/TKCode.Ai Unified message model, streaming events, OpenAI / Anthropic adapters
src/TKCode.Agent Agent loop, tool abstraction, approval hook, steer / follow-up queues
src/TKCode.Agent.Coding Coding session, JSONL session store, system prompt builder, built-in tools
src/TKCode.Rpc.Contracts Host ↔ UI interfaces and DTOs, minimal JSON-RPC 2.0 implementation
src/TKCode.AgentHost Standalone process that hosts sessions and translates agent events into RPC notifications
src/TKCode.Config Settings types and parsing, shared by Host and Desktop
src/TKCode.Runtimes External agent runtimes: Claude Code, Codex, ACP
src/TKCode.Mcp MCP client: server configuration, connection pool, tool / resource / prompt bridging
src/TKCode.Terminal.* Terminal: libghostty-vt core, PTY, pty host process and protocol, Avalonia view
src/TKCode.Desktop Avalonia application: window, theme, views, view models, Host connection

Dependencies point one way. TKCode.Ai, TKCode.Agent, and TKCode.Agent.Coding have no UI dependency and are marked IsAotCompatible.

Getting started

Prerequisites

  • .NET 11 RC2 SDK (11.0.100-rc.2.26504.105 or newer in the same major/minor release; pinned in global.json, latestFeature roll-forward with prereleases enabled). Runtime Async is enabled for all projects, including NativeAOT builds.

  • .NET 10 Runtime, required by AtomUI 6.2.6's isolated build tools. A .NET 10 SDK installation also provides it. Published NativeAOT applications include their runtime.

  • A Rust toolchain, used once to build the native LaTeX library for StreamMark.

  • StreamMark comes in as a git submodule (external/StreamMark). Its StreamMark.* packages are read from a local feed (packages/streammark, set in nuget.config), so pack them first:

    git submodule update --init
    tools/streammark/pack.sh
  • AtomUI (AtomUI.Desktop.Controls 6.2.6) is consumed from nuget.org; Avalonia is pinned to 12.1.4, AtomUI's minimum. No source checkout is needed.

Build and run

dotnet build TKCode.slnx
dotnet run --project src/TKCode.Desktop

The desktop build copies the Agent Host into the output directory's agenthost/ folder, and the app starts it on demand.

Run the tests

dotnet test TKCode.slnx

The Desktop tests render real components headlessly (Avalonia.Headless + Skia) and write PNG snapshots to the test output's snapshots/ directory, or to TKCODE_SNAPSHOT_DIR if set. tools/readme-screenshots.sh renders the README screenshots into docs/images/ the same way.

Publish (NativeAOT)

Both the desktop app and the Agent Host are published with PublishAot=true. On macOS you can build an app bundle:

tools/package_macos_app.sh osx-arm64        # outputs artifacts/TKCode.app

Or publish directly:

dotnet publish src/TKCode.Desktop -c Release -r osx-arm64

Smoke test a published build (runs the real app headlessly against the Fake provider):

artifacts/publish/osx-arm64/TKCode --smoke --out=frame.png

Configuration

Settings live in ~/.tkcode/settings.json (JSONC, with a generated JSON Schema for editor completion). Set TKCODE_HOME to use a different directory. The file is hot-reloaded; invalid edits keep the last good configuration and show the error in the settings view.

{
  "$schema": "./settings.schema.json",
  "model": "anthropic/claude-opus-5-5",   // <provider>/<model>
  "language": "en-US",                     // zh-CN | en-US
  "theme": "system",                       // system | dark | light

  "providers": {
    // Built-in provider: only the key is required
    "anthropic": { "apiKey": "{env:ANTHROPIC_API_KEY}" },

    // Custom OpenAI-compatible endpoint
    "my-gateway": {
      "name": "My Gateway",
      "api": "chat",                       // chat | responses | messages
      "baseUrl": "https://gw.example.com/v1",
      "apiKey": "{env:MY_GATEWAY_KEY}",
      "models": { "qwen3-coder": { "contextWindow": 262144, "reasoning": true } }
    }
  }
}

API keys can be plain text, {env:VAR}, or $VAR. Saving from the UI sets the file mode to 0600. See docs/settings.md for the full specification.

Documentation

Document Contents
docs/architecture.md Technical decisions, layering, RPC, UI and theming, NativeAOT rules
docs/settings.md settings.json format and merge rules
docs/design/builtin-agent-tools.md Built-in agent system prompt and tool design
docs/design/external-agent-runtimes.md Claude Code, Codex, and ACP runtimes
docs/design/composer.md Composer: mentions, commands, skills, roles
docs/design/mcp.md MCP client
docs/design/auto-update.md In-app updates and the release pipeline
docs/terminal/ Terminal architecture, pty host, and roadmap
docs/design/motion.md Motion guidelines
docs/protocols/ Wire protocol specs the adapters implement

Roadmap

  • Harden the protocol adapters and external runtimes against recorded provider traffic.
  • Context compaction, session branching and fork, and a diff view for changes.
  • Terminal: split panes, shell profiles, SSH, and agent integration (see docs/terminal/13-roadmap.md).
  • Signed and notarized macOS builds.

Contributing

Issues and pull requests are welcome once the project settles. Please keep these rules in mind:

  • NativeAOT. TKCode.Ai, TKCode.Agent, TKCode.Agent.Coding, TKCode.Desktop, and TKCode.AgentHost must stay AOT-safe. Use source-generated JSON contexts and no reflection or runtime code generation. Check that an AOT publish produces zero IL/AOT warnings.
  • UI components. Use AtomUI through NuGet and its public theme tokens. Do not copy or modify AtomUI source.
  • Strings. UI text comes from src/TKCode.Desktop/Localization/strings.tsv. Regenerate the catalogs with tools/gen_strings.py; do not hand-edit the generated files.

License

TKCode is licensed under the Apache License 2.0.

About

A native desktop client for AI coding agents, built with Avalonia and AtomUI. Multi-provider, MCP, integrated terminal, local resumable sessions, NativeAOT.

Resources

Stars

39 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages