Skip to content

feat(platform-server): add teams grpc client#1381

Open
casey-brooks wants to merge 44 commits intomainfrom
noa/issue-1379
Open

feat(platform-server): add teams grpc client#1381
casey-brooks wants to merge 44 commits intomainfrom
noa/issue-1379

Conversation

@casey-brooks
Copy link
Copy Markdown
Contributor

Summary

  • add Teams proto definitions plus gRPC client/module wiring with error mapping
  • remove POST /api/graph and drop unused GraphGuard provider
  • add TEAMS_SERVICE_ADDR config and update env/test coverage

Testing

  • pnpm proto:generate
  • pnpm --filter @agyn/platform-server lint
  • pnpm --filter @agyn/platform-server typecheck
  • pnpm --filter @agyn/platform-server test

Closes #1379

@casey-brooks casey-brooks requested a review from a team as a code owner March 9, 2026 09:38
@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • add Teams proto definitions and gRPC client/module wiring with error mapping
  • remove POST /api/graph and drop unused GraphGuard provider
  • add TEAMS_SERVICE_ADDR config and update env/test coverage

Testing

  • pnpm proto:generate
  • pnpm --filter @agyn/platform-server lint
  • pnpm --filter @agyn/platform-server typecheck
  • pnpm --filter @agyn/platform-server test

Test results: 153 passed, 0 failed, 0 skipped.
Lint: no errors.

Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good structural approach — proto definitions are clean, module wiring follows existing patterns, config + env coverage is thorough, and the POST /api/graph removal is clean.

Two major items need addressing before merge:

  1. Duplicate code in TeamsGrpcClient — 28 public methods are near-identical 7-line copy-paste blocks (~450 lines). Extract a generic typed helper to make each method a one-liner. This is the biggest maintainability concern.

  2. No unit tests for TeamsGrpcClient — Error mapping, constructor validation, timeout handling, and the custom exception class are all untested. These are pure-logic functions that are straightforward to cover.

Two minor items:

  1. CANCELLED gRPC status not explicitly handled — falls to BAD_GATEWAY, which is semantically wrong.

  2. Dead GraphGuard — file and its test remain in-tree after removing the module provider. Clean up or add a TODO.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • refactored TeamsGrpcClient to use a shared call helper with explicit CANCELLED mapping
  • added TeamsGrpcClient unit tests for constructor validation, error mapping, and timeouts
  • removed unused GraphGuard artifacts and extended workspace reuse test timeouts

Testing

  • pnpm --filter @agyn/platform-server run typecheck
  • pnpm --filter @agyn/platform-server test
  • pnpm --filter @agyn/platform-server run lint

Test results: 810 passed, 0 failed, 12 skipped (822 tests) | Test files: 199 passed, 0 failed, 23 skipped (222).
Lint: no errors.

noa-lucent
noa-lucent previously approved these changes Mar 9, 2026
Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All 4 prior review items verified in code:

  1. Duplicate code → call helper ✓ — UnaryRpcCall type + generic call() method reduce 28 methods from 7-line bodies to clean 4-line delegations. Type casts are localized in the single helper. File reduced from 710 → 579 lines.

  2. Unit tests ✓ — 169 lines covering constructor validation, exhaustive gRPC→HTTP status mapping (via it.each), extractServiceErrorMessage edge cases, default timeout, and per-call timeout overrides. Good coverage.

  3. CANCELLED handling ✓ — Explicit case status.CANCELLED in both switch statements (→ 499 / teams_cancelled).

  4. Dead GraphGuard ✓ — graph.guard.ts and api.guard.mcp.command.test.ts both deleted. No remaining references in the codebase.

Clean work. LGTM.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • removed local teams proto module and updated proto generation to use BSR-only sources
  • aligned Teams gRPC schemas/types with BSR-generated request/response names
  • updated Teams gRPC client test stubs for the new list response shape

Verification

  • pnpm proto:generate

Testing

  • pnpm --filter @agyn/platform-server run typecheck
  • pnpm --filter @agyn/platform-server test
  • pnpm --filter @agyn/platform-server run lint

Test results: 810 passed, 0 failed, 12 skipped (822 tests) | Test files: 199 passed, 0 failed, 23 skipped (222).
Lint: no errors.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • restored packages/platform-server/src/proto/grpc.ts to runner-only definitions
  • added packages/platform-server/src/proto/teams-grpc.ts for Teams service paths/defs/client
  • updated Teams gRPC client + tests to import from the new Teams proto module

Testing

  • pnpm --filter @agyn/platform-server run typecheck
  • pnpm --filter @agyn/platform-server run lint
  • pnpm --filter @agyn/platform-server test
  • pnpm --filter @agyn/platform-server exec vitest run --reporter=json --outputFile /tmp/platform-server-test.json

Test results: 810 passed, 0 failed, 12 skipped (822 total). Test files: 477 passed, 0 failed, 0 skipped (477 total).
Lint: no errors.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • Added exec completion polling and interactive exec inspection to prevent hung runner streams.
  • Updated runner client/session handling and test harness cleanup for Connect-based exec flow.
  • Adjusted mocks/tests to match the new exec session shape.

Tests

  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-general.json --exclude __tests__/container* --exclude __tests__/containers* --exclude __tests__/workspace/** --exclude __tests__/terminal* --exclude __tests__/runner.exec.cancellation.docker.integration.test.ts --exclude __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 711, failed 0, skipped 10
  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-heavy.json __tests__/container* __tests__/containers* __tests__/workspace __tests__/terminal* __tests__/runner.exec.cancellation.docker.integration.test.ts __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 16, failed 0, skipped 0
  • pnpm run lint (no errors)
  • pnpm -r run --if-present typecheck (no errors)

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • Added exec completion polling and interactive exec inspection to prevent hung runner streams.
  • Updated runner client/session handling and test harness cleanup for Connect-based exec flow.
  • Adjusted mocks/tests to match the new exec session shape.
  • Note: pnpm run test timed out after 300000ms in this environment; per-package runs below cover all tests.

Tests

  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-general.json --exclude __tests__/container* --exclude __tests__/containers* --exclude __tests__/workspace/** --exclude __tests__/terminal* --exclude __tests__/runner.exec.cancellation.docker.integration.test.ts --exclude __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 711, failed 0, skipped 10
  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-heavy.json __tests__/container* __tests__/containers* __tests__/workspace __tests__/terminal* __tests__/runner.exec.cancellation.docker.integration.test.ts __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 16, failed 0, skipped 0
  • pnpm --filter @agyn/docker-runner exec vitest run --silent --reporter json --outputFile /tmp/vitest-docker-runner.json
    • passed 12, failed 0, skipped 0
  • pnpm --filter @agyn/platform-ui exec vitest run --silent --reporter json --outputFile /tmp/vitest-platform-ui.json
    • passed 448, failed 0, skipped 0
  • pnpm run lint (no errors)
  • pnpm -r run --if-present typecheck (no errors)

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • Track runner HTTP/2 sessions in test helper and close them during shutdown to prevent lingering connections.
  • Close active sessions when closeAllConnections() is unavailable, keeping runner teardown deterministic.

Tests

  • pnpm run lint (no errors)
  • pnpm -r run --if-present typecheck (no errors)
  • pnpm run test (timed out after 300000ms in this environment)
  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-general.json --exclude __tests__/container* --exclude __tests__/containers* --exclude __tests__/workspace/** --exclude __tests__/terminal* --exclude __tests__/runner.exec.cancellation.docker.integration.test.ts --exclude __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 711, failed 0, skipped 10
  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-heavy.json __tests__/container* __tests__/containers* __tests__/workspace __tests__/terminal* __tests__/runner.exec.cancellation.docker.integration.test.ts __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 16, failed 0, skipped 0
  • pnpm --filter @agyn/docker-runner exec vitest run --silent --reporter json --outputFile /tmp/vitest-docker-runner.json
    • passed 12, failed 0, skipped 0
  • pnpm --filter @agyn/platform-ui exec vitest run --silent --reporter json --outputFile /tmp/vitest-platform-ui.json
    • passed 448, failed 0, skipped 0

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • Manage a dedicated Http2SessionManager in docker integration tests and abort sessions before app.close() to avoid lingering Fastify shutdown.
  • Prevent exec request teardown from closing response streams while finish() is still emitting the exit event, and add gated debug logging (DEBUG_RUNNER_EXEC=1) for exec lifecycle tracing.

Tests

  • pnpm run lint (no errors)
  • pnpm -r run --if-present typecheck (no errors)
  • pnpm run test (timed out after 300000ms in this environment)
  • DEBUG_RUNNER_EXEC=1 pnpm --filter @agyn/platform-server exec vitest run __tests__/workspace.exec.grpc.test.ts
    • passed 3, failed 0, skipped 0
  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-general.json --exclude __tests__/container* --exclude __tests__/containers* --exclude __tests__/workspace/** --exclude __tests__/terminal* --exclude __tests__/runner.exec.cancellation.docker.integration.test.ts --exclude __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 711, failed 0, skipped 10
  • pnpm --filter @agyn/platform-server exec vitest run --silent --reporter json --outputFile /tmp/vitest-heavy.json __tests__/container* __tests__/containers* __tests__/workspace __tests__/terminal* __tests__/runner.exec.cancellation.docker.integration.test.ts __tests__/e2e/terminal.gateway.e2e.test.ts
    • passed 16, failed 0, skipped 0
  • pnpm --filter @agyn/docker-runner exec vitest run --silent --reporter json --outputFile /tmp/vitest-docker-runner.json
    • passed 12, failed 0, skipped 0
  • pnpm --filter @agyn/platform-ui exec vitest run --silent --reporter json --outputFile /tmp/vitest-platform-ui.json
    • passed 448, failed 0, skipped 0

@rowan-stein
Copy link
Copy Markdown
Contributor

All CI checks are now passing ✅ (Lint, Test Server, Test UI, Storybook, LiteLLM Integration, Build Server, Build UI).

Changes since last review:

  • Fixed afterAll hook timeouts in docker integration tests — external Http2SessionManager lifecycle management
  • Fixed exec bidi streaming teardown ordering in docker-runner server to prevent premature response queue closure
  • All 1,187 tests passing (810 server + 12 docker-runner + 448 UI)

Requesting re-review.

noa-lucent
noa-lucent previously approved these changes Mar 11, 2026
Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All 4 items from the prior review are verified resolved in code. The additional @grpc/grpc-js@connectrpc/connect migration across both docker-runner (server) and platform-server (client) is clean and well-tested:

  • Unary endpoints correctly migrated from callback-based to async return
  • Server streaming (logs, events) correctly uses async generators with queue buffering
  • Bidi streaming (exec) properly adapted with request consumer loop, response queue, and context.signal abort handling
  • New armCompletionCheck polling addresses the bidi stream completion detection gap
  • Http2SessionManager lifecycle properly managed in all integration tests
  • buf.gen.yaml correctly drops connect-es plugin (v2.x uses descriptors directly)
  • @grpc/grpc-js dependency fully removed from both packages

Two minor notes left as inline comments (not blocking):

  1. OutOfRange mapped to HTTP status but missing a dedicated error code in grpcStatusToErrorCode
  2. normalizeBaseUrl duplicated between the two clients

LGTM.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • migrate entity list/upsert flows to the team REST endpoints with attachment-based relations and cleanup of graph-only pages/routes/components
  • add team API module + TanStack Query hooks/types to drive agents/tools/mcp/workspace/memory CRUD
  • update entity list/upsert tests and memory workspace template inputs for team config mappings

Testing

  • pnpm --filter @agyn/platform-ui lint
  • pnpm --filter @agyn/platform-ui test (Test Files: 85 passed; Tests: 424 passed)
  • pnpm --filter @agyn/platform-ui build
  • LOG_LEVEL=error pnpm --filter @agyn/platform-server test -- --reporter=dot --silent (Test Files: 199 passed, 24 skipped; Tests: 807 passed, 16 skipped)

Lint

  • no errors

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • align teams gRPC client imports/types to the latest buf-generated schemas and update list response typing
  • add @grpc/grpc-js dependency for the proto-generated gRPC helpers
  • update teams gRPC client test fixtures for new paginated list shape

Testing

  • pnpm --filter @agyn/platform-ui lint
  • pnpm --filter @agyn/platform-ui test (Test Files: 85 passed; Tests: 424 passed)
  • pnpm --filter @agyn/platform-ui build
  • pnpm --filter @agyn/platform-server lint
  • pnpm --filter @agyn/platform-server typecheck
  • LOG_LEVEL=error pnpm --filter @agyn/platform-server test -- --reporter=dot --silent (Test Files: 199 passed, 24 skipped; Tests: 807 passed, 16 skipped)

Lint

  • no errors

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • remove obsolete AgentsGraph Storybook story referencing deleted graph container
  • verify no remaining story imports reference removed graph components

Testing

  • pnpm --filter @agyn/platform-ui lint
  • pnpm --filter @agyn/platform-ui test (Test Files: 85 passed; Tests: 424 passed)
  • pnpm --filter @agyn/platform-ui build
  • pnpm --filter @agyn/platform-ui build-storybook

Lint

  • no errors

@rowan-stein
Copy link
Copy Markdown
Contributor

Requesting re-review after UI migration changes.

New commits since last approval:

  • Merged latest main (devspace config 5e194938)
  • feat(platform-ui): migrate entity CRUD — removed graph page, switched all entity CRUD to gateway REST API (/apiv2/team/v1/*)
  • fix(platform-server): align teams grpc types — fixed proto schema import names for CI
  • chore(storybook): drop removed graph story — removed stale AgentsGraph.stories.tsx

What changed in the UI:

  • Removed /agents/graph route, AgentsGraphContainer, graph canvas components, graph-page-only hooks
  • Removed "Open graph" button from AgentsListPage, "Team" sidebar link
  • Created new gateway API client (teamApi.ts) + TanStack Query hooks for all 6 resource types
  • Rewrote EntityListPage, EntityUpsertPage, EntityUpsertForm to use gateway REST API
  • Relations now managed via /apiv2/team/v1/attachments (AttachmentKind enum)
  • Triggers kept on existing platform-server graph API
  • Deleted graphEntities.ts, useGraphEntities.ts, graph mappers
  • Removed stale Storybook story

CI: All 7 checks green (Lint, Test Server, Test UI, Storybook, Build UI, Build Server, LiteLLM Integration).

Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Re-review: UI Migration Commits

The server-side proto type renames (commit 97bceb8) are clean — straightforward CreateXRequest/CreateXResponseXCreateRequest/X alignment.

The graph page removal, storybook cleanup, and route changes are also clean.

However, the new UI API client and entity mapper code (teamApi.ts, teamEntities.ts, useTeamEntities.ts, team.ts types) has systemic boundary/internal confusion that needs to be addressed before merge:

Core Issue: "Try Everything" Compatibility Pattern

The code consistently guesses at the API contract rather than implementing against a known one:

  • Sends both camelCase AND snake_case keys in the same request body
  • Probes multiple field name variants when reading responses
  • Sends all possible pagination parameter names (pageSize, page_size, per_page)
  • Casts typed objects to Record<string, unknown> to access undeclared fields

This is a hallmark of AI-generated code that hedges against an unknown API — but the gateway is your service with a known contract.

Structural Issues

  1. Types are maximally loose — all entity fields optional, enum unions widened with | string | number
  2. Normalization logic belongs at the boundary, not in feature code — 200+ lines of enum/field normalization are embedded in teamEntities.ts instead of in teamApi.ts
  3. No unit tests for the 1105-line mapper module
  4. Duplicate utilitiesisRecord/isPlainRecord duplicated within the same file, and isRecord/readString/readNumber duplicated across files

Prior Unresolved Items (from last review)

The two minor items from the previous review remain unresolved:

  • OutOfRange still missing from grpcStatusToErrorCode
  • normalizeBaseUrl still duplicated between runner and teams clients

These are non-blocking but should be tracked.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary:

  • aligned team UI API parsing/builders with the camelCase contract, strict enums, and required entity fields
  • updated attachments/list fixtures and added teamEntities unit tests for mapping, requests, diffs, and config sanitization
  • introduced shared type guards used by team API/entity parsing

Tests:

  • pnpm --filter @agyn/platform-ui lint (pass)
  • pnpm --filter @agyn/platform-ui test (passed: 429, failed: 0, skipped: 0)
  • pnpm --filter @agyn/platform-ui typecheck (pass)

noa-lucent
noa-lucent previously approved these changes Mar 13, 2026
Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All 11 prior review comments verified as resolved in the actual code. Clean work.

What changed:

  • Boundary layer (teamApi.ts): Single naming convention, throws on unexpected shapes, typed request interfaces, enum validation via Set-based guards. This is exactly how a boundary should work.
  • Types (team.ts): id/createdAt/updatedAt required on response entities. Strict enum unions with no | string | number widening. Separate request types.
  • Feature code (teamEntities.ts): Direct camelCase property access—no multi-key probing. Enum normalizers removed (handled at boundary). File dropped from 1105 to 860 lines.
  • Hooks (useTeamEntities.ts): createAttachment sends only { kind, sourceId, targetId }. No more Record<string, unknown> casts or snake_case probing.
  • Shared utilities: isRecord/readString/readNumber extracted to src/utils/typeGuards.ts.
  • Tests: New teamEntities.test.ts covering mappers, request builders, attachment diffing, and config sanitization.

The two minor items from the earlier server-side review (OutOfRange in grpcStatusToErrorCode, normalizeBaseUrl duplication) are still unresolved but non-blocking for this PR. Recommend tracking separately.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary:

  • merged origin/main into noa/issue-1379 and resolved the config.service.fromEnv.test.ts conflict

Tests:

  • pnpm --filter @agyn/platform-ui lint (pass)
  • pnpm --filter @agyn/platform-ui test (passed: 429, failed: 0, skipped: 0)
  • pnpm --filter @agyn/platform-ui typecheck (pass)

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary:

  • merged origin/main into noa/issue-1379 (already up to date)

Tests:

  • pnpm --filter @agyn/platform-ui test (passed: 429, failed: 0, skipped: 0)
  • pnpm --filter @agyn/platform-ui lint (pass)
  • pnpm --filter @agyn/platform-ui typecheck (pass)

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary:

  • lowered team list default perPage to 100 to match gateway limits

Tests:

  • pnpm --filter @agyn/platform-ui test (passed: 429, failed: 0, skipped: 0)
  • pnpm --filter @agyn/platform-ui lint (pass)
  • pnpm --filter @agyn/platform-ui typecheck (pass)

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • Added Teams graph source + hybrid repository to merge Teams-managed nodes/edges with the filesystem graph, wiring TeamsModule into graph domain exports.
  • Updated AgentsPersistenceService to resolve agent descriptors via Teams gRPC and adjusted relevant tests to use Teams client stubs.

Testing

  • pnpm --filter @agyn/platform-server lint (no errors)
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server exec vitest run --reporter=json --outputFile=/tmp/vitest-platform-server.json
    • Passed: 851, Failed: 0, Skipped: 6

@rowan-stein
Copy link
Copy Markdown
Contributor

Ready for review — Teams Graph Runtime Integration

This commit adds the bridge between the Teams gRPC service and the graph runtime, fixing three runtime bugs introduced by the Teams migration:

  1. "(unknown agent)" on threadsresolveAgentDescriptors() now queries Teams directly
  2. Default system prompt fallback — Agent configs now flow from Teams service into graph nodes
  3. No tools loaded — Attachments are converted to graph edges wiring tools/MCP/memory to agents

New files

  • teamsGraph.source.ts — Fetches all entities + attachments from Teams gRPC, converts to PersistedGraphNode[] + PersistedGraphEdge[] with correct port wiring
  • hybridGraph.repository.ts — Implements GraphRepository by merging filesystem graph (triggers) with Teams graph (all managed entities)

Modified files

  • graph-domain.module.ts — DI wiring: imports TeamsModule, creates HybridGraphRepository
  • agents.persistence.service.ts — Injects TeamsGrpcClient, queries Teams for agent descriptors

CI: All 7 checks passing ✅

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • Aligned Teams graph ingestion and tests to use EntityMeta IDs for agents/tools/attachments.
  • Updated UI hooks/tests and GraphLayout expectations for MCP tool discovery without node-state persistence.
  • Refreshed API/UI/docs references for read-only Teams graph snapshots, variables, and discover-tools endpoint.

Testing

  • pnpm --filter @agyn/platform-server lint
  • pnpm --filter @agyn/platform-ui lint
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server test -- --reporter dot
  • pnpm --filter @agyn/platform-ui test -- --reporter dot
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm test

Test results (from full run):

  • @agyn/docker-runner: 4 passed, 0 failed
  • @agyn/platform-server: 785 passed, 12 skipped
  • @agyn/platform-ui: 461 passed, 0 failed

Lint: no errors

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • switch UI graph snapshot loading to Teams entities and remove full-graph save flow
  • update secrets and threads flows to use team agents/tools snapshots
  • refresh graph/secret/threads tests to align with Teams APIs

Tests

  • pnpm --filter @agyn/platform-ui lint
  • pnpm --filter @agyn/platform-ui test (458 passed)

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • update memory service docs test mocks for load-only graph repo

Tests

  • pnpm --filter @agyn/platform-ui lint
  • pnpm --filter @agyn/platform-ui test (458 passed)
  • pnpm --filter @agyn/platform-server lint
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server test -- --reporter dot (770 passed, 12 skipped)

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • Aligned Teams gRPC definitions/client request schema names with regenerated proto outputs.
  • Adjusted variable resolver request creation and workspace config limit parsing for string values.
  • Added a local picomatch type declaration to satisfy strict typecheck.

Test & Lint

  • pnpm --filter @agyn/platform-server typecheck
  • pnpm --filter @agyn/platform-server lint
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server test -- --reporter dot
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server test -- --reporter json --outputFile /tmp/vitest-platform-server.json

Tests: 784 passed, 0 failed, 6 skipped.
Lint: no errors.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary

  • removed unused state mapping when creating graph nodes from team entities.
  • adjusted MCP tools parsing to emit optional descriptions with proper typing.

Testing

  • pnpm --filter @agyn/platform-ui typecheck
  • pnpm --filter @agyn/platform-ui lint
  • pnpm --filter @agyn/platform-ui test (458 passed, 0 failed, 0 skipped)

@rowan-stein
Copy link
Copy Markdown
Contributor

Ready for Review

All 7 CI checks are passing. Summary of changes in this PR:

Server (platform-server)

  • FS graph removal: Deleted fsGraph.repository, hybridGraph.repository, graphSchema.validator, yaml.util, NodeStateService, GraphPersistController
  • SlackTrigger removal: Removed node, templates, module, and all 8 test files (SlackAdapter kept for send_slack_message)
  • GraphRepository simplified: Interface now has a single load(): Promise<PersistedGraph> method (no get, upsert, initIfNeeded)
  • TeamsGraphRepository: Load-only, delegates to TeamsGraphSource — no PrismaService dependency
  • GraphVariablesService → Teams gRPC: Variables CRUD now uses TeamsGrpcClient RPCs instead of local Prisma
  • Proto updated: Local proto synced with agynio/api (Variables RPCs + McpToolFilter), all imports aligned to Create*/Update* naming
  • VariablesController: REST endpoints backed by Teams gRPC
  • discover-tools endpoint: POST /api/graph/nodes/:nodeId/discover-tools
  • Config cleanup: Removed graphRepoPath, graphLockTimeoutMs
  • Type cleanup: Removed PersistedGraphUpsertRequest/Response, old graph variable/node-state Prisma models
  • Fixtures/tools deleted: __fixtures__/graph-migration/, tools/graph-ref-migrate/

UI (platform-ui)

  • Removed getFullGraph, saveFullGraph, putNodeState, getNodeState API calls
  • Graph loading now uses Teams snapshot service
  • Secrets hook updated to use Teams entities API
  • AgentsThreads page updated to use Teams agents list
  • Added discoverTools API support
  • All tests updated and passing (458 UI, 784 server)

noa-lucent
noa-lucent previously approved these changes Mar 15, 2026
Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Re-review: Full FS Graph Removal (commits e7941b1..3691491)

All prior review feedback (across 5 review rounds) is verified resolved in the code. The new commits since the last LGTM cleanly complete the refactor:

Issue Coverage (all 11 phases verified)

  • Proto + Client: Teams gRPC client with call helper, exhaustive error mapping, CANCELLED handling, unit tests ✓
  • GraphRepository replacement: TeamsGraphRepositoryTeamsGraphSource.load(), abstract class simplified to single load()
  • Consumer updates: liveGraph.manager.ts and memory.service.ts use load() (no get('main')) ✓
  • FS infrastructure deleted: fsGraph.repository.ts, hybridGraph.repository.ts, graphSchema.validator.ts, yaml.util.ts — all gone, zero stale references ✓
  • NodeStateService removed: deleted file, removed from module/controllers, MCP tool discovery is in-memory only ✓
  • GraphPersistController removed
  • Variables migrated to Teams RPCs: new VariablesController uses TEAMS_GRPC_CLIENT directly ✓
  • SlackTrigger removed: directory, module registration, template — all deleted ✓
  • Cleanup: config fields, types, fixtures, tools/graph-ref-migrate — all removed ✓
  • UI: clean boundary layer (teamApi.ts), strict types, typed request interfaces, shared typeGuards.ts, teamEntities.test.ts
  • Tests: FS graph tests deleted, stubs updated to load(), TeamsGraphSource/HybridGraphRepository/TeamsGrpcClient all tested ✓

Architecture

The two-zone architecture is properly maintained:

  • Boundary: teamApi.ts (UI), VariablesController, TeamsGraphSource — all validate/parse/normalize external data
  • Internal: LiveGraphRuntime, memory.service.ts, feature hooks — operate on canonical types only

Minor Items (non-blocking)

  1. proto/grpc.ts has ~250 lines of dead Teams definitions added by this PR (inline comment)
  2. variables.controller.ts:80 has unnecessary ?? [] on proto repeated field (inline comment)
  3. OutOfRange in grpcStatusToErrorCode and normalizeBaseUrl duplication — tracked from prior reviews, non-blocking

Clean refactor. LGTM.

TouchWorkloadRequestSchema,
TouchWorkloadResponseSchema,
} from './gen/agynio/api/runner/v1/runner_pb.js';
import {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[minor] This PR adds ~250 lines of Teams service gRPC definitions (teamsServiceGrpcDefinition, TeamsServiceGrpcClient, all TEAMS_SERVICE_*_PATH constants) to this file, but none of them are imported anywhere in the codebase.

The TeamsGrpcClient (in teamsGrpc.client.ts) uses @connectrpc/connect with createClient(TeamsService, ...) and derives paths via teamsServicePath() from the TeamsService descriptor — it never touches this file.

Additionally, the runner definitions in this file appear to be dead as well (since the runner client also migrated to @connectrpc/connect), but those are pre-existing.

Consider removing the Teams additions from this file. If the entire file is now unused, it could be deleted entirely as a cleanup.

});
const response = await this.teamsClient.listVariables(request);
return {
items: response.variables ?? [],
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[nit] response.variables is a proto repeated field — it always produces an array (defaults to [] in protobuf). The ?? [] fallback is unnecessary. Same for ?? undefined on nextPageToken (line 81) — proto string fields default to "", and the pagination utility's readString already handles empty strings.

items: response.variables,
nextPageToken: response.nextPageToken,

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Summary:

  • Removed unused graph builder UI components/hooks/tests, including the graph flows integration test.
  • Dropped GraphRepository/TeamsGraphRepository and wired LiveGraphRuntime/MemoryService/GraphDomainModule to TeamsGraphSource with updated test stubs.

Tests:

  • pnpm --filter @agyn/platform-ui typecheck
  • pnpm --filter @agyn/platform-ui lint
  • pnpm --filter @agyn/platform-ui test
    • Tests: 414 passed, 0 failed, 0 skipped
  • pnpm --filter @agyn/platform-server typecheck
  • pnpm --filter @agyn/platform-server lint
  • pnpm --filter @agyn/platform-server test
    • Tests: 104 passed, 0 failed, 3 skipped

Lint: no errors.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Test rerun:

  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server test -- --reporter dot
    • Tests: 104 passed, 0 failed, 0 skipped

Lint: not run (not requested).

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Storybook cleanup:

  • Removed stale GraphCanvas and EmptySelectionSidebar stories.

Tests/Lint:

  • pnpm --filter @agyn/platform-ui lint (no errors)
  • pnpm --filter @agyn/platform-ui test
    • Test Files: 78 passed
    • Tests: 414 passed
  • pnpm --filter @agyn/platform-ui build-storybook

@rowan-stein
Copy link
Copy Markdown
Contributor

Ready for Re-review

All 7 CI checks passing. New changes since last approval:

Graph screen dead code removal (UI)

  • Deleted GraphLayout.tsx, GraphCanvas.tsx, EmptySelectionSidebar.tsx, GradientEdge.tsx
  • Deleted components/graph/ directory (NodeDetailsPanel, NodeTracingSidebar)
  • Deleted dead hooks: useGraphData, useGraphSocket
  • Deleted sidebarNodeItems.ts
  • Deleted stale Storybook stories (GraphCanvas.stories.tsx, EmptySelectionSidebar.stories.tsx)

GraphRepository abstraction eliminated (Server)

  • Deleted graph.repository.ts and teamsGraph.repository.ts
  • LiveGraphRuntime and MemoryService now inject TeamsGraphSource directly
  • graph-domain.module.ts simplified — no more abstract/alias DI binding
  • All test mocks updated from GraphRepository to TeamsGraphSource

noa-lucent
noa-lucent previously approved these changes Mar 16, 2026
Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Re-review: 165c8d4 (prune builder UI and repos) + fe2998c (remove graph stories)

Clean continuation of the refactor. No new issues.

What changed

GraphRepository abstraction eliminated — The abstract class (graph.repository.ts) and its sole implementation (teamsGraph.repository.ts) are deleted. Consumers (LiveGraphRuntime, MemoryService) now inject TeamsGraphSource directly using the typed TeamsGraphSnapshot return type. The unnecessary PersistedGraph envelope (with name, version, updatedAt) is gone — correct, since those fields were synthetic fillers in the Teams path.

Graph builder UI removed (~4900 lines)GraphLayout, GraphCanvas, EmptySelectionSidebar, NodeActionButtons, NodeDetailsPanel, NodeStatusBadges, NodeTracingSidebar, useGraphData, useGraphSocket, sidebarNodeItems, plus all associated tests and stories. Zero orphaned references remain. Surviving hooks (useNodeAction, useNodeStatus, useNodeTitleMap) and their tests correctly stay since they're still imported by live entity components.

8 test files updated — All GraphRepository stubs replaced with new TeamsGraphSource(createTeamsClientStub()) + vi.spyOn(...).mockResolvedValue(). Consistent pattern across all tests. The old StubRepo extends GraphRepository classes (with fake name, version, updatedAt fields) are gone.

DI wiringgraph-domain.module.ts exports TeamsGraphSource directly instead of through the GraphRepositoryTeamsGraphRepositoryTeamsGraphSource chain. Clean.

Prior unresolved threads (non-blocking)

Two [minor]/[nit] items from the previous review remain unaddressed:

  1. Dead Teams gRPC definitions in proto/grpc.ts
  2. Unnecessary ?? [] on proto repeated field in variables.controller.ts:80

Neither blocks merge.

LGTM.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Removed the graph_state_tables migration directory.

Tests/Lint:

  • pnpm --filter @agyn/platform-server lint (no errors)
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server exec vitest run --reporter=json --outputFile=/tmp/vitest-platform-server.json
    • Tests: 770 passed, 0 failed, 12 skipped

noa-lucent
noa-lucent previously approved these changes Mar 16, 2026
Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Re-review: 2d5f692 (remove graph state migration)

Correct removal of a bogus migration (20251222120000_graph_state_tables) that would have created GraphVariable and GraphNodeState tables with no corresponding Prisma models.

Verified:

  • No GraphVariable/GraphNodeState models in schema.prisma
  • Zero references to either table in source code
  • No downstream migration depends on these tables
  • Migration timestamp places it after all other applied migrations — confirms it was introduced in this branch and never deployed

Clean. LGTM.

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Merged main into noa/issue-1379 and resolved conflicts (kept proto:generate update, grpc-js bump, restored Teams env, added node_state emission).

Tests/Lint:

  • pnpm --filter @agyn/platform-server lint (no errors)
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test pnpm --filter @agyn/platform-server exec prisma migrate deploy
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server exec vitest run --reporter=json --outputFile=/tmp/vitest-platform-server-merge.json
    • Tests: 771 passed, 0 failed, 12 skipped

@casey-brooks
Copy link
Copy Markdown
Contributor Author

Updated pnpm-lock.yaml via pnpm install to reflect grpc-js bump.

Tests/Lint:

  • pnpm --filter @agyn/platform-server lint (no errors)
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test pnpm --filter @agyn/platform-server exec prisma migrate deploy
  • AGENTS_DATABASE_URL=postgresql://postgres:postgres@localhost:5432/agents_test RUN_DB_TESTS=true pnpm --filter @agyn/platform-server exec vitest run --reporter=json --outputFile=/tmp/vitest-platform-server-lockfile.json
    • Tests: 771 passed, 0 failed, 12 skipped

Copy link
Copy Markdown
Contributor

@noa-lucent noa-lucent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Re-review: merge from main (c73aa71) + lockfile sync (cd71d43)

Verified the merge brought in two already-reviewed PRs from main:

  • #1372 — notifications gRPC publisher (new NotificationsModule, NotificationsPublisher injection into GraphSocketGateway, emitNodeState, NodeStateEventSchema)
  • #1399 — docker-runner removal

No conflicts with PR #1381 code. The gateway changes are orthogonal — this PR removed graph-persist/snapshot events; the notifications PR adds a parallel gRPC notification channel. Config, module wiring, and test stubs all merge cleanly.

The lockfile commit is a single-line pnpm-lock.yaml change.

No functional changes to PR-specific code. LGTM.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Update platform-server to use Teams gRPC service

3 participants