@evalops/proto
v0.1.1
Published
Generated TypeScript protobuf types and Connect descriptors from the EvalOps platform monorepo
Readme
Platform
platform is the EvalOps control-plane monorepo.
It combines three previously separate surfaces:
- shared protobuf contracts from
evalops/proto - shared runtime code from
evalops/service-runtime - service implementations under one Go module
The repo now owns the public contract surface, the shared runtime, service entrypoints, service internals, DB migrations, build assets, generated SDKs, and release automation in one place.
Quick Start
Recommended local baseline:
- Go
1.26.1via thego 1.26.0/toolchain go1.26.1root module - Node
20 - Python
3.12 bufjq- Docker for container-backed integration tests
ghfor workflow and release inspectionkoonly when publishing or smoke-testing images locally
Common commands:
make proto-lint
make runtime-lint
make event-types-check
make generate
make test
make test TEST_FLAGS="-short -race"
make test TEST_FLAGS="-race -p 2"
make ko-base-image-check
make upstream-drift
make build SERVICE=identity
make test SERVICE=identity
make go-lint SERVICE=identity
make ko-install
make image SERVICE=keys IMAGE_REPO=ghcr.io/evalops/platform/keys
make hook-archives HOOK_VERSION=v0.1.36What Lives Here
Repo layout:
proto/: public cross-service protobuf contractsgen/: generated Go, TypeScript, and Python code for the public contractspkg/: shared runtime packages plus runtime-private generated proto outputcmd/: service and helper entrypointsinternal/: service implementation packagesdb/: namespaced SQL migrationsbuild/: charts, configs, scripts, compose files, and other non-image assetsopenapi/: service OpenAPI documents that are still checked in separatelydocs/services/: per-service docs migrated from standalone reposapps/: service-owned UIs that intentionally remain outside the root packagesdk/: service-owned SDKs that are not part of the root TypeScript package
Monorepo decisions that matter to contributors:
- The repo is a single Go module:
github.com/evalops/platform. - Public contract generation remains committed under
gen/go,gen/ts, andgen/python. - Runtime-private proto generation remains under
pkg/gen/proto/go. - Pure-Go images publish with root
koconfig instead of per-service Dockerfiles. - Services that need REST compatibility should prefer
google.api.httpannotations plus the shared Vanguard wrapper over duplicate handwritten REST route trees. - Cross-service analytics APIs should use
common.v1.TimeRange,common.v1.Money,common.v1.InsightSource, andcommon.v1.EvidenceRefrather than defining local period, currency, source, or evidence messages. gatestill uses a CGO-capablekoprofile because it ships checked-in configs and policies viakodata.- Standalone service repositories are archived; service source of truth is the monorepo service layout.
- HTTP services should use
startup.NotifyContext,startup.Lifecycle, andstartup.RunHTTPServerinstead of bespoke signal/shutdown goroutines. - Long-lived HTTP service commands have been standardized on that startup flow; worker, migrator, benchmark, and similar non-HTTP or one-shot commands are expected to keep command-specific lifecycle handling.
Services
Imported services currently include:
agent-mcpapprovalssecret-brokerattributionauditcomplianceconnectorsentitiesgategovernanceidentitykeysllm-gatewaymemorymeternotificationsobjectiveshrispipelinepromptsagent-registryingestskillstraces
There are also repo-level helper commands that are not published as normal
service images, including agent-hook, gate-benchmark,
gate-policy, dev-token, and hris-seed.
For the full service catalog, command mapping, extra docs, OpenAPI files, frontend surfaces, and publish status, see docs/services/README.md.
CI And Release Automation
The repo currently runs these top-level workflows:
CI: proto/runtime lint, proto breaking checks on pull requests, code generation freshness, descriptions coverage,go vet, a rootgolangci-lintratchet for new issues, Go tests, TypeScript package checks, Python package checks, and disposable-Postgres migration validation.generateis an independent freshness gate; the test and packaging jobs do not wait on itPublish Images: selectivekopublishing to GHCR based on changed paths with thekoversion sourced from the rootMakefileandpackages: writescoped to the publish job only. Published image digests are signed with keyless cosign, and SPDX SBOMs are uploaded as workflow artifacts.CodeQL: static analysis for Go, JavaScript/TypeScript, and Python on PRs, pushes tomain, manual dispatch, and a weekly scheduleko-base-image-drift: verifies the pinned Chainguard base image digests in.ko.yamlon PRs touching that file, on pushes, and on a weekly scheduleSDK Publish: verifies generated Go, TypeScript, and Python SDKs when public proto or generated files change onmain. Manual releases publish@evalops/sdk-ts,@evalops/proto, andevalops-sdkwhen registry gates are enabled;gen/ts/v*tags publish@evalops/protofrom the root package so downstream TypeScript consumers can install the generated protobuf surface directly. The Go job tags thegithub.com/evalops/platform/gen/gosubmodule.agent-hook: builds cross-platform hook archives and attaches them to tag-based releasesworkflow-security-guardrails: validates workflow permissions and SHA pinningactionlint: workflow syntax and style lintingDependabot: weekly updates for Go modules, GitHub Actions, npm, and pip, plus monthly Docker updates
Current test policy:
- Pull requests run
go test -short -race ./... - Pushes to
mainrungo test -race -p 2 ./... - Generated code freshness is enforced in CI for both
gen/andpkg/gen/
See docs/testing-ci.md for the exact local parity commands and the environment variables used by integration tests.
Generated Contracts And Runtime
Public contracts and code generation are owned at the repo root. Runtime-private
protobufs remain under pkg/.
Important points:
buf.yamlandpkg/buf.yamlboth useWIRE_JSONbreaking checks.- Generated code is intentionally committed and marked as generated in GitHub
diffs via
.gitattributes. descriptions.yamlis checked against the public proto surface in CI.proto/common/v1/analytics.protoprovides shared analytics primitives used by attribution P&L now and intended for governance policy synthesis and production-to-eval generation next.proto/events/v1/event_types.yamlcatalogs allowed CloudEventtypevalues and expectedAnypayload messages using a proto-shaped YAML schema, and CI validates that catalog against the checked-in event fixtures.- The root package publishes
@evalops/protofromgen/distfor downstream TypeScript consumers that need the canonical generated protobuf surface (npm i @evalops/[email protected]). - The
gen/tspackage publishes the generated@evalops/sdk-tsTypeScript contract surface. - The
gen/pythonpackage publishesevalops-sdkfrom the committed generated Python modules. - The Go SDK is a submodule under
gen/gowith module pathgithub.com/evalops/platform/gen/go.
See docs/contracts-and-codegen.md for the exact edit/regenerate workflow.
Development Docs
Start here depending on task:
- CONTRIBUTING.md: contributor entry point
- docs/README.md: docs index
- docs/development.md: local setup, layout, and common workflows
- docs/testing-ci.md: local validation and CI parity
- docs/contracts-and-codegen.md: proto, generation, and packaging workflow
- docs/services/README.md: service inventory and docs map
- docs/monorepo-transition.md: migration status, archived upstream ledger, and history lookup
- pkg/README.md: shared runtime package reference
Transition Notes
The service-repo crossover window is closed. Standalone service repositories
are archived, _import/ mirrors have been removed, and service development now
happens directly in this monorepo. The only upstream sync helpers that remain
are for shared proto and service-runtime history.
Shared repos:
make upstream-driftmake sync-protomake sync-runtime
Merge proto and runtime sync PRs with merge commits rather than squash
merges so the upstream parent remains in history and drift checks stay accurate.
The final service archive evidence lives in docs/services/upstream-archive.md.
Imported History
Relocated service files may still show the monorepo import commit in some blame views.
Configure local blame once so Git skips relocation noise where possible:
git config blame.ignoreRevsFile .git-blame-ignore-revsWhen you need the original standalone-repo history, inspect the second parent
of the matching import <service> history subtree merge:
merge_commit=$(git log --merges --grep='import identity history' --format=%H -n 1)
git log "${merge_commit}^2" -- internal/organizations/service.goThe general path-mapping guidance is documented in docs/monorepo-transition.md.
