Skip to content

Commit 08b03ed

Browse files
refactor: rewrite kimi-cli from Python to Bun + TypeScript + React Ink
Complete rewrite of the CLI from Python to TypeScript/Bun with React Ink UI, including OpenAI-compatible LLM provider, slash commands, tool system, subagent support, and all upstream Python fixes synced from main. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent a8f09bc commit 08b03ed

196 files changed

Lines changed: 34322 additions & 1 deletion

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.
Lines changed: 134 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,134 @@
1+
name: CI - Kimi CLI (TypeScript)
2+
3+
on:
4+
push:
5+
branches: [main]
6+
pull_request:
7+
branches: [main]
8+
9+
permissions:
10+
contents: write
11+
12+
jobs:
13+
typecheck-and-test:
14+
name: Typecheck & Test
15+
runs-on: ubuntu-latest
16+
steps:
17+
- uses: actions/checkout@v4
18+
19+
- uses: oven-sh/setup-bun@v2
20+
with:
21+
bun-version: latest
22+
23+
- run: bun install --frozen-lockfile
24+
25+
- name: Typecheck
26+
run: ./node_modules/.bin/tsc --noEmit --skipLibCheck
27+
28+
- name: Test
29+
run: bun test
30+
31+
build-binaries:
32+
name: Build Binary (${{ matrix.os }}-${{ matrix.arch }})
33+
needs: typecheck-and-test
34+
runs-on: ${{ matrix.runner }}
35+
strategy:
36+
fail-fast: false
37+
matrix:
38+
include:
39+
- os: linux
40+
arch: x64
41+
runner: ubuntu-latest
42+
target: bun-linux-x64
43+
artifact: kimi-linux-x64
44+
- os: linux
45+
arch: arm64
46+
runner: ubuntu-latest
47+
target: bun-linux-arm64
48+
artifact: kimi-linux-arm64
49+
- os: darwin
50+
arch: x64
51+
runner: macos-13
52+
target: bun-darwin-x64
53+
artifact: kimi-darwin-x64
54+
- os: darwin
55+
arch: arm64
56+
runner: macos-14
57+
target: bun-darwin-arm64
58+
artifact: kimi-darwin-arm64
59+
- os: windows
60+
arch: x64
61+
runner: windows-latest
62+
target: bun-windows-x64
63+
artifact: kimi-windows-x64
64+
65+
steps:
66+
- uses: actions/checkout@v4
67+
68+
- uses: oven-sh/setup-bun@v2
69+
with:
70+
bun-version: latest
71+
72+
- run: bun install --frozen-lockfile
73+
74+
- name: Build standalone binary
75+
run: bun build src/kimi_cli_ts/index.ts --compile --outfile dist/kimi --target=${{ matrix.target }}
76+
77+
- name: Verify binary (unix)
78+
if: matrix.os != 'windows'
79+
run: |
80+
chmod +x dist/kimi
81+
dist/kimi --version
82+
dist/kimi --help
83+
84+
- name: Verify binary (windows)
85+
if: matrix.os == 'windows'
86+
run: |
87+
dist\kimi.exe --version
88+
dist\kimi.exe --help
89+
90+
- name: Upload artifact
91+
uses: actions/upload-artifact@v4
92+
with:
93+
name: ${{ matrix.artifact }}
94+
path: dist/kimi*
95+
if-no-files-found: error
96+
97+
release:
98+
name: Create Release
99+
needs: build-binaries
100+
if: github.event_name == 'push' && github.ref == 'refs/heads/main' && startsWith(github.event.head_commit.message, 'release:')
101+
runs-on: ubuntu-latest
102+
steps:
103+
- uses: actions/checkout@v4
104+
105+
- name: Get version
106+
id: version
107+
run: echo "version=$(node -p "require('./package.json').version")" >> $GITHUB_OUTPUT
108+
109+
- name: Download all artifacts
110+
uses: actions/download-artifact@v4
111+
with:
112+
path: artifacts/
113+
114+
- name: Prepare release assets
115+
run: |
116+
mkdir -p release
117+
for dir in artifacts/kimi-*; do
118+
name=$(basename "$dir")
119+
if [[ "$name" == *windows* ]]; then
120+
(cd "$dir" && zip -r "../../release/${name}.zip" .)
121+
else
122+
chmod +x "$dir/kimi"
123+
tar -czf "release/${name}.tar.gz" -C "$dir" kimi
124+
fi
125+
done
126+
ls -la release/
127+
128+
- name: Create GitHub Release
129+
uses: softprops/action-gh-release@v2
130+
with:
131+
tag_name: v${{ steps.version.outputs.version }}
132+
name: v${{ steps.version.outputs.version }}
133+
files: release/*
134+
generate_release_notes: true

.gitignore

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,4 +44,15 @@ node_modules/
4444
static/
4545
.memo/
4646
.entire
47-
.claude
47+
.claude
48+
49+
# TypeScript / Bun
50+
out
51+
*.tgz
52+
coverage
53+
*.lcov
54+
logs
55+
*.log
56+
*.tsbuildinfo
57+
.eslintcache
58+
.cache

CLAUDE.md

Lines changed: 111 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
---
2+
description: Use Bun instead of Node.js, npm, pnpm, or vite.
3+
globs: "*.ts, *.tsx, *.html, *.css, *.js, *.jsx, package.json"
4+
alwaysApply: false
5+
---
6+
7+
Default to using Bun instead of Node.js.
8+
9+
- Use `bun <file>` instead of `node <file>` or `ts-node <file>`
10+
- Use `bun test` instead of `jest` or `vitest`
11+
- Use `bun build <file.html|file.ts|file.css>` instead of `webpack` or `esbuild`
12+
- Use `bun install` instead of `npm install` or `yarn install` or `pnpm install`
13+
- Use `bun run <script>` instead of `npm run <script>` or `yarn run <script>` or `pnpm run <script>`
14+
- Bun automatically loads .env, so don't use dotenv.
15+
16+
## APIs
17+
18+
- `Bun.serve()` supports WebSockets, HTTPS, and routes. Don't use `express`.
19+
- `bun:sqlite` for SQLite. Don't use `better-sqlite3`.
20+
- `Bun.redis` for Redis. Don't use `ioredis`.
21+
- `Bun.sql` for Postgres. Don't use `pg` or `postgres.js`.
22+
- `WebSocket` is built-in. Don't use `ws`.
23+
- Prefer `Bun.file` over `node:fs`'s readFile/writeFile
24+
- Bun.$`ls` instead of execa.
25+
26+
## Testing
27+
28+
Use `bun test` to run tests.
29+
30+
```ts#index.test.ts
31+
import { test, expect } from "bun:test";
32+
33+
test("hello world", () => {
34+
expect(1).toBe(1);
35+
});
36+
```
37+
38+
## Frontend
39+
40+
Use HTML imports with `Bun.serve()`. Don't use `vite`. HTML imports fully support React, CSS, Tailwind.
41+
42+
Server:
43+
44+
```ts#index.ts
45+
import index from "./index.html"
46+
47+
Bun.serve({
48+
routes: {
49+
"/": index,
50+
"/api/users/:id": {
51+
GET: (req) => {
52+
return new Response(JSON.stringify({ id: req.params.id }));
53+
},
54+
},
55+
},
56+
// optional websocket support
57+
websocket: {
58+
open: (ws) => {
59+
ws.send("Hello, world!");
60+
},
61+
message: (ws, message) => {
62+
ws.send(message);
63+
},
64+
close: (ws) => {
65+
// handle close
66+
}
67+
},
68+
development: {
69+
hmr: true,
70+
console: true,
71+
}
72+
})
73+
```
74+
75+
HTML files can import .tsx, .jsx or .js files directly and Bun's bundler will transpile & bundle automatically. `<link>` tags can point to stylesheets and Bun's CSS bundler will bundle.
76+
77+
```html#index.html
78+
<html>
79+
<body>
80+
<h1>Hello, world!</h1>
81+
<script type="module" src="./frontend.tsx"></script>
82+
</body>
83+
</html>
84+
```
85+
86+
With the following `frontend.tsx`:
87+
88+
```tsx#frontend.tsx
89+
import React from "react";
90+
91+
// import .css files directly and it works
92+
import './index.css';
93+
94+
import { createRoot } from "react-dom/client";
95+
96+
const root = createRoot(document.body);
97+
98+
export default function Frontend() {
99+
return <h1>Hello, world!</h1>;
100+
}
101+
102+
root.render(<Frontend />);
103+
```
104+
105+
Then, run index.ts
106+
107+
```sh
108+
bun --hot ./index.ts
109+
```
110+
111+
For more information, read the Bun API docs in `node_modules/bun-types/docs/**.md`.

0 commit comments

Comments
 (0)