feat(ai-tools): greek-room repeated-words endpoint + fluent-ai client#181
Open
JEdward7777 wants to merge 11 commits into
Open
feat(ai-tools): greek-room repeated-words endpoint + fluent-ai client#181JEdward7777 wants to merge 11 commits into
JEdward7777 wants to merge 11 commits into
Conversation
Mechanical prettier --write only (no semantic changes): - emphasis markers *foo* -> _foo_ - markdown table separator padding - reflow of TS code samples inside fenced blocks
The repo's @antfu/eslint-config (formatters: true) lints TS code blocks inside markdown. Adjust the illustrative import statements in the repeated-word-check proposal to satisfy perfectionist/sort-imports and import/consistent-type-specifier-style: - separate import groups with blank lines - hoist inline type specifiers to top-level 'import type' Hand-formatted (not raw eslint --fix output) so the samples stay readable. No prose changed. Verified: 'eslint .' and 'prettier --check .' both pass.
…tools proposal Capture kaseywright's review outcomes (approved 2026-06-02) directly in the proposal docs so the decisions persist beyond the PR thread: - D8/§8.1: intentional snake_case divergence accepted; add in-code-comment guardrail - D10/§9.3: AI_TOOLS_USE permission alias confirmed; document for future reference - D9/§8.2: envelope pass-through confirmed, conditioned on standard web-client format - §15: mark open questions resolved, each linking its originating review comment
…ient Implements the AI-tools integration approved in PR eten-tech-foundation#173 (per docs/proposals/repeated-word-check/ai-tools-integration-suggestion.md §2). - New domain src/domains/ai-tools/ exposing POST /ai/tools/greek-room/repeated-words, registered on the OpenAPIHono app via app.ts. - Shared client callFluentAi<TReq,TResult>(toolPath, body, resultSchema, options?) at src/lib/services/fluent-ai/ (30s default timeout, AbortSignal support, no polling/caching/retries per §7.3). - Two env vars FLUENT_AI_URL and FLUENT_AI_KEY (required, no defaults) wired through env.ts + .env.example + .env.test. - Permission alias PERMISSIONS.AI_TOOLS_USE = 'content:update' (D10) with review-link comment. - Two ErrorCodes AI_SERVICE_UNAVAILABLE and AI_TOOL_EXECUTION_FAILED, both -> HTTP 502. - Envelope pass-through (D9): 200 for terminal completed/failed/cancelled, 202 for queued/running; errors via getHttpStatus standard shape. - snake_case wire contract kept verbatim (D8) with guardrail comments next to the Zod schemas. - Tests: callFluentAi unit tests (§13.1), route tests (§13.2), and host-runnable scripts/smoke-repeated-words.ts via npm run smoke:repeated-words. Schemas verified against the live fluent-ai contract; proposal §8.2/§10.2 updated to match. Out of scope: polling endpoint, DB persistence, frontend hooks, retries, caching. Refs: PR eten-tech-foundation#173 (kaseywright, 2026-06-02)
…12.10 wiring runbook - Split the long proposal at the §10/§11 boundary so each file stays under the markdown line-count lint limit; sections numbered continuously across the pair so all 'see §N' references stay valid. - Part 1 (ai-tools-integration-suggestion.md): contract & design, §1-§10. - Part 2 (ai-tools-integration-operations.md, new): job-queue forward compatibility, service discovery / Docker / env wiring, testing, future work, resolved reviewer Q&A, §11-§15. - Add §12.10 'Wiring up a running ecosystem' runbook (env vars, compose override, restart-just-api, health checks, BetterAuth set-auth-token sign-in, smoke-script invocation) reconciled with scripts/smoke-repeated-words.ts. - Add ai-tools-integration-status.md: file-by-file account of what is implemented at b055f84 vs. what remains (live e2e run + paired fluent-platform PR) vs. out of scope. - Update summary.md companion links to the new file set. - Fix relative-path depth in all four docs (now under repeated-word-check/); all 79 internal links resolve; repoint a stale route-test example to server.test.ts / projects.service.test.ts. Docs-only; no source changes.
…in; verify live e2e - Add FLUENT_AI_API_PREFIX env var (default empty) and buildToolUrl() so the fluent-ai base path is configurable instead of hardcoded /api/v1/, matching the live build that serves Greek-Room tools at the root. - Enhance scripts/smoke-repeated-words.ts: BetterAuth auto sign-in with a trusted Origin header, set-auth-token capture, missing-dev-user + origin hints, and a PASS/FAIL verdict banner. - Add client tests for empty-prefix and configured-prefix URL building. - Document FLUENT_AI_API_PREFIX in .env.example. - Update repeated-word-check proposal docs to mark the live end-to-end run and compose wiring as done and to reflect the configurable prefix.
# Conflicts: # docs/proposals/repeated-word-check/ai-tools-integration-suggestion.md # docs/proposals/repeated-word-check/ai-tools-integration-summary.md
This was referenced Jun 4, 2026
Merged
kaseywright
approved these changes
Jun 5, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Exposes fluent-ai's Greek-Room Repeated Words check through fluent-api as the first AI-tool endpoint, behind a generic, reusable pattern designed to absorb future AI tools (other Greek-Room checks, LLM drafting, embeddings) with a small per-tool wrapper.
This is the implementation that follows the design reviewed and approved in PR #173 (kaseywright, 2026-06-02). PR #173 was documentation/proposal only and has been merged; this PR contains the actual code on a fresh branch (
jel-word-check-impl), rebased on top of currentmain.This PR is paired with a small fluent-platform compose PR that must land for the live
fluent-api ↔ fluent-aiconnection to authenticate and for the integration to run from a clean stack:Prerequisite: eten-tech-foundation/fluent-platform#5
Without those compose overrides,
fluent-apicannot reach/authenticate againstfluent-ai(and theaicontainer fails to come up from a clean slate), so an end-to-end run / any future integration check would fail. The fluent-platform PR addsFLUENT_AI_URL: http://ai:8200, mountsfluent-api/scriptsinto theapicontainer, and fixes two clean-slateai-container issues (MIGRATIONS_DATABASE_URLpassword drift and aUV_CACHE_DIRon anoexecmount).What's added
New endpoint:
POST /ai/tools/greek-room/repeated-words/ai/as fluent-api's first service-family prefix. Per-tool URL preserves OpenAPI type-safety (a generic/dispatchwas rejected).requirePermission(PERMISSIONS.AI_TOOLS_USE).ToolJobResponse<T>verbatim — 200 for terminal statuses, 202 for non-terminal (queued/running) — so the same code path handles sync today and polling later.Shared client:
callFluentAi<TReq, TResult>(toolPath, body, schema, options?)insrc/lib/services/fluent-ai/withDatabaseRetrypatterns. Adding a new tool is ~2 files / a few lines.FLUENT_AI_URL+ optionalFLUENT_AI_API_PREFIX+toolPath; 30s default timeout; validatesresultagainst the schema only whenstatus === "completed".AI_SERVICE_UNAVAILABLE;failed/cancelledenvelopes →AI_TOOL_EXECUTION_FAILED(both → HTTP 502). No polling, caching, or retries by design.Configuration:
FLUENT_AI_URL,FLUENT_AI_KEY(no defaults — boot fails if missing), plus optionalFLUENT_AI_API_PREFIX(defaults to empty to match the live fluent-ai build, which serves routes at the root; set/api/v1when fluent-ai versions its routes). Documented in.env.example, test values in.env.test.PERMISSIONS.AI_TOOLS_USEas a string alias ofcontent:update(D10).Tests & tooling:
fluent-ai.client.test.ts— completed/queued happy paths, failed/cancelled and 4xx/5xx/network/parse/schema/timeout/abort error mappings, request-shape assertions, andFLUENT_AI_API_PREFIXcases.ai-tools.route.test.ts— 401/403/400, 200 completed pass-through, 202 queued pass-through, 502 on failure, and a "no enrichment" verbatim-forward assertion.scripts/smoke-repeated-words.ts+npm run smoke:repeated-words— host/in-container probe with BetterAuth auto sign-in and a PASS/FAIL banner.Verification
prettier --check,eslint,tsc --noEmit, and 78/78 vitest tests passing.POST /ai/tools/greek-room/repeated-words 200onapi; matching200onai). The canned 3-verse corpus returns exactly two findings — one suspicious ("in in") and one legitimate ("truly truly") — withverse_count === 3.Out of scope (deferred by design)
Polling endpoint (
GET /ai/tools/jobs/{job_id}), DB persistence of tool runs, frontend hooks/UI, transport retries, caching, rate limits, MCP facade. ThecallFluentAi/ToolJobResponseshapes are forward-compatible with all of these.See
docs/proposals/repeated-word-check/for the full design (Part 1/Part 2), the file-by-file implementation status, and the reviewer-orientation summary.