@dhzh/foundry 0.2.1 → 1.0.0-beta.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/README.md +41 -102
  2. package/package.json +43 -30
  3. package/dist/index.js +0 -1
package/README.md CHANGED
@@ -1,135 +1,74 @@
1
1
  # Foundry
2
2
 
3
- Foundry is an Electron desktop application for managing local AI agent Runtime configurations. The current release focuses on custom Provider management for Codex and Claude Code: define connection and model settings once, preview the resulting configuration changes, and apply them to the corresponding local Runtime.
3
+ Foundry provides a CLI-managed local web interface backed by a loopback-only Hono server. It is distributed as an ESM-only Node.js package.
4
4
 
5
- > Foundry is in an early stage. Provider and Runtime management are functional; the Skills area is currently a placeholder, and broader tools, agents, and workflows remain future work.
5
+ ## Usage
6
6
 
7
- Tagged builds are published on the [GitHub Releases](https://github.com/tinywaves/foundry/releases) page. The current automated release workflow produces an unsigned, unnotarized macOS Universal DMG, so macOS may require explicit approval before opening it.
7
+ Start the local web interface with:
8
8
 
9
- ## Current Features
10
-
11
- - Manage separate custom Providers for Codex and Claude Code.
12
- - Store Provider names, Base URLs, API keys, model mappings, remarks, websites, and optional avatars locally.
13
- - Test Provider connectivity before or after saving.
14
- - View Provider health and Runtime status from the dashboard.
15
- - Select a Provider or restore Official Default settings for each Runtime.
16
- - Preview every managed configuration field before writing to disk, with secrets redacted by default.
17
- - Preserve settings outside Foundry's managed fields and keep a backup of the previous configuration.
18
- - Automatically reapply an in-use Provider after a Runtime-effective edit.
19
- - Show persistent restart guidance after every successful configuration write.
20
- - On macOS, optionally restart an already-running ChatGPT desktop app so its hosted Codex experience reloads the configuration.
21
-
22
- ## Supported Runtimes
23
-
24
- | Runtime | Configuration file | Managed configuration | Reload behavior |
25
- | --- | --- | --- | --- |
26
- | Codex | `~/.codex/config.toml` | Model selection and a Foundry-managed `model_providers` entry | Foundry can gracefully restart an already-running ChatGPT desktop app on macOS. Existing Codex CLI sessions must be restarted manually. |
27
- | Claude Code | `~/.claude/settings.json` | Anthropic endpoint, token, model-role mappings, fallback model, and subagent model under `env` | Existing Claude Code CLI sessions must be restarted manually. |
28
-
29
- Restoring Official Default removes the Runtime selection overrides managed by Foundry. It does not delete saved Provider records or unrelated Runtime settings.
30
-
31
- ## Typical Workflow
32
-
33
- 1. Open **Agent Runtime > Providers** and add a Provider for Codex or Claude Code.
34
- 2. Enter the endpoint, API key, and Runtime-specific model settings.
35
- 3. Run **Test Connection** to verify that the endpoint responds successfully.
36
- 4. Open **Agent Runtime > Runtimes**, select the desired Provider, and choose **Apply**.
37
- 5. Review the exact field-level changes in the preview dialog and confirm the write.
38
- 6. Follow the result dialog to restart the affected desktop application or CLI session.
39
-
40
- When an in-use Provider is edited, Foundry saves the Provider first and reapplies it only when a Runtime-effective field changed. If the reapply fails, the saved Provider remains available and the dialog offers the existing Apply retry flow.
41
-
42
- ## Connection Tests
43
-
44
- Provider tests run in the Electron main process with a 15-second timeout and do not follow redirects.
45
-
46
- - Codex sends `GET <base-url>/models` and uses `Authorization: Bearer <api-key>` when a key is configured.
47
- - Claude Code sends `GET <base-url>/v1/models`, or `GET <base-url>/models` when the Base URL already ends in `/v1`. It sends `anthropic-version: 2023-06-01` and uses `x-api-key` when configured.
48
- - Any `2xx` response passes. Network, TLS, timeout, redirect, and non-`2xx` outcomes are recorded as sanitized connection failures.
49
-
50
- ## Configuration Safety
51
-
52
- Foundry treats configuration writes as a previewed and recoverable operation:
53
-
54
- - Existing TOML or JSON is parsed before any change is offered.
55
- - Only the documented Runtime fields are modified; unrelated settings are preserved.
56
- - The proposed output is generated, parsed again, and validated before replacing the active file.
57
- - Writes use same-directory temporary files with restrictive `0600` permissions.
58
- - The latest previous file content is stored beside the Runtime configuration as `<filename>.foundry-backup`.
59
- - If the configuration is written but Foundry cannot record the new application state, it restores the previous file content.
60
- - Concurrent writes to the same Runtime are rejected.
61
-
62
- Provider records, including API keys and avatars, are stored in a local SQLite database named `foundry.sqlite` under Electron's platform-specific `userData` directory. Applied API keys are also written to the target Runtime configuration because the Runtime requires them. Treat both the Foundry user-data directory and Runtime configuration files as sensitive local data.
63
-
64
- ## ChatGPT Restart Behavior
65
-
66
- Automatic restart is intentionally narrow and available only on macOS:
9
+ ```bash
10
+ pnpm dlx @dhzh/foundry ui
11
+ ```
67
12
 
68
- - ChatGPT is identified by the fixed bundle identifier `com.openai.codex`.
69
- - Foundry offers restart only after confirming that ChatGPT is already running.
70
- - Restart requests a normal application termination and never force-quits ChatGPT.
71
- - Foundry waits up to 15 seconds for exit, reopens the same bundle, and waits up to another 15 seconds to confirm startup.
72
- - If detection, quit, or reopen fails, the applied configuration remains intact and Foundry shows manual guidance without an automatic retry action.
73
- - Foundry never launches ChatGPT when it was not already running and never starts or terminates Codex CLI or Claude Code CLI processes.
13
+ The server listens on `http://127.0.0.1:54321` and opens the interface in the default browser. Use a different port or keep the browser closed when needed:
74
14
 
75
- Restarting ChatGPT affects the entire desktop application and may interrupt work in its Chat, Work, and Codex views.
15
+ ```bash
16
+ pnpm dlx @dhzh/foundry ui --port 61234 --no-open
17
+ ```
76
18
 
77
19
  ## Development
78
20
 
79
- ### Prerequisites
80
-
81
- - Node.js `24.18.0`
82
- - pnpm `11.9.0`
21
+ The repository is a pnpm workspace containing the published server and CLI package, a private React app, and a private API contract package.
83
22
 
84
- ### Install and Run
23
+ Install dependencies from the repository root:
85
24
 
86
25
  ```bash
87
26
  pnpm install
88
- pnpm dev
89
27
  ```
90
28
 
91
- ### Verify Changes
29
+ Start the Hono server:
92
30
 
93
31
  ```bash
94
- pnpm test
95
- pnpm typecheck
96
- pnpm lint
97
- pnpm build
32
+ pnpm dev:server
98
33
  ```
99
34
 
100
- ### Package the Application
35
+ In another terminal, start the React app at [http://localhost:3000](http://localhost:3000):
101
36
 
102
37
  ```bash
103
- pnpm build:mac
104
- pnpm build:win
105
- pnpm build:linux
38
+ pnpm dev:app
106
39
  ```
107
40
 
108
- `pnpm build:unpack` creates an unpacked application directory for local packaging checks. Pushing a `v*` tag runs the release workflow, builds a macOS Universal DMG, and attaches it to a GitHub Release. Automated release artifacts are not currently signed or notarized.
41
+ Rsbuild proxies `/api` requests to the Hono server at `http://127.0.0.1:54321`.
109
42
 
110
- ## Architecture
43
+ ## Health Endpoint
111
44
 
112
- ```text
113
- src/main/ Electron lifecycle, SQLite storage, configuration writes,
114
- connection tests, and native ChatGPT control
115
- src/preload/ Narrow contextBridge APIs for Provider and Runtime operations
116
- src/renderer/ React UI, page workflows, and renderer-side response validation
117
- src/shared/ Typed Provider and Runtime contracts shared across processes
118
- resources/ Runtime packaging assets
119
- build/ electron-builder resources and macOS entitlements
45
+ `GET /api/health` returns HTTP 200 with the shared response envelope:
46
+
47
+ ```json
48
+ {
49
+ "status": "SUCCESS",
50
+ "data": true,
51
+ "message": "Service is healthy."
52
+ }
120
53
  ```
121
54
 
122
- The renderer does not receive arbitrary filesystem, process, shell, or IPC access. Native operations remain in the main process and are exposed through purpose-specific preload methods with constrained inputs and validated responses.
55
+ Unexpected query parameters are rejected with HTTP 400.
56
+
57
+ ## Workspace Layout
123
58
 
124
- ## Technology
59
+ - `src/cli/` - CLI entry point and the `foundry ui` command.
60
+ - `src/server/` - Hono server, health handler, static app serving, and lifecycle management.
61
+ - `app/` - React and Rsbuild local web interface.
62
+ - `packages/api-contract/` - Shared response constants and TypeScript types.
63
+ - `test/` - Vitest test suite.
125
64
 
126
- - Electron and `electron-vite`
127
- - React 19 and TypeScript
128
- - Astryx Design System and StyleX
129
- - TanStack Query
130
- - SQLite through `better-sqlite3`
131
- - Vitest and ESLint
132
- - `electron-builder`
65
+ ## Verification
66
+
67
+ ```bash
68
+ pnpm test
69
+ pnpm --filter @dhzh/foundry-app typecheck
70
+ pnpm build
71
+ ```
133
72
 
134
73
  ## License
135
74
 
package/package.json CHANGED
@@ -1,11 +1,11 @@
1
1
  {
2
2
  "name": "@dhzh/foundry",
3
3
  "type": "module",
4
- "version": "0.2.1",
4
+ "version": "1.0.0-beta.1",
5
5
  "devEngines": {
6
6
  "packageManager": {
7
7
  "name": "pnpm",
8
- "version": "^11.9.0",
8
+ "version": "^11.22.0",
9
9
  "onFail": "download"
10
10
  },
11
11
  "runtime": {
@@ -23,9 +23,19 @@
23
23
  "homepage": "https://github.com/tinywaves/foundry",
24
24
  "keywords": [
25
25
  "agent",
26
- "cli",
27
26
  "ai"
28
27
  ],
28
+ "exports": {
29
+ ".": {
30
+ "types": "./dist/index.d.mts",
31
+ "import": "./dist/index.mjs"
32
+ }
33
+ },
34
+ "main": "./dist/index.mjs",
35
+ "types": "./dist/index.d.mts",
36
+ "bin": {
37
+ "foundry": "./dist/cli.mjs"
38
+ },
29
39
  "files": [
30
40
  "dist"
31
41
  ],
@@ -35,45 +45,48 @@
35
45
  },
36
46
  "sideEffects": false,
37
47
  "devDependencies": {
38
- "@astryxdesign/cli": "^0.1.7",
39
- "@commitlint/cli": "^21.0.2",
40
- "@commitlint/config-conventional": "^21.0.2",
41
- "@dhzh/eslint-config": "^2.1.1",
42
- "@types/node": "^26.1.0",
43
- "@vitest/coverage-v8": "^4.1.9",
44
- "bumpp": "^11.1.0",
45
- "changelogithub": "^14.0.0",
46
- "eslint": "^10.5.0",
48
+ "@commitlint/cli": "^21.2.2",
49
+ "@commitlint/config-conventional": "^21.2.2",
50
+ "@dhzh/eslint-config": "^2.4.3",
51
+ "@dhzh/foundry-api-contract": "0.0.0",
52
+ "@types/node": "^26.2.0",
53
+ "@vitest/coverage-v8": "^4.1.11",
54
+ "bumpp": "^12.2.1",
55
+ "changelogithub": "^15.0.4",
56
+ "eslint": "^10.9.0",
47
57
  "husky": "^9.1.7",
48
- "lint-staged": "^17.0.7",
49
- "tsdown": "^0.22.2",
50
- "tsx": "^4.22.4",
58
+ "lint-staged": "^17.3.0",
59
+ "taze": "^21.1.0",
60
+ "tsdown": "^0.22.14",
61
+ "tsx": "^4.23.12",
51
62
  "typescript": "^6.0.3",
52
- "vitest": "^4.1.9",
63
+ "vitest": "^4.1.11",
53
64
  "node": "runtime:^24.18.0"
54
65
  },
55
66
  "dependencies": {
56
- "@hono/node-server": "^2.0.8",
67
+ "@hono/node-server": "^2.1.1",
57
68
  "@hono/zod-validator": "^0.9.0",
58
- "cac": "^7.0.0",
59
- "cli-table3": "^0.6.5",
60
- "consola": "^3.4.2",
61
- "hono": "^4.12.27",
62
- "terminal-link": "^5.0.0",
63
- "zod": "^4.4.3"
69
+ "citty": "^0.2.2",
70
+ "hono": "^4.13.5",
71
+ "open": "^11.0.2",
72
+ "zod": "^4.5.4"
64
73
  },
65
74
  "scripts": {
66
- "build": "pnpm run build:cli && pnpm run build:web",
67
- "build:cli": "tsdown",
68
- "build:web": "pnpm run --filter web build",
69
- "dev:cli": "tsx watch --clear-screen=true src/cli/index.ts",
70
- "dev:web": "pnpm run --filter web dev",
75
+ "build": "pnpm run build:server && pnpm run build:app",
76
+ "build:app": "pnpm --filter @dhzh/foundry-app build",
77
+ "build:server": "tsdown",
78
+ "dev:app": "pnpm --filter @dhzh/foundry-app dev",
79
+ "dev:cli": "tsx src/cli/index.ts ui",
80
+ "dev:server": "tsx watch --clear-screen=false src/server/dev.ts",
71
81
  "lint": "eslint",
72
- "lint-fix": "eslint --fix .",
82
+ "lint-fix": "eslint --fix",
73
83
  "release": "bumpp",
74
84
  "release:publish": "pnpm release && pnpm publish --access public",
75
85
  "test": "vitest run",
76
86
  "test:coverage": "pnpm run test --coverage",
77
- "test:dev": "vitest"
87
+ "test:dev": "vitest",
88
+ "typecheck": "tsc --noEmit",
89
+ "version:update": "taze major",
90
+ "version:update:w": "taze major -w"
78
91
  }
79
92
  }
package/dist/index.js DELETED
@@ -1 +0,0 @@
1
- export default function Test() {}