{"id":50699620,"url":"https://github.com/ralscha/codemode","last_synced_at":"2026-06-09T08:32:50.682Z","repository":{"id":361623796,"uuid":"1224830242","full_name":"ralscha/codemode","owner":"ralscha","description":"Tools for implementing codemode in Go","archived":false,"fork":false,"pushed_at":"2026-05-31T13:51:23.000Z","size":34,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-05-31T15:22:26.264Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/ralscha.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-04-29T17:11:02.000Z","updated_at":"2026-05-31T13:51:27.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/ralscha/codemode","commit_stats":null,"previous_names":["ralscha/codemode"],"tags_count":null,"template":false,"template_full_name":null,"purl":"pkg:github/ralscha/codemode","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ralscha%2Fcodemode","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ralscha%2Fcodemode/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ralscha%2Fcodemode/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ralscha%2Fcodemode/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ralscha","download_url":"https://codeload.github.com/ralscha/codemode/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ralscha%2Fcodemode/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34098932,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-09T02:00:06.510Z","response_time":63,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2026-06-09T08:32:48.444Z","updated_at":"2026-06-09T08:32:50.674Z","avatar_url":"https://github.com/ralscha.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# codemode\n\nSearch tool definitions, generate a TypeScript API surface for them, and execute\nsmall JavaScript programs against caller-provided tool callbacks.\n\n```bash\ngo get github.com/ralscha/codemode\n```\n\nThe root package depends directly on [QuickJS](https://gitlab.com/cznic/quickjs) and the [MCP SDK](https://github.com/modelcontextprotocol/go-sdk).\n\n## Tool Search\n\n`NewToolIndex(...)` builds a searchable index over many tool definitions. The\nindex accepts either `[]codemode.ToolDefinition` or `[]mcp.Tool` and searches\nby name, description, input schema, and output schema.\n\n```go\ndefinitions := []codemode.ToolDefinition{\n    codemode.NewToolDefinition(\"search-products\").\n        WithDescription(\"Search the product catalog\").\n        WithInputSchema(codemode.NewObjectSchema().\n            WithProperty(\"query\", codemode.NewStringSchema().WithDescription(\"Search query\")).\n            WithRequired(\"query\")).\n        WithOutputSchema(codemode.NewObjectSchema().\n            WithProperty(\"items\", codemode.NewArraySchema(codemode.NewObjectSchema().\n                WithProperty(\"id\", codemode.NewStringSchema().WithDescription(\"Product identifier\")).\n                WithProperty(\"title\", codemode.NewStringSchema().WithDescription(\"Product title\")).\n                WithRequired(\"id\", \"title\")).WithDescription(\"Matched items\")).\n            WithRequired(\"items\")).\n        Build(),\n}\n\nindex, err := codemode.NewToolIndex(definitions)\nif err != nil {\n    return err\n}\n\nresults := index.Query(\"matched product items\", codemode.WithToolSearchLimit(3))\nfor _, result := range results {\n    fmt.Println(result.Definition.Name, result.Score, result.Matches)\n}\n```\n\n`Query(...)` combines BM25-style lexical ranking with exact, normalized, and\nfuzzy name boosts. Schema property names and descriptions carry more weight\nthan raw schema JSON, so queries like `matched product items` can find a tool\nfrom its output shape.\n\n`QueryRegex(...)` provides deterministic filtering:\n\n```go\nresults, err := index.QueryRegex(`github.*issues`)\n```\n\n## Generate API\n\n`GenerateFromDefinitions(...)` and `GenerateFromMCPTools(...)` generate\nTypeScript API declarations. The output uses sanitized method names,\ngenerated input and output types, and JSDoc from tool and schema descriptions.\n\n```go\napi, err := codemode.GenerateFromDefinitions(definitions)\nif err != nil {\n    return err\n}\nfmt.Println(api)\n```\n\nThe generator produces declarations like:\n\n```ts\ndeclare const tools : {\n /**\n  * Create a new project\n  * @param name - Project name\n  * @returns id - Project identifier\n  */\n create_project: (input: { name: string; }) =\u003e { id: string; name: string; };\n}\n```\n\nSupported inputs:\n\n- `GenerateFromDefinitions(...)`: normalized `ToolDefinition` values\n- `GenerateFromMCPTools(...)`: MCP SDK `mcp.Tool` values\n\n`ToolDefinition` supports both input and output schemas. The builder APIs keep\nnested JSON schema values readable:\n\n```go\ndefinition := codemode.NewToolDefinition(\"create-project\").\n    WithDescription(\"Create a new project\").\n    WithInputSchema(codemode.NewObjectSchema().\n        WithProperty(\"name\", codemode.NewStringSchema().WithDescription(\"Project name\")).\n        WithRequired(\"name\")).\n    WithOutputSchema(codemode.NewObjectSchema().\n        WithProperty(\"id\", codemode.NewStringSchema().WithDescription(\"Project identifier\")).\n        WithProperty(\"name\", codemode.NewStringSchema().WithDescription(\"Project name\")).\n        WithRequired(\"id\", \"name\")).\n    Build()\n```\n\n`GenerateFromMCPTools(...)` works directly with tool definitions from an MCP\nserver:\n\n```go\napi, err := codemode.GenerateFromMCPTools(mcpTools, codemode.WithNamespace(\"githubTools\"))\n```\n\nBy default the output starts with `declare const tools : { ... }`.\n`WithNamespace(...)` changes the object name:\n\n```go\ngithubAPI, _ := codemode.GenerateFromMCPTools(githubTools, codemode.WithNamespace(\"githubTools\"))\nstripeAPI, _ := codemode.GenerateFromMCPTools(stripeTools, codemode.WithNamespace(\"stripeTools\"))\n```\n\n## Execute\n\n`Execute(...)` runs JavaScript returned by an LLM. The code executes inside a\nQuickJS VM with a memory limit and timeout. The caller provides the callback\nnamespaces, so execution stays independent of HTTP clients, databases, or any\nother tool runtime.\n\nExecution is synchronous. Tool callbacks are exposed as regular JavaScript\nfunctions, so generated code should not use `await`, `Promise.all(...)`, dynamic\n`import(...)`, or other async-only patterns.\n\nBefore evaluation, code is normalized for common LLM output shapes:\n\n- markdown code fences are stripped\n- bare expressions and final expressions are returned automatically\n- sync arrow functions and simple `async () =\u003e { ... }` wrappers are unwrapped\n\n```go\ntype WeatherInput struct {\n    City string `json:\"city\"`\n}\n\ntype WeatherOutput struct {\n    City        string `json:\"city\"`\n    Temperature string `json:\"temperature\"`\n}\n\nresult, err := codemode.Execute(ctx, `\nconst weather = tools.get_weather({ city: \"Zurich\" });\nreturn { text: \"Weather in \" + weather.city + \": \" + weather.temperature };\n`, []codemode.ToolCallbackNamespace{\n    {\n        Callbacks: []codemode.ToolCallbackDefinition{\n            codemode.NewToolCallback(\"get-weather\", func(ctx context.Context, input WeatherInput) (WeatherOutput, error) {\n                return WeatherOutput{City: input.City, Temperature: \"12 C\"}, nil\n            }),\n        },\n    },\n})\nif err != nil {\n    return err\n}\nfmt.Println(result.Value)\n```\n\nSandboxed code can write diagnostic output with `console.log`, `console.warn`,\nand `console.error`. Messages are captured in `ExecuteResult.Logs`; warnings and\nerrors are prefixed with `[warn]` and `[error]`. Logs captured before a\nJavaScript error are still returned with the result value.\n\nThe JavaScript API uses the same sanitized names as the generated declarations.\nFor example, `get-weather` becomes `tools.get_weather(...)`.\n`WithNamespace(...)` changes the object name for both generation and execution.\n\n```go\napi, _ := codemode.GenerateFromDefinitions(definitions, codemode.WithNamespace(\"sdk\"))\nresult, _ := codemode.Execute(ctx, `return sdk.search_docs({ query: \"install\" });`, []codemode.ToolCallbackNamespace{\n    {Callbacks: callbacks},\n}, codemode.WithNamespace(\"sdk\"))\n```\n\nMultiple namespace entries expose helper objects from multiple generated\nnamespaces to the same JavaScript program.\n\n```go\nresult, err := codemode.Execute(ctx, `\nconst repos = githubTools.list_repos({ owner: \"ralscha\" }).items;\nconst customers = stripeTools.list_customers({ limit: 2 }).items;\nreturn { repos: repos.length, customers: customers.length };\n`, []codemode.ToolCallbackNamespace{\n    {Namespace: \"githubTools\", Callbacks: githubCallbacks},\n    {Namespace: \"stripeTools\", Callbacks: stripeCallbacks},\n})\n```\n\nExecution options:\n\n- `WithEvalTimeout(...)`: limit JavaScript runtime, default `10s`\n- `WithMemoryLimit(...)`: limit QuickJS memory, default `32 MiB`\n\n## License\n\nMIT License. See [LICENSE](LICENSE) for details.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fralscha%2Fcodemode","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fralscha%2Fcodemode","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fralscha%2Fcodemode/lists"}