Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 4 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -257,12 +257,14 @@ For now, code and documentation pull requests are accepted only from repository
The same engine that powers the TUI also drives a browser frontend:

```bash
mcode-web # http://127.0.0.1:8080 (loopback by default)
mcode-web # http://127.0.0.1:18090 (loopback by default)
mcode web # same thing — `web` and `webui` both work
mcode webui --port 8123 # custom port, prints the URL
```

From a source checkout use `pnpm mcode-web`.
From a source checkout use `pnpm mcode-web`. Without `--port` the server starts
on 18090 and moves to the next free port when 18090 is taken, printing the URL it
bound; an explicit `--port` is pinned and never moves.

The Web UI streams chat over SSE, renders tool calls and permission prompts, manages sessions and workspaces (with a modal directory picker over `/api/fs/*`, confined to allowed workspace roots), shows the current model in the selector, and mounts a read-only session **trajectory studio** at `/trajectory/`. It binds loopback by default; LAN exposure is explicit opt-in and token-gated. See [packages/webui](packages/webui/README.md) and [docs/webui.md](docs/webui.md).

Expand Down
6 changes: 4 additions & 2 deletions README_ZH.md
Original file line number Diff line number Diff line change
Expand Up @@ -256,12 +256,14 @@ node /absolute/path/to/minimax-code/dist/cli.js
驱动 TUI 的同一引擎也可以驱动浏览器前端:

```bash
mcode-web # http://127.0.0.1:8080(默认只绑定回环地址)
mcode-web # http://127.0.0.1:18090(默认只绑定回环地址)
mcode web # 等价写法 —— `web` 与 `webui` 均可
mcode webui --port 8123 # 自定义端口,启动后打印访问地址
```

源码构建目录下使用 `pnpm mcode-web`。
源码构建目录下使用 `pnpm mcode-web`。不带 `--port` 时服务器从 18090 启动,
18090 被占用就换下一个空闲端口,并打印实际绑定的地址;显式传入的 `--port`
会被钉住,不会自动后移。

Web UI 通过 SSE 流式输出对话,渲染工具调用与权限确认,管理会话与工作区(含模态目录选择器,接口限制在允许的工作区根内),模型选择器常显当前模型,并在 `/trajectory/` 挂载只读的会话**轨迹工作室**。默认仅绑定回环地址;局域网暴露需显式开启并通过令牌鉴权。详见 [packages/webui](packages/webui/README.md) 与 [docs/webui.md](docs/webui.md)。

Expand Down
6 changes: 4 additions & 2 deletions docs/webui.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ The Web UI (`packages/webui`) is the browser frontend for MiniMax Code. It uses
## Launch

```bash
mcode-web # http://127.0.0.1:8080
mcode-web # http://127.0.0.1:18090
mcode web # equivalent — `web` and `webui` both resolve
mcode webui --port 8123 --host 127.0.0.1
mcode webui --token "$(openssl rand -hex 16)" --host 0.0.0.0 # LAN, token-gated
Expand All @@ -17,6 +17,8 @@ node packages/webui/server.js # direct, from a checkout

The command resolves the webui package (installed `dist/webui/` or source `packages/webui/`), spawns the server as a child process, and points it back at the running CLI through `MCODE_WEBUI_SELF_ENTRY`. The webui then spawns `node <cli> acp` per active browser tab.

Without `--port` the server starts on 18090 and moves to the next free port when 18090 is taken, logging the URL it bound — the launcher opens that one. An explicit `--port` (or `PORT`) is pinned: it never moves, so a taken port exits with EADDRINUSE instead.

## Running a development build

The development Web UI runs alongside an installed official mcode without
Expand All @@ -29,7 +31,7 @@ From a checkout of this repository:

```bash
corepack pnpm install && corepack pnpm build # once, and after engine changes
node dist/cli.js webui # dev Web UI on 127.0.0.1:8080
node dist/cli.js webui # dev Web UI on 127.0.0.1:18090
node dist/cli.js webui --port 8123 # keep the installed one free
```

Expand Down
6 changes: 4 additions & 2 deletions docs/webui.zh-CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ Web UI(`packages/webui`)是 MiniMax Code 的浏览器前端。它使用与 T
## 启动

```bash
mcode-web # http://127.0.0.1:8080
mcode-web # http://127.0.0.1:18090
mcode web # equivalent — `web` and `webui` both resolve
mcode webui --port 8123 --host 127.0.0.1
mcode webui --token "$(openssl rand -hex 16)" --host 0.0.0.0 # LAN, token-gated
Expand All @@ -17,6 +17,8 @@ node packages/webui/server.js # direct, from a checkout

该命令解析 webui 包(已安装的 `dist/webui/` 或源码 `packages/webui/`),把服务器作为子进程启动,并通过 `MCODE_WEBUI_SELF_ENTRY` 将其指回正在运行的 CLI。然后 webui 会为每个活动的浏览器标签页生成一个 `node <cli> acp`。

不传 `--port` 时服务器从 18090 启动,若 18090 被占用就换下一个空闲端口,并打印实际绑定的地址 —— 启动器打开的就是这个地址。显式指定的 `--port`(或 `PORT`)会被钉住:不会自动后移,端口被占用时以 EADDRINUSE 退出。

## 运行开发构建

开发版 Web UI 可以与已安装的官方 mcode 并行运行而不冲突:
Expand All @@ -29,7 +31,7 @@ node packages/webui/server.js # direct, from a checkout

```bash
corepack pnpm install && corepack pnpm build # once, and after engine changes
node dist/cli.js webui # dev Web UI on 127.0.0.1:8080
node dist/cli.js webui # dev Web UI on 127.0.0.1:18090
node dist/cli.js webui --port 8123 # keep the installed one free
```

Expand Down
4 changes: 3 additions & 1 deletion packages/tui/src/cli/mcode-web-entry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,9 @@ import { parseArgs } from 'node:util';
import { runTuiWebuiCommand } from './run-webui-command.js';

const usage = `Usage: mcode-web [--port <number>] [--host <address>] [--token <value>] [--no-open]
Starts the MiniMax Code Web UI (same as 'mcode webui' / 'mcode web').`;
Starts the MiniMax Code Web UI (same as 'mcode webui' / 'mcode web').
Without --port the server starts on 18090 and moves to the next free port when
18090 is taken; an explicit --port is pinned and never moves.`;

let values: ReturnType<typeof parseArgs<{ port: string; host: string; token: string; open: boolean; 'no-open': boolean }>>['values'];
try {
Expand Down
4 changes: 3 additions & 1 deletion packages/tui/src/cli/program.ts
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,9 @@ export function createTuiProgram(options: CreateTuiProgramOptions): Command {
// `web` reads as the Web UI, not as a TUI prompt — accept both spellings.
.alias('web')
.description('Start the MiniMax Code Web UI (browser frontend driven by the same engine)')
.option('--port <number>', 'HTTP port (default 8080)', parsePort)
// An explicit --port is pinned: the webui binds it or exits, because
// docker port publishing and healthchecks address the configured value.
.option('--port <number>', 'HTTP port (default 18090, which moves to the next free port when taken)', parsePort)
.option('--host <address>', 'bind address (default 127.0.0.1; LAN exposure is opt-in)')
.option('--token <value>', 'auth token required for non-local requests')
.option('--no-open', 'print the URL without opening a browser')
Expand Down
4 changes: 2 additions & 2 deletions packages/webui/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ repository root for the full people & history record.

```bash
# From a built checkout (or an installed mcode CLI):
mcode webui # http://127.0.0.1:8080
mcode webui # http://127.0.0.1:18090
mcode webui --port 8123 --host 127.0.0.1

# Direct launch (development):
Expand All @@ -37,7 +37,7 @@ Recommended on non-loopback networks:
```bash
export TOKEN="$(openssl rand -hex 16)"
mcode webui --host 0.0.0.0
# open http://<lan-ip>:8080/?token=$TOKEN
# open http://<lan-ip>:18090/?token=$TOKEN
```

## What's in the box
Expand Down
4 changes: 2 additions & 2 deletions packages/webui/README.zh-CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ PR #56 的轨迹工作室),并作为 `packages/webui` 迁移入产品。完

```bash
# 从已构建的检出(或已安装的 mcode CLI):
mcode webui # http://127.0.0.1:8080
mcode webui # http://127.0.0.1:18090
mcode webui --port 8123 --host 127.0.0.1

# 直接启动(开发):
Expand All @@ -37,7 +37,7 @@ node packages/webui/server.js
```bash
export TOKEN="$(openssl rand -hex 16)"
mcode webui --host 0.0.0.0
# 打开 http://<lan-ip>:8080/?token=$TOKEN
# 打开 http://<lan-ip>:18090/?token=$TOKEN
```

## 目录内容
Expand Down
12 changes: 6 additions & 6 deletions packages/webui/docs/API.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ All non-API routes return static files (`server.js` → `serveStatic` /

## Conventions

- **Base URL**: `http://127.0.0.1:8080` (or LAN IP if enabled)
- **Base URL**: `http://127.0.0.1:18090` (or LAN IP if enabled)
- **Path prefix**: `/api/`
- **Content-Type**: `application/json; charset=utf-8` for both request and response
- **Auth header**: if `TOKEN` env is set, every request must include either
Expand All @@ -36,7 +36,7 @@ Returns server status. No auth required, no CID required.
```json
{
"ok": true,
"port": 8080,
"port": 18090,
"defaultModel": "minimax_api/MiniMax-M3",
"defaultWorkspace": "C:\\Users\\you\\.minimax-code\\webui",
"mcodeCmd": "C:\\Users\\you\\.minimax-code\\mcode.cmd",
Expand Down Expand Up @@ -341,12 +341,12 @@ state changes (see [ARCHITECTURE.md §5 SSE state push](./ARCHITECTURE.md#5-sse-
{
"ok": true,
"lanBroadcast": true,
"port": 8080,
"port": 18090,
"host": "127.0.0.1",
"lanIp": "192.168.1.50",
"lanUrl": "http://192.168.1.50:8080",
"lanUrlWithToken": "http://192.168.1.50:8080/?token=…", // 🔒 v2 — FIRST-RUN BOOTSTRAP ONLY: present while tokenAcknowledged=false, omitted entirely after ack (UI falls back to lanUrl); re-issued once per rotation
"localUrl": "http://127.0.0.1:8080",
"lanUrl": "http://192.168.1.50:18090",
"lanUrlWithToken": "http://192.168.1.50:18090/?token=…", // 🔒 v2 — FIRST-RUN BOOTSTRAP ONLY: present while tokenAcknowledged=false, omitted entirely after ack (UI falls back to lanUrl); re-issued once per rotation
"localUrl": "http://127.0.0.1:18090",
"lanBind": false, // 🔒 v2 — persisted LAN-bind opt-in; true binds 0.0.0.0 on next boot (env HOST still wins)
"bindHost": "127.0.0.1", // 🔒 v2 — what the NEXT boot resolves to (env HOST > lanBind > loopback)
"lanExposed": false, // 🔒 v2 — effective bind is not loopback
Expand Down
12 changes: 6 additions & 6 deletions packages/webui/docs/API.zh-CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@

## 约定

- **基础 URL**:`http://127.0.0.1:8080`(若启用则为局域网 IP)
- **基础 URL**:`http://127.0.0.1:18090`(若启用则为局域网 IP)
- **路径前缀**:`/api/`
- **Content-Type**:请求与响应均为 `application/json; charset=utf-8`
- **认证头**:若设置了 `TOKEN` 环境变量,每个请求必须包含以下二者之一
Expand All @@ -36,7 +36,7 @@
```json
{
"ok": true,
"port": 8080,
"port": 18090,
"defaultModel": "minimax_api/MiniMax-M3",
"defaultWorkspace": "C:\\Users\\you\\.minimax-code\\webui",
"mcodeCmd": "C:\\Users\\you\\.minimax-code\\mcode.cmd",
Expand Down Expand Up @@ -339,12 +339,12 @@ Linux 上为 `/`)
{
"ok": true,
"lanBroadcast": true,
"port": 8080,
"port": 18090,
"host": "127.0.0.1",
"lanIp": "192.168.1.50",
"lanUrl": "http://192.168.1.50:8080",
"lanUrlWithToken": "http://192.168.1.50:8080/?token=…", // 🔒 v2 — FIRST-RUN BOOTSTRAP ONLY: present while tokenAcknowledged=false, omitted entirely after ack (UI falls back to lanUrl); re-issued once per rotation
"localUrl": "http://127.0.0.1:8080",
"lanUrl": "http://192.168.1.50:18090",
"lanUrlWithToken": "http://192.168.1.50:18090/?token=…", // 🔒 v2 — FIRST-RUN BOOTSTRAP ONLY: present while tokenAcknowledged=false, omitted entirely after ack (UI falls back to lanUrl); re-issued once per rotation
"localUrl": "http://127.0.0.1:18090",
"lanBind": false, // 🔒 v2 — persisted LAN-bind opt-in; true binds 0.0.0.0 on next boot (env HOST still wins)
"bindHost": "127.0.0.1", // 🔒 v2 — what the NEXT boot resolves to (env HOST > lanBind > loopback)
"lanExposed": false, // 🔒 v2 — effective bind is not loopback
Expand Down
14 changes: 14 additions & 0 deletions packages/webui/docs/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,20 @@ This project follows [Keep a Changelog](https://keepachangelog.com/).
The `## Unreleased` section at the top tracks changes that have
landed on the development branch but are not yet cut into a release.

## Unreleased

### Changed

- **默认端口 8080 → 18090**。8080 在桌面机与开发机上被各类服务占用得太频繁。
显式设置的 `PORT`(或 `mcode-web --port`)仍按精确值处理,不受此影响。
- **默认端口被占用时自动回退**到下一个空闲端口(最多尝试 20 个),并打印实际绑定
的端口 —— 启动器(`mcode-web` / `mcode webui`)打开的就是这个地址。此前端口被
占用会以 EADDRINUSE 退出;又因为全局 `uncaughtException` 处理器只记录不退出,
进程还可能停在“活着但没有在监听”的状态。
- CORS origin 信任集、`/api/health`、state 快照与 LAN 分享 URL 改为按**实际监听
端口**(`getServingPort()`)计算。否则回退之后的浏览器 origin 会被自身的 CSRF
网关拒绝,分享 URL 也会指向没有服务在听的端口。

## v2.0.0 — 2026-09-20 (工业化重写,同步自 MiniMax-Code-Plugins PR #55 @ 7b4aae8)

v1.x 单体 `server.js` 的工业化重写。本轮同步包含 PR #55 全量 26 提交,
Expand Down
19 changes: 14 additions & 5 deletions packages/webui/docs/DEVELOPMENT.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ Zero npm install. Clone, run:
```powershell
cd ~/.minimax-code/webui
node server.js
# → http://127.0.0.1:8080
# → http://127.0.0.1:18090
```

If you want a debug session (verbose SSE, no cache, injectable events):
Expand Down Expand Up @@ -145,7 +145,7 @@ command; the webui picks it up on connect.
## Testing without mcode

1. Set `$env:DEBUG_INJECT = '1'` before `node server.js`.
2. Open `http://127.0.0.1:8080/?debug=1` (or just check the right
2. Open `http://127.0.0.1:18090/?debug=1` (or just check the right
panel — the debug panel is always visible).
3. In the browser console:
```js
Expand Down Expand Up @@ -186,9 +186,18 @@ After changing `public/app/main.js`:
2. Bump N. (Current value: see the comment above the script tag.)

### Change the default port
```powershell
$env:PORT = 8080
18090 is a default, not a pinned value: when it is taken the server walks
forward to the next free port and logs the one it bound. Setting `PORT` (or
passing `--port` to `mcode-web`) pins the port instead — a taken pinned port
exits with EADDRINUSE rather than moving, so docker port publishing and
healthchecks keep addressing the configured value.

```bash
# default port: 18090, or the next free port when 18090 is taken
node server.js

# pinned to 7891 — never moves
PORT=7891 node server.js
```

### Enable LAN sharing
Expand All @@ -214,7 +223,7 @@ The webui will spawn a fresh one on the next send.
The `/api/settings` endpoint is exempt from the LAN guard by design.
From any machine on the LAN, even with `lanBroadcast: false`:
```bash
curl -X POST http://192.168.1.50:8080/api/settings \
curl -X POST http://192.168.1.50:18090/api/settings \
-H 'Content-Type: application/json' \
-d '{"lanBroadcast": true}'
```
Expand Down
18 changes: 13 additions & 5 deletions packages/webui/docs/DEVELOPMENT.zh-CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
```powershell
cd ~/.minimax-code/webui
node server.js
# → http://127.0.0.1:8080
# → http://127.0.0.1:18090
```

如果想要调试会话(详细 SSE、无缓存、可注入事件):
Expand Down Expand Up @@ -146,7 +146,7 @@ webui 会在连接时获取它。
## 在没有 mcode 的情况下测试

1. 在 `node server.js` 之前设置 `$env:DEBUG_INJECT = '1'`。
2. 打开 `http://127.0.0.1:8080/?debug=1`(或者直接查看右侧
2. 打开 `http://127.0.0.1:18090/?debug=1`(或者直接查看右侧
面板——调试面板始终可见)。
3. 在浏览器控制台中:
```js
Expand Down Expand Up @@ -187,9 +187,17 @@ mcode 侧的会话存储是 SQLite:
2. 增大 N。(当前值:见 script 标签上方的注释。)

### 修改默认端口
```powershell
$env:PORT = 8080
18090 只是默认值,不是被钉住的值:它被占用时服务器会往后找下一个空闲
端口,并打印实际绑定的端口。设置 `PORT`(或给 `mcode-web` 传 `--port`)
则是把端口钉住 —— 被占用的钉住端口会以 EADDRINUSE 退出而不是自动后移,
这样 docker 端口发布和健康检查仍然按配置值寻址。

```bash
# 默认端口:18090,被占用时换下一个空闲端口
node server.js

# 钉在 7891 —— 不会移动
PORT=7891 node server.js
```

### 启用局域网共享
Expand All @@ -215,7 +223,7 @@ webui 会在下一次发送时启动一个新的子进程。
`/api/settings` 端点在设计上豁免局域网守卫。
从局域网上的任何机器,即使 `lanBroadcast: false`:
```bash
curl -X POST http://192.168.1.50:8080/api/settings \
curl -X POST http://192.168.1.50:18090/api/settings \
-H 'Content-Type: application/json' \
-d '{"lanBroadcast": true}'
```
Expand Down
Loading