Commit Graph

2599 Commits

Author SHA1 Message Date
diegosouzapw
bcfc87f31b fix(mitm): add CONNECT handler with bypass/passthrough TCP support (C1, plan 11 §4.6/§12 #16)
Bring `src/mitm/server.cjs` into compliance with the AgentBridge MITM
contract (master plan §3.5 / §12 acceptance #16). Prior to this commit
the bypass/passthrough logic existed in TS (`src/mitm/passthrough.ts`,
`src/mitm/targets/index.ts::routeConnection`, `src/lib/db/agentBridgeBypass.ts`)
but was completely disconnected from the running CJS proxy.

Changes:

- Add `server.on("connect", ...)` so HTTPS proxy clients can still tunnel
  to non-AgentBridge hosts without losing internet. Per host the handler
  decides:
    - bypass (default regex or user glob)  → raw TCP pipe, NO TLS decrypt,
      NO content logging (privacy: bypass = "never see content")
    - target (in TARGET_HOSTS)              → write 200 Connection
      Established and emit `connection` so the existing
      `https.createServer` decrypts and routes via the normal flow
    - passthrough (anything else)           → raw TCP pipe
- Introduce `src/mitm/_internal/bypass.cjs` shim that mirrors
  `DEFAULT_BYPASS_PATTERNS` and `routeConnection` from the TS source.
  Defaults stay hardcoded (banks, gov, okta, auth0); user patterns load
  from `<DATA_DIR>/mitm/bypass.json` (written by manager — separate commit).
- Add a CJS port of `sanitizeErrorMessage` and wire it into the intercept
  error path so HTTP/SSE error bodies never expose raw `err.message`.
  Closes a pre-existing Hard Rule #12 violation in the file.

Defaults match `src/mitm/passthrough.ts::DEFAULT_BYPASS_PATTERNS` and
`shouldBypass` precedence is identical to `routeConnection`. Antigravity
non-regression preserved — known hosts still trigger TLS termination via
the existing request handler.
2026-05-28 16:47:10 -03:00
diegosouzapw
0d52125ca6 polish(translator): add type='button' to MonitorTab toggle/refresh buttons (GAP-NOVO-7)
Match the rest of the codebase pattern. No functional change — there is
no <form> parent — but improves consistency.
2026-05-28 16:25:25 -03:00
diegosouzapw
053e62dcf8 refactor(translator): remove unused onSlugChange prop from AdvancedSection (GAP-NOVO-6)
Prop was declared but destructured as _onSlugChange (never consumed).
TranslatorPageClient relies on onOpenChange callbacks on each child
accordion instead. Cleaning the interface.
2026-05-28 16:25:20 -03:00
diegosouzapw
eaa6aa8b12 fix(translator): sync forceOpen reactively in StreamTransformer + Compression accordions (GAP-NOVO-4, GAP-NOVO-5)
Both accordions initialized open/hasOpened from forceOpen but never
reacted to forceOpen changes after mount. RawJsonPanel and PipelineView
already had this useEffect. Aligns the pattern so back/forward navigation
and inter-accordion switches work consistently.

Uses useRef to track false→true transitions only, so a manual close by the
user is not immediately overridden while forceOpen remains true.
2026-05-28 16:25:15 -03:00
diegosouzapw
6dc6282102 fix(translator): PipelineView ref callback to set hasOpened on first Collapsible mount (GAP-NOVO-3)
Collapsible does not expose onOpenChange, so clicking the accordion header
opens it but leaves {hasOpened && ...} false, rendering an empty container.
The ref callback (same pattern as RawJsonPanel) detects the first DOM
mount inside the Collapsible and sets hasOpened + notifies parent.

Adds regression test covering manual click flow (existing tests only
exercised defaultOpen=true). Also updates the pre-existing lazy-render test
whose assertion was incompatible with the new ref callback (Collapsible stub
always renders children, so the ref fires immediately — asserting 0 items
was only valid without the ref; the meaningful part of the test is preserved).
2026-05-28 16:25:08 -03:00
diegosouzapw
0f1bbc58a4 fix(batch): wireframe polishing — Used by roles, -50% inline, (partial) suffix
- FilesListTab: add (input)/(output)/(error) role label next to batch id in Used by column + tooltip (G-AUD1, plan §4 wireframe `b1 (input)`)
- BatchListTab: add -50% inline badge on Cost column per wireframe §3 `$6.20 (-50%)` (G-AUD2) + (partial) suffix on progress when expired_with_failures (G-AUD3)
- ExpirationBadge: document <1h/<6h/<24h tier semantics + >24h graceful fallback (G-AUD4)
- 4 new i18n keys in en + pt-BR (filesListUsedByRoleInput/Output/Error, batchListProgressPartial); 40 locales auto-filled via fill-missing-from-en.mjs
- Update list-regression test #13 to assert new used-by format (truncated id + role label + tooltip carries full id+role)
2026-05-28 16:24:32 -03:00
diegosouzapw
f0cdc3622e fix(agent-bridge-ui): remove double-write of risk-accepted localStorage (M5)
AgentCard.handleRiskAccept was calling markRiskAccepted() before opening the
RiskNoticeModal, which itself writes the same key via dontShowAgainKey on accept.
Remove the redundant markRiskAccepted call and delete the now-unused helper so
RiskNoticeModal (D16) is the sole canonical persistence owner. Add a spy-based
test asserting the key is written exactly once per accept.
2026-05-28 16:24:09 -03:00
diegosouzapw
d779707b3a refactor(inspector-ui): split StatsTab charts into separate dynamic-imported module (C3)
Move all recharts rendering into StatsCharts.tsx and replace the orphaned
_rechartsPreload no-op with a proper next/dynamic() call (ssr: false), achieving
real bundle split so recharts is not included in the initial page chunk.
2026-05-28 16:07:03 -03:00
diegosouzapw
9df7cad803 refactor(inspector): return 'unknown' from kindDetector for unclear signals (B1) 2026-05-28 16:06:25 -03:00
diegosouzapw
cc22ca0088 fix(quota,i18n): close B26 audit gap on DELETE plan + pt-BR translation
Two gaps found in second-pass code review of Group B:

1. B26 violation: DELETE /api/quota/plans/[connectionId] did not emit
   logAuditEvent. Per master plan B26, every plan mutation must audit.
   Now emits quota.plan.updated with metadata.reverted=true to mark the
   revert-to-auto/catalog semantic. Test integration extended with
   assertion that audit event is present after DELETE.

2. pt-BR / pt locales had "costsSection": "Costs" (English label) instead
   of the Portuguese "Custos". Other section labels in the same block are
   left in English intentionally (analytics, monitoring) — they are
   project-wide untranslated terms; "Custos" is the established repo
   translation for the Costs section title.

Validation:
- npm run typecheck:core: clean
- tests/integration/quota-plans-crud.test.ts: 10/10 pass (includes new
  assertion on DELETE → audit event)
- eslint --no-warn-ignored on touched files: clean
2026-05-28 16:03:30 -03:00
diegosouzapw
dfa17ef621 chore(cli): remove unused BaseUrlSelect/ApiKeySelect/ManualConfigModal (plan 14)
Components were created by F4 per master-plan §3.7-§3.9 but never integrated:
the `*ToolCard.tsx` files use the legacy `ManualConfigModal` from
`@/shared/components` (barrel-export root), not the F4 versions in
`@/shared/components/cli`. The 3 files were sitting as dead code.

Removes:
- src/shared/components/cli/BaseUrlSelect.tsx
- src/shared/components/cli/ApiKeySelect.tsx
- src/shared/components/cli/ManualConfigModal.tsx
- tests/unit/ui/BaseUrlSelect.test.tsx
- tests/unit/ui/ApiKeySelect.test.tsx
- tests/unit/ui/ManualConfigModal.test.tsx

Updates `src/shared/components/cli/index.ts` to drop the dead exports.

Kept (actively used by page clients):
- CliToolCard, CliConceptCard, CliComparisonCard

Verified:
- typecheck:core + noimplicit:core clean
- npx eslint src/shared/components/cli/: 0 issues
- check:cycles: clean (212 files, -3 from removed components)
- 50/50 UI tests pass across the 3 kept components + 3 page clients
- 0 residual imports of the 3 removed symbols anywhere in src/ or tests/

Closes code review v3 gap #1 (dead code).
2026-05-28 15:57:02 -03:00
Ronaldo Davi
46b451c5fa i18n(pt-BR): complete missing translations and sync with en.json 2026-05-28 15:30:56 -03:00
diegosouzapw
958418f9d9 fix(memory): expose cacheStats + restore 40/40/40/40 gate + add test:vitest:ui script
Gap 1 (auditor deep review): `GET /api/memory` was computing hitRate from
memoryCache.stats() but never exposing cacheStats in the response. MemoriesTab
reads `stats.cacheStats` to decide whether to render the Hit Rate card (only
when hits + misses > 0). Without this field the card never appeared even when
hitRate > 0, contradicting plan 21 §7 #6 and bug-fix #5.

Gap 2 (auditor deep review): 8 `tests/unit/ui/*.test.tsx` files created by F7
were orphaned — `test:unit` filters `*.test.ts` only, and `vitest.mcp.config.ts`
does not include `tests/unit/ui/`. Added `test:vitest:ui` script using the
default vitest.config.ts (which already includes `tests/unit/**/*.test.tsx`).

Coverage gate aligned with the effective 40/40/40/40 per user decision.
2026-05-28 15:16:31 -03:00
diegosouzapw
bd1ef1a685 merge: G5 canonical KPIs (Util média + Em empréstimo) + usePoolsUsageAggregate (gap #5 closed) 2026-05-28 14:23:20 -03:00
diegosouzapw
a1399effab chore(i18n): pt-BR + en quotaShare.kpiAvgUtilization + kpiBorrowingNow (B/G5) 2026-05-28 14:12:00 -03:00
diegosouzapw
5e79f1e656 refactor(quota-share): replace stale KPIs with canonical 4 cards (active/keys/avg-util/borrowing) (B/G5) 2026-05-28 14:11:53 -03:00
diegosouzapw
e7014ffaa0 feat(quota-share): add usePoolsUsageAggregate hook for avg util + borrowing count (B/G5) 2026-05-28 14:11:47 -03:00
diegosouzapw
533db63a86 merge(F9): E2E + docs + i18n consolidation 2026-05-28 13:59:27 -03:00
diegosouzapw
eab8b12171 fix(memory): align legacy cli-memory-commands test with D17 type mapping + env doc tweaks
Plan 21 / D17 — CLI now remaps legacy types (user/feedback/project/reference) to
canonical (factual/episodic/procedural/semantic). The legacy assertion in
cli-memory-commands.test.ts still expected 'user'; update to expect 'factual'.

Also includes incidental .env.example + docs/ENVIRONMENT.md + qdrant
embedding-models route tweaks captured by F10 audit pass.
2026-05-28 13:59:19 -03:00
diegosouzapw
27d4a7aeac fix(cli): suppress react-hooks/set-state-in-effect for load-on-mount pattern (plan 14)
Pre-existing lint error from F8 commit 2d58519ca9 — the new react-hooks/set-state-in-effect rule conservatively flags any setState within useEffect body, even when setState happens async after Promise resolution. The "load remote data on mount" pattern is canonical until React 19 use()/Suspense migration.

Fix adds cancelled-flag pattern to prevent setState after unmount + block-disable with justification comment. Tests still pass 5/5.

Found during code review v2 deep audit — F10 audit reported "lint 0 errors" but only ran focused lint, not full project (which surfaces ~2985 pre-existing warnings + this 1 new error).
2026-05-28 13:58:54 -03:00
diegosouzapw
c73a90134b feat(agent-skills): rewrite generator templates to English (GAP-D - template change) 2026-05-28 13:55:32 -03:00
diegosouzapw
01d49f5373 chore(i18n): pt-BR + en quotaShare.stackedBarTitle + usedSuffix (B/G4)
Add stackedBarTitle and usedSuffix keys to quotaShare namespace in both
pt-BR and en locales to support the new StackedAllocationBar component.
2026-05-28 13:51:52 -03:00
diegosouzapw
d002288266 fix(quota-share): correct PoolCard statusCls template literal + remove duplicate icon span (B/G4)
Line 68: {statusCls} string literal → \${statusCls} template literal so status color applies.
Remove duplicate <span> wrapping (lines 71-73) that rendered the icon twice via copy-paste bug.
2026-05-28 13:51:26 -03:00
diegosouzapw
b1fb1509ff feat(quota-share): add StackedAllocationBar component (per-key slices) (B/G4)
New component renders a horizontal stacked bar split by allocation weight,
with optional per-key consumed% labels sourced from PoolUsageSnapshot.dimensions[dimensionIndex].perKey.
Returns null when allocations is empty. Uses shared PALETTE of 8 colors.
2026-05-28 13:51:20 -03:00
diegosouzapw
517385e789 docs(memory): F9 — E2E specs, MEMORY.md engine arch, openapi routes, i18n sort
- Add tests/e2e/memory-engine.spec.ts (7 scenarios: 3-tab render, memories table,
  add/edit modal, playground simulate, engine status chips, reindex button)
- Add tests/e2e/memory-qdrant-routes.spec.ts (3 scenarios: Qdrant config card,
  Test Connection → sanitized error without stack, Cleanup → sanitized error)
- Update docs/frameworks/MEMORY.md: add Engine architecture (3-tier ASCII diagram),
  Embedding sources table, Hybrid RRF (k=60) section, Backfill lazy+reindex section,
  Settings extension (7 new fields D9), updated REST API table (10 new routes),
  updated Dashboard section (Studio 3 tabs), MCP D16 strategy from settings, See Also
- Update docs/reference/openapi.yaml: add Memory tag + 13 new paths
  (/api/memory, /api/memory/{id} PUT, retrieve-preview, embedding-providers,
  engine-status, summarize, reindex, /api/settings/memory GET+PUT,
  /api/settings/qdrant GET+PUT+health+search+cleanup+embedding-models)
  + MemoryEntry, MemorySettingsExtended, QdrantSettings, QdrantHealthResult schemas
- Update docs/architecture/REPOSITORY_MAP.md: add embedding/, vectorStore.ts,
  reindex.ts, memoryVec.ts, memory Studio UI entries
- Sort memory.* namespace keys alphabetically in pt-BR.json and en.json
  (no duplicate found — pure reorder, no content change)
- .env.example already has all 7 vars from §3.9 (confirmed, no change needed)
2026-05-28 13:36:43 -03:00
diegosouzapw
3528ad4515 fix(agent-skills): add 200ms debounce to preview pane lazy-fetch (GAP-C) 2026-05-28 13:30:41 -03:00
diegosouzapw
083d5c0fb9 feat(agent-skills): expand SkillsConceptCard with 5-row conceptual comparison (GAP-A) 2026-05-28 13:18:37 -03:00
diegosouzapw
cd46090b75 feat(i18n): banner/separator/risk strings for fix4 (en + pt-BR) 2026-05-28 12:58:44 -03:00
diegosouzapw
72fd52db83 feat(ui): per-agent RiskNoticeModal on first DNS activation (fix4 gap3) 2026-05-28 12:58:39 -03:00
diegosouzapw
5f065a20e5 feat(ui): conversation tab CONTEXT HISTORY / MODEL RESPONSE separators (fix4 gap2) 2026-05-28 12:58:33 -03:00
diegosouzapw
2406e392d8 feat(ui): historic session banner with back-to-live action (fix4 gap1) 2026-05-28 12:58:29 -03:00
diegosouzapw
52af5a13f0 fix(agent-skills): replace hardcoded "Todas" with i18n t(filterAll) (GAP-F) 2026-05-28 12:58:03 -03:00
diegosouzapw
401632d925 fix(translator): add 17 missing i18n keys (pipeline steps + concept diagram) (GAP-NOVO-1)
Added pipelineStepClientRequest/Desc, pipelineStepFormatDetected/Desc,
pipelineStepOpenAIIntermediate/Desc, pipelineStepProviderFormat/Desc,
pipelineStepProviderResponse/Desc, conceptDiagramArrow1-3,
conceptDiagramExampleHub, conceptDiagramHubTooltip,
conceptDiagramSourceTooltip, conceptDiagramTargetTooltip to both
en.json and pt-BR.json.

Extended translator-friendly-i18n-keys.test.ts NEW_KEYS array with all
17 new keys. Test suite now covers 69 keys (was 52) — 172 tests pass.
2026-05-28 12:55:33 -03:00
diegosouzapw
77b055aba0 fix(cli): address code review v2 findings — broken test path, dead code, type narrowing (plan 14)
- tests/unit/custom-cli-config.test.ts: fix ERR_MODULE_NOT_FOUND — stale import path cli-tools → cli-code (regression from F8 git mv, missed by F10 audit because it only ran curated test subset).
- tests/unit/ui/CliAgentsPage.test.tsx: update vi.mock path to current cli-code location (was no-op mock pointing to deleted path).
- tests/unit/ui/CliToolCard.test.tsx: update URL strings /dashboard/cli-tools/claude → /dashboard/cli-code/claude (cosmetic alignment with new routes).
- src/app/(dashboard)/dashboard/cli-code/components/ToolDetailClient.tsx: remove dead case "cliproxyapi" + unused import (no entry in CLI_TOOLS catalog).
- src/app/(dashboard)/dashboard/cli-agents/CliAgentsPageClient.tsx: replace inline div skeleton with shared <CardSkeleton /> for visual consistency with CliCodePageClient.
- src/app/api/cli-tools/{forge,jcode,deepseek-tui,smelt,pi}-settings/route.ts: replace catch (err: any) with catch (err) + (err as NodeJS.ErrnoException).code narrowing (8 instances, eliminates 8 of 11 implicit-any introductions).

Validated: custom-cli-config.test.ts now 3/3 PASS (was 0/1 FAIL with ERR_MODULE_NOT_FOUND); F1/F3 tests 147/147 PASS; UI tests 25/25 PASS; typecheck:core + noimplicit clean.
2026-05-28 12:47:31 -03:00
diegosouzapw
3f3e64a800 merge: G3 allowlist refactor to align with real logAuditEvent naming (gap #3 closed) 2026-05-28 12:36:07 -03:00
diegosouzapw
29e79764d4 chore(i18n): pt-BR + en activity.eventVerb keys for real audit actions (B/G3)
Add 22 new keys under activity.eventVerb.* in both pt-BR.json and en.json
corresponding to the new ACTIVITY_ICONS i18nKeyVerb values (providerCredentials*,
authLogin*, authLogoutSuccess, syncToken*, settingsUpdate, settingsUpdateFailed,
serviceRevealApiKey). Existing keys preserved for back-compat.
2026-05-28 12:31:31 -03:00
diegosouzapw
8f0beb99a0 refactor(audit): align ACTIVITY_ICONS 1:1 with new allowlist (B/G3)
Replace all icon specs to match the new 26 real action names. Every entry in
HIGH_LEVEL_ACTIONS now has a corresponding ACTIVITY_ICONS spec with appropriate
Material Symbols icon and i18nKeyVerb key. Old entries (provider.added, auth.login,
etc.) removed since those actions are no longer in the allowlist.
2026-05-28 12:31:24 -03:00
diegosouzapw
8771e7232e refactor(audit): align HIGH_LEVEL_ACTIONS with real logAuditEvent emitters (B/G3)
Replace the old "clean naming" allowlist (provider.added, auth.login, etc.) with
the 26 real action strings emitted by logAuditEvent calls in the codebase
(provider.credentials.*, auth.login.*, settings.update, sync.token.*, etc.).
Activity feed was empty because HIGH_LEVEL_ACTIONS used invented names that
never matched any real audit event.
2026-05-28 12:31:17 -03:00
diegosouzapw
becf55ddb1 fix(translator): add onInputChange callback to TranslateTab to sync sharedInputContent (GAP-NOVO-2)
TranslateTab now accepts onInputChange?(text: string) => void. A unified
handleInputChange wrapper calls both setInputText and onInputChange? so
CompressionPreviewAccordion and pipeline Step 1 at the shell level receive
the real input text instead of always seeing an empty string.

TranslatorPageClient passes onInputChange={setSharedInputContent} to wire
the sync. Test files updated to accept the new optional prop in mocks and
verify the callback is wired without throwing.
2026-05-28 12:27:20 -03:00
diegosouzapw
826d436abb Merge branch 'feat/playground-search-i18n-docs-F9' into chore/playground-search-audit-F10 2026-05-28 12:27:16 -03:00
diegosouzapw
000a529744 fix(translator): remove unused slug='testbench' phantom prop (BUG-NOVO-1)
TestBenchAccordionProps extends Omit<AdvancedAccordionProps, 'slug'> so slug
is not a valid prop on that component. The slug is fixed internally as
'testbench' — callers must not pass it.
2026-05-28 12:17:52 -03:00
diegosouzapw
22d2633773 fix(memory): replace swr with native React hooks (swr not installed)
F7 originally implemented useEngineStatus/useMemorySettings via swr, but the
package is not in package.json — would crash at runtime. Replaced with native
useState + useEffect + setInterval polling. Same public API
(status/settings/isLoading/isError/mutate/save) so the existing components
and the 8 UI tests (which mock the hooks directly) keep working unchanged.
2026-05-28 12:17:31 -03:00
diegosouzapw
5e6e513c02 fix(search-tools): wire real ExportCodeModal from F7 into SearchToolsTopBar
Replace MockExportCodeModal stub in SearchToolsTopBar with the real
ExportCodeModal component from playground/components/ExportCodeModal.
Update SearchToolsClient exportState type from Record<string,unknown>
to PlaygroundState for proper type alignment.

Micro-fix detected during F10 audit: F8 left a TODO(F7-merge) stub
that was never resolved after F7 merged.
2026-05-28 12:15:35 -03:00
diegosouzapw
bff01d6fe3 feat(i18n): deep-merge EN fallback to fill missing locale keys (B/G1)
Export deepMergeFallback and apply it in getRequestConfig so all 39
non-EN locales receive EN text for any key absent in their JSON file.
Locale-specific translations always win; EN fills gaps only.
2026-05-28 12:13:59 -03:00
diegosouzapw
566ebb9531 feat(i18n): add playground + search-tools keys (PT-BR + EN)
Add 60 new playground.* keys and 50 new search.* keys to en.json and
pt-BR.json covering Playground Studio tabs (Chat/Compare/API/Build),
config pane, param sliders, presets, improve prompt, export, compare
metrics (TTFT/TPS), Build tab (tools/structured output), and Search Tools
Studio tabs (Search/Scrape/Compare), SearchConceptCard, ProviderCatalog,
ScrapeResult, and config pane fields.

PT-BR has full Portuguese translations. EN has EN strings.
2026-05-28 11:58:33 -03:00
diegosouzapw
f8bf164180 feat(memory): implement F7 Studio UI layer for /dashboard/memory
Converts the monolithic memory page into a 3-tab Studio layout
(Memories | Playground | Engine) with URL-driven tab state, 8 new
React components, 2 SWR hooks, 50+ i18n keys, and 8 Vitest unit tests
covering all new components (45/45 passing).
2026-05-28 11:55:18 -03:00
diegosouzapw
2f3cbdb9fe merge(fix3): wire useTranslations in Traffic Inspector components (Group A) 2026-05-28 11:40:29 -03:00
diegosouzapw
f37148903d merge(fix2): system proxy revert on page exit (Group A) 2026-05-28 11:38:13 -03:00
diegosouzapw
8dbc3ae551 feat(i18n): wire useTranslations in Traffic Inspector components (fix3)
Convert CaptureModesToolbar, TopBarControls, CustomHostsManager,
HttpProxySnippetCard and SessionRecorderBar to consume useTranslations
instead of hardcoded English strings. Add 7 missing trafficInspector
keys (customHostsTitle, loading, copied, copy, httpProxyTitle,
notRecording, anyStatus) to both en.json and pt-BR.json.
2026-05-28 11:36:02 -03:00
diegosouzapw
953f795b15 Merge branch 'feat/search-tools-ui-F8' into chore/playground-search-audit-F10 2026-05-28 11:27:15 -03:00