Appearance
Handoff: SVC-005-student-roster-import-boundary organization-service student roster import boundary
Scope
- Service/area:
organization-serviceimplemented byservices/school-service - Task pack:
docs/agents/service-tasks/organization-service.md - Goal: accept the bounded
SVC-005student roster import boundary slice, keeping school-service ownership to organization/unit metadata and IAM-synchronized membership read models while student roster import remains a cross-service IAM/profile/classroom handoff. - Non-goals: default
/api/organizations*route promotion, live/browser proof, IAM membership write implementation inside school-service, student-import public cutover, data migration/backfill, or changes to legacy source under/Users/velikho/Desktop/WORKING/HOCTAPAZ/.
Docs Read
go-platform/docs/architecture/service-responsibility-matrix.mdgo-platform/docs/architecture/legacy-api-map.mdgo-platform/docs/agents/service-agent-execution-queue.jsongo-platform/docs/agents/service-agent-closeout-ledger.jsongo-platform/docs/agents/service-tasks/organization-service.mdgo-platform/docs/agents/agent-handoff-format.mdgo-platform/docs/api/school-service.mdgo-platform/docs/qa/service-agent-goal-completion-audit.mdgo-platform/docs/qa/service-agent-readiness-smoke.md
Legacy Evidence Read
/Users/velikho/Desktop/WORKING/HOCTAPAZ/node-platform/apps/api/src/modules/organizations/organizations.controller.ts/Users/velikho/Desktop/WORKING/HOCTAPAZ/node-platform/apps/api/src/modules/organizations/**/Users/velikho/Desktop/WORKING/HOCTAPAZ/node-platform/apps/api/src/modules/app-data/app-data.organizations.ts/Users/velikho/Desktop/WORKING/HOCTAPAZ/node-platform/apps/api/src/modules/app-data/app-data.student-imports.ts/Users/velikho/Desktop/WORKING/HOCTAPAZ/node-platform/apps/api/src/modules/tenant/**/Users/velikho/Desktop/WORKING/HOCTAPAZ/node-platform/apps/api/prisma/schema.prisma- Legacy source was read-only evidence only; no student-import or organization-member public route parity is claimed.
Files Changed
go-platform/docs/agents/handoffs/SVC-005-student-roster-import-boundary.mdgo-platform/docs/agents/service-agent-closeout-ledger.jsongo-platform/docs/agents/service-agent-closeout-ledger.mdgo-platform/contracts/events/README.mdgo-platform/docs/qa/organization-iam-membership-school-sync-proof.mdgo-platform/services/school-service/internal/http/server.gogo-platform/services/school-service/internal/http/server_test.gogo-platform/services/school-service/internal/http/iam_membership_boundary_test.gogo-platform/services/iam-service/internal/http/server.gogo-platform/services/iam-service/internal/schoolsync/client.gogo-platform/services/iam-service/internal/schoolsync/client_test.gogo-platform/contracts/openapi/services/school-service.yamlgo-platform/services/school-service/api/openapi.yaml
Behavior Implemented
student.roster.import.requested.v1now defines the cross-service handoff keys and owner sequence without adding a public route or changing school-service write authority.- IAM resolves/creates the account and canonical organization membership; profile-service owns student display fields; classroom-service owns local classroom membership; school-service remains an IAM membership read model.
- Stable
importJobId,rowId, andsourceEventIdvalues provide replay protection, while accepted/rejected row reporting keeps partial retries from duplicating owner mutations. - School-service membership sync now requires the IAM marker plus trusted
X-Internal-Service: iam-serviceandX-Internal-Token; marker-only and spoofed-token requests are rejected. - IAM school-sync publisher forwards the trusted internal headers and uses the shared token configured for the runtime.
- Configured school-service database failures no longer silently fall back to memory outside local/test environments; readiness checks the live pool.
- Existing audited school-service code returns
SCHOOL_MEMBERSHIP_NOT_AUTHORITATIVEfor ordinary member writes and supports IAM sync ordering/tombstone replay behavior for read-model updates. - Existing audited organization route tables keep read rehearsals non-default and route membership write rehearsals to IAM, not school-service.
Tests And Verification
- Command:
GOTOOLCHAIN=go1.25.11 go test ./services/school-service/... -count=1 - Result: passed.
- Evidence: school-service packages passed, including HTTP/usecase tests for ordinary member write rejection, IAM sync writes, stale replay/tombstone handling, and last-owner IAM removal.
- Command:
make test-organization-routes - Result: passed.
- Evidence: default route table kept broad
/api/organizationslegacy; non-default read routes target school-service; non-default membership write routes target IAM. - Contract verification:
contracts/events/README.mdcontains the required roster event name, owner sequence, stable replay keys, and legacy-route boundary. - Command:
GOTOOLCHAIN=go1.25.11 go test ./services/school-service/... ./services/iam-service/internal/schoolsync -count=1 - Result: passed, including spoofed sync-marker rejection and IAM publisher internal-header forwarding.
Route State
- Legacy route: default
/api/organizations*remains legacy-proxied, and student roster import remains legacy-proxied. - Native route: non-default read examples route exact organization list/detail/units/members reads to school-service; membership write examples route member POST/DELETE operations to IAM.
- Gateway state:
make test-organization-routesverifies default legacy state, route order, auth/organization guards, and IAM target for membership writes. - Rollback: keep
deploy/gateway/routes.jsonas the active route table; do not promote organization member writes or student roster imports until IAM-owned account/membership writes, profile hydration, classroom membership handoff, browser/runtime proof, and rollback evidence are attached.
Data Notes
- Tables touched: none in this handoff run; verification used package tests and route-table guards.
- Migration run: none.
- Validation report: not applicable because no live data was migrated or backfilled.
Risks / Blockers
- SVC-003 IAM dependency remains open, so SVC-005 cannot be complete.
- Student roster import crosses IAM account/membership writes, profile hydration, and classroom membership; those owner contracts are not implemented by this handoff.
- The boundary contract is defined, but the native coordinator/owner adapters and their live/browser/rollback evidence are still not implemented.
- No default route promotion, live/browser proof, rollback proof, or data validation exists for organization member writes or student roster imports.
- School-service must not become the permission-bearing organization membership owner.
Next Step
- Implement the coordinator and owner adapters behind a non-default rehearsal, then add live/browser/rollback proof before considering student-import route promotion.