{"id":51884763,"url":"https://github.com/convertigo/c8oprj-lib-flow-mcp","last_synced_at":"2026-07-25T19:01:28.711Z","repository":{"id":372247710,"uuid":"1265117989","full_name":"convertigo/c8oprj-lib-flow-mcp","owner":"convertigo","description":null,"archived":false,"fork":false,"pushed_at":"2026-07-19T23:21:39.000Z","size":597,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"spike-flowscript","last_synced_at":"2026-07-20T00:23:42.871Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/convertigo.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"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":"AGENTS.md","dco":null,"cla":null}},"created_at":"2026-06-10T13:33:58.000Z","updated_at":"2026-07-19T23:21:43.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/convertigo/c8oprj-lib-flow-mcp","commit_stats":null,"previous_names":["convertigo/c8oprj-lib-flow-mcp"],"tags_count":null,"template":false,"template_full_name":null,"purl":"pkg:github/convertigo/c8oprj-lib-flow-mcp","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/convertigo%2Fc8oprj-lib-flow-mcp","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/convertigo%2Fc8oprj-lib-flow-mcp/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/convertigo%2Fc8oprj-lib-flow-mcp/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/convertigo%2Fc8oprj-lib-flow-mcp/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/convertigo","download_url":"https://codeload.github.com/convertigo/c8oprj-lib-flow-mcp/tar.gz/refs/heads/spike-flowscript","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/convertigo%2Fc8oprj-lib-flow-mcp/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":35889141,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-07-20T02:08:10.276Z","status":"online","status_checked_at":"2026-07-25T02:00:06.922Z","response_time":64,"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-07-25T19:01:27.976Z","updated_at":"2026-07-25T19:01:28.694Z","avatar_url":"https://github.com/convertigo.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# lib_flow_mcp\n\nFlow-native MCP server for Convertigo Flow authoring.\n\nThis project intentionally keeps MCP tooling outside `lib_flow_engine`.\n`lib_flow_engine` remains the standard runtime vocabulary; this library owns the\nMCP surface and any blocks specific to Flow authoring automation.\n\nHTTP entry point:\n\n```text\nhttp://localhost:18080/convertigo/api/flow-mcp\n```\n\nThe UrlMapper path is `/flow-mcp`; the trailing-slash variant `/flow-mcp/` is\nalso mapped to the same requestable. The legacy Convertigo MCP project keeps\n`/mcp`.\n\nRuntime shape:\n\n```text\nlib_flow_mcp.McpServer\n  -\u003e libs/flows/McpServer.flow.yaml\n  -\u003e high-level MCP graph blocks (mcp.batch, mcp.handle, mcp.tools.call)\n  -\u003e visible tools/call families (inspect, source, author, runtime)\n  -\u003e private mcp.* blocks\n  -\u003e reusable core/project blocks via ctx.callBlock(...)\n  -\u003e explicit low-level libraries in libs/flow/lib/*.js, declared with uses\n  -\u003e lib_flow_engine.Engine\n```\n\nThe flow graph owns the visible protocol routing. Reusable protocol branches\nthat deserve a palette/catalog item are composite graph blocks in\n`libs/flow/blocks/*.block.js`; for example `mcp.handle` routes one JSON-RPC\nrequest, and `mcp.tools.call` is implemented with `mcp.tool.identify` and one\nbranch per tool family. Private native `mcp.*` blocks keep the low-level\nJSON-RPC/Convertigo glue small. When reusable behavior has a clear contract,\nexpose it as a block and call it with `ctx.callBlock(...)`; keep\n`libs/flow/lib/mcp.js` only for local algorithmic helpers that would add noise\nto the Flow catalog, and declare that dependency with `uses: [mcp]`.\n\nScope naming convention for new Flow sources:\n\n- `input.*` is the data received by the executable Flow or block implementation.\n- `local.*` is the private working scope of the current execution.\n- `config.*`, `current`, `result` keep their usual meanings.\n- `props.*` and `flow.*` are not expression scopes. JS hooks/raw implementations\n  can inspect the raw node with `ctx.props(node)`.\n\nFor simple MCP tools, prefer this graph shape:\n\n```yaml\nnodes:\n  - id: run\n    block: mcp.tool.run\n    request: input.request\n    target: resource.search\n    out: local.response\n  - id: done\n    block: return\n    value: \"{{ local.response }}\"\n```\n\n`mcp.tool.run` prepares MCP arguments, resolves the target project, calls the\ntarget block with `ctx.callBlock(...)`, and wraps either the result or the error\nas a JSON-RPC tools/call response.\n\nThe simple read/test/introspection tools now use this shape and delegate to\ncore capability blocks such as `flow.list`, `flow.get`, `flow.run`,\n`flow.test`, `flow.tree`, `flow.context`, `flow.outputSchema`, `flow.apply`,\n`resource.*`, `block.*` and `type.*`. Keep JavaScript wrappers only when the\ntool still owns MCP-specific behavior such as workspace search or Studio DBO\nregistration after writing a Flow.\n\nWhen adding a new operation, ask whether the underlying behavior is:\n\n- general Flow runtime behavior: add it to `lib_flow_engine`;\n- MCP authoring behavior: keep it here;\n- project-specific glue: keep it in the target project, preferably private.\n\nDefault authoring cycle for a blank agent context:\n\n```text\nresources/list\nresources/read flow://guide/start\ntools/list\nflow-search to find flows, nodes, catalog entries and schemas; multi-word queries match unordered tokens\nflow-code-rg / flow-code-get for FlowScript source\nflow-tree / flow-get only for model-conversion debugging\nflow-context when choosing paths or expressions\nflow-output-schema when downstream nodes need the result shape\nflow-node-output-schema when one HTTP/exec/parser producer needs schema inspection, adoption or removal\nflow-schema-reset only for broader stale learned-schema cleanup\nflow-code-set for broad Flow edits; it writes the FlowScript working copy\nflow-code-patch for revision-checked maintenance edits on that working copy\nflow-code-check / flow-code-run, then flow-code-promote once behavior is clean\nflow-catalog only when search/examples are insufficient; it is summary by default\nflow-block-code-rg / flow-block-code-get / flow-block-code-patch for project-local blocks\nflow-block-code-set only when reusable vocabulary is needed\nflow-block-create / flow-block-duplicate / flow-block-edit are compatibility facades that still write canonical .block.js\nflow-type-create only for project-local property type definitions\nflow-resource-search / flow-resource-get / flow-resource-patch for maintenance patches on project JS/HTML/CSS resources and Flow libraries\n```\n\nThe default path remains catalog-first and sidecar-first. Custom blocks are\nproject vocabulary, not automatic core changes.\n\nProject-local blocks use a canonical `*.block.js` source containing `_meta`\nplus either one FlowScript function or one Rhino IIFE. Use Rhino blocks only for\nJVM/Java integration code or low-level primitives. Rhino code may use Java classes\nthrough `Packages`, but not Node.js APIs such as `require`, npm modules or\nbrowser globals. Keep the Rhino IIFE to `run(ctx, node)` plus local helpers.\nPut shared helper dependencies in `uses`; optional dynamic\n`displayName(node)` / `analyze(ctx, node)` hooks stay separate from runtime code.\n\nExecutable Flows may declare request variables and reusable test inputs with a\ntop-level FlowScript contract:\n\n```javascript\nconst _flow = {\n  inputs: {\n    city: { type: \"string\", description: \"City name.\", default: \"Paris\" }\n  },\n  tests: {\n    checkParis: { input: { city: \"Paris\" } }\n  }\n}\n```\n\n`flow-code-*` tools expose this as `inputDefinitions`, `inputVariables`, and\n`testCases`. Explicit `_flow.inputs` are synchronized to Convertigo request\nvariables so Studio, SDK callers and generated test cases see the same contract.\nWithout `_flow.inputs`, inputs are only inferred from `input.foo` reads and\nauthoring tools report a warning asking for the missing declarations.\n\nDo not use a Rhino block as a shortcut for a whole backend feature. Keep HTTP\nfetches in `http.get`/`http.request`, Convertigo calls in `requestable.call`,\narray transforms in `list.*`, JSON shaping in `json.*`, and response assignment\nin FlowScript. If only parsing or one Java bridge is missing, create that small\nprimitive and compose it visibly from the Flow.\n\nMost tools accept either:\n\n- `project`: Convertigo project name, resolved by the live engine;\n- `projectDir`: direct filesystem path, mainly for standalone tests.\n\nWhen omitted, tools operate on `lib_flow_mcp` itself. Agents should pass\n`project` for application work, for example `AAAProject`.\n\nMutation tools accept semantic node targets first. Prefer this shape after\n`flow-search` returns a `nodeId`:\n\n```json\n{\n  \"name\": \"WeatherAlert\",\n  \"mutation\": {\n    \"op\": \"replace\",\n    \"nodeId\": \"setMessage\",\n    \"property\": \"value\",\n    \"value\": \"Done\"\n  }\n}\n```\n\nUse `afterNodeId`, `beforeNodeId` or `parentNodeId + slot` to insert nodes\nwithout hard-coding array indexes:\n\n```json\n{\n  \"name\": \"WeatherAlert\",\n  \"mutation\": {\n    \"op\": \"insert\",\n    \"afterNodeId\": \"setMessage\",\n    \"value\": {\n      \"id\": \"logDone\",\n      \"block\": \"log\",\n      \"message\": \"Done\"\n    }\n  }\n}\n```\n\nLow-level mutations can still use the same JSON Pointer syntax as the Flow\nvirtual tree:\n\n```json\n{\n  \"name\": \"WeatherAlert\",\n  \"mutation\": {\n    \"op\": \"insert\",\n    \"path\": \"/nodes\",\n    \"index\": \"end\",\n    \"value\": {\n      \"id\": \"setMessage\",\n      \"block\": \"set\",\n      \"path\": \"result.message\",\n      \"value\": \"Done\"\n    }\n  }\n}\n```\n\nUse `flow-apply` to preview the updated YAML source. Use `flow-edit` to apply\nthe same mutation to a named project Flow sidecar.\n\nFor a broader edit, use the tree-like model round trip instead of inventing a\nnew command:\n\n1. `flow-get` returns `source` and `definition`.\n2. Modify `definition` as a JSON object.\n3. Send it back with `flow-set` using the same `definition` property.\n\n`flow-run`, `flow-test`, `flow-tree`, `flow-apply`, `flow-output-schema` and\n`flow-block-test` also accept this `definition` shape. This is the preferred\nKISS alternative to multiplying CRUD aliases such as create/update/replace.\n\n`flow-catalog` intentionally returns summary block/type contracts by default.\nAsk for `detail:\"compact\"` when property docs are useful. Ask for\n`detail:\"full\"` only when icon paths, type usage lists or full descriptor\nresources are useful.\n\nWhen `flow-set` or `flow-edit` receives a live `project`, it also registers the\nnamed sidecar as a minimal Flow DBO by default, saves the project, and refreshes\nthe Studio tree when Studio is available. Pass `register:false`, `autoSave:false`\nor `refresh:false` only for deliberate tooling cases. With `projectDir` only,\nregistration is skipped and the tool stays a pure filesystem sidecar writer.\n\nThe common node wrappers are preferred when they fit:\n\n- `flow-node-add`: add a node near another node or inside a parent slot.\n- `flow-node-edit`: replace one property or merge several properties.\n- `flow-node-move`: move a node by `nodeId`.\n- `flow-node-delete`: delete a node by `nodeId`.\n- `flow-node-duplicate`: duplicate a node and optionally patch the new copy.\n\n`flow-node-add` requires a stable `id`. `flow-node-duplicate` requires `newId`\nor `properties.id` to avoid creating duplicate ids.\n\nBlock authoring is intentionally explicit:\n\n- `flow-block-get` reads any visible block source.\n- `flow-block-code-set` writes canonical project-local `.block.js` source.\n- `flow-block-create` is a compatibility facade that also writes `.block.js`.\n- `flow-block-duplicate` copies a core/shared/project block to a new\n  project-local name.\n- `flow-block-edit` replaces the source of an existing project-local block.\n\nCore and shared blocks are read-only through this MCP surface. Duplicate them\nfirst when an agent needs a custom variant.\n\n## FlowScript spike tools\n\nOn the `spike-flowscript` branch, the MCP also exposes an experimental source\nview for agents:\n\n```text\nflow-code-get\nflow-code-set\nflow-code-patch\nflow-code-rg\n\nflow-source-get\nflow-source-validate\nflow-source-patch\n```\n\nPrefer `flow-code-*` for normal agent work:\n\n- `flow-code-get({qname})` returns only FlowScript `code` plus `revision`.\n- `flow-code-set({qname, revision?, code})` writes and validates the FlowScript working copy.\n- `flow-code-patch({qname, revision, codepatch|code})` applies a revision-checked edit to the working copy.\n- `flow-code-run({qname, input?})` runs the current working copy without resending code.\n- `flow-code-promote({qname, revision?})` saves the working copy to the official Flow.\n- `flow-code-rg({qname?, pattern})` returns small FlowScript extracts.\n\nThe engine parses and validates the FlowScript, returns line-based diagnostics\nwhen a block/property is invalid, and writes the canonical FlowScript sidecar\nafter validation succeeds. Legacy YAML sidecars are only fallback inputs during\nthe spike migration.\n\nKeep `flow-source-*` for compiler/debug work where canonical definitions, YAML\nor full analysis are intentionally needed.\n\nThis is a research path to measure whether agents transpose code instincts more\nefficiently than direct block/tree MCP editing.\n\nFor iterative maintenance, prefer patching the project-local resource instead\nof replacing a whole source file:\n\n```text\nflow-resource-search -\u003e flow-resource-get -\u003e flow-resource-patch(baseHash, unified diff)\n```\n\nThe patch API is limited to Flow resources such as\n`libs/flow/blocks/**/*.block.js`, `libs/flow/fragments/**/*.fragment.yaml`,\n`libs/flow/lib/**/*.js`, `libs/flow/types/**/*.{type.yaml,js}` and\n`libs/flow/types/editors/**/*.{html,css,js}`. It validates block/type/library\nresources and parses Flow/fragment YAML by default.\nUnified diff line numbers may be approximate when the surrounding context is\nunique.\n\nSearch is the MCP equivalent of `rg` for Flow authoring:\n\n```json\n{\n  \"project\": \"AAAProject\",\n  \"query\": \"temperature\",\n  \"kinds\": [\"node\"],\n  \"context\": 1,\n  \"limit\": 20\n}\n```\n\nEach node match returns `flowQName`, `nodeId` and a canonical JSON Pointer\n`path`. Use `nodeId` for semantic edits and `path` for low-level mutations.\nPass `doc:false,hints:false` once the agent has learned the tool contract.\n\nMCP responses are sanitized before they are sent to agents: internal `__flow*`\nfields are removed, empty metadata fields such as `mode:\"\"` are omitted, and\nfilesystem paths are shortened to project-relative paths or `engine:...`\nreferences. Studio-only icon/resource paths may still exist in internal Flow\ntree data, but they should not leak through the MCP JSON-RPC result payload.\n\nOptional JSONL tracing can write one line per MCP request and response. Enable\nit with the Convertigo symbol:\n\n```text\nflow.mcp.traceJsonl=true\nflow.mcp.traceJsonl=/path/to/flow-mcp.jsonl\nflow.mcp.traceJsonl.maxChars=30000\n```\n\nWhen set to `true`, the default file is\n`\u003clib_flow_mcp project\u003e/_private/flow-mcp-trace.jsonl`. Tracing is best-effort\nand never fails the MCP request path. Each JSONL line includes a sanitized\npayload plus a compact `summary`, `payloadChars`, `payloadTruncated` and, for\nresponses, `durationMs`. The optional `maxChars` symbol limits large payloads\nwhile preserving their summary. Standalone tests may also pass\n`config.mcp.traceJsonl` and `config.mcp.traceJsonlMaxChars`, but production\nconfiguration should use symbols.\n\nMCP resources provide the same guidance to agents that cannot read this repo:\n\n- `flow://guide/start`\n- `flow://guide/authoring`\n- `flow://guide/search-and-edit`\n- `flow://guide/custom-blocks`\n- `flow://guide/fullstack-paperboard`\n- `flow://guide/frontend-svelte`\n- `flow://guide/tracing`\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fconvertigo%2Fc8oprj-lib-flow-mcp","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fconvertigo%2Fc8oprj-lib-flow-mcp","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fconvertigo%2Fc8oprj-lib-flow-mcp/lists"}