Skip to content

Sirloin API

The contract surface of sirloin. For service overview see Sirloin. For generated proto reference see proto-api.

Surface Map

Sirloin exposes four gRPC services and a small set of HTTP endpoints (health, webhooks, MCP). The single Go process listens on three ports:

PortPurposeSource
50051gRPC + gRPC-Web (h2c)apps/sirloin/cmd/app/main.go (grpcHTTPServer)
8087Webhook intake (HTTP)apps/sirloin/cmd/app/main.go (webhookHTTPServer)
8086MCP / Foxy360 (HTTP)apps/sirloin/cmd/app/main.go (mcpHTTPServer)

Defaults: container ports per docker-compose.yml (sirloin service). Default SIRLOIN_PORT=:50051 per apps/sirloin/internal/app/config/config.go.

gRPC Services

Proto contracts live under proto/sirloin/v5/. Generated stubs are checked into apps/sirloin/internal/pkg/pb/. RPC list below is summarised; for full request/response shapes refer to the proto files and the generated docs at proto-api.

SirloinService (proto/sirloin/v5/sirloin.proto)

End-user surface: characters, media, profile, KYC. Consumed by brisket over gRPC-Web. Selected RPCs (28 total):

  • CreateCharacter, UpdateCharacter, ListCharacters, DeleteCharacter
  • GetCharacterReferenceImageUploadURL, GetCharacterReferenceDatasetUploadURLs
  • VerifyCharacterReferenceDatasetImage, DeleteCharacterReferenceDatasetImage
  • UpdateCharacterReferenceDataset, TriggerCharacterReferenceImageUploaded
  • GenerateMedia, ListMedia, ToggleMediaFavorite, ToggleMediaArchived, SetMediaDownloaded, ListMediaTags, ListMediaExamples
  • GetUserProfile, UpdateUserProfile, RequestWelcomePics, SubmitFeedback
  • GetInstagramProfile, StartKYCVerification

BillingService (proto/sirloin/v5/billing.proto)

Billing surface: subscriptions, payments, products, coupons. Consumed by brisket and strip. Selected RPCs:

  • GetCurrentUsage, ListProducts, GetWorkflowPricing
  • CreatePrimerCheckout, SubmitPaidInvoice, GetPayment, GetTransactions
  • GetSubscriptionDetails, CancelSubscription, ReactivateSubscription, CancelScheduledDowngrade, ProvideCancellationBenefit
  • RetryDunningPayment, ValidateCoupon, SetReferralCode
  • GetPaymentMethods, AddPaymentMethod, DeletePaymentMethod, SetPrimaryPaymentMethod, CreateVaultingSession
  • UpdateBillingAddress, UpdateNextBillingDateForTesting (test-only)

Behaviour notes (deferred activation, polling, invariants) are described in apps/sirloin/internal/app/services/billing/BILLING.md and the billing runbook.

StripService (proto/sirloin/v5/strip.proto)

Admin surface consumed exclusively by strip (SSR admin). Auth via short-lived admin Clerk token (see auth-model). Selected RPCs:

  • StripListUsers, StripUpdateUser
  • StripListCharacters, StripCreateCharacter, StripUpdateCharacter, StripDeleteCharacter, StripBypassCharacterOnboardingChecks
  • StripListMedia, StripFailMedia, StripListDatasetImages
  • StripListPopularExamples, StripListPopularCategories
  • StripLogAudit, StripListAuditLogs, StripGetAuditLog

FlankStorageService — removed

Under T-Bone the workflow engine and storage moved into brain, which owns workflows, subworkflows, adapters, secrets, and executions over an HTTP API. The sirloin-hosted FlankStorageService (workflow/adapter/secret/execution CRUD in proto/sirloin/v5/flank.proto), the FlankMCP route, and the flank DB tables have been deleted. Flank is now only the visual workflow editor and reads/writes brain directly.

The workflow-facing RPCs that survive are brain-backed and live on the main protos: ListGenerationCatalog (proto/sirloin/v5/sirloin.proto) and GetWorkflowPricing (proto/sirloin/v5/billing.proto).

gRPC Health

grpc.health.v1.Health implemented in apps/sirloin/internal/app/services/health.go. Used by the container healthcheck (/bin/grpc_health_probe -addr=:50051).

REST Endpoints

Sirloin’s HTTP surface is intentionally narrow. Routes registered in apps/sirloin/cmd/app/main.go against webhookMux, grpcHTTPMux, and mcpMux.

MethodPathServerAuthSource
GET/healthgRPC HTTP (50051)noneinternal/app/services/health.go
POST/webhooks/chargebee/eventswebhooks (8087)HTTP Basic (SIRLOIN_CHARGEBEE_WEBHOOK_USERNAME / _PASSWORD)internal/app/services/billing/webhooks/chargebeewebhook.go
POST/webhooks/primer/disputeswebhooks (8087)HMAC over SIRLOIN_PRIMER_WEBHOOK_SECRETinternal/app/services/billing/disputes/primerwebhook.go
POST/webhooks/primer/paymentswebhooks (8087)HMAC over SIRLOIN_PRIMER_WEBHOOK_SECRETinternal/app/services/billing/webhooks/ (NewPrimerPaymentsWebhookHandler)
POST/webhooks/ondato/verification-statuswebhooks (8087)shared secret SIRLOIN_ONDATO_WEBHOOK_SECRETinternal/app/services/characters/ondato_webhook.go
ANY${SIRLOIN_FOXY360_BASE_PATH}/*MCP (8086)Clerk (SIRLOIN_FOXY360_CLERK_API_KEY) via OAuth proxyinternal/app/foxy360/, internal/app/mcpoauth/

grpcHTTPMux falls back to a 404 for everything except /health and the gRPC + gRPC-Web protocol routes (apps/sirloin/cmd/app/main.go).

Webhooks Received

Chargebee Events

  • Path: POST /webhooks/chargebee/events on port 8087
  • Auth: HTTP Basic with SIRLOIN_CHARGEBEE_WEBHOOK_USERNAME / SIRLOIN_CHARGEBEE_WEBHOOK_PASSWORD. Missing creds → all webhooks rejected (config.go warns at startup).
  • Payload: Chargebee event JSON (event_type, content).
  • Behaviour: webhook is a fallback; sirloin’s own poller (every 15s, see internal/app/services/billing/events/poller.go) is the authoritative ingest path.

Primer Disputes

  • Path: POST /webhooks/primer/disputes on port 8087
  • Auth: HMAC verified with SIRLOIN_PRIMER_WEBHOOK_SECRET. 3-minute clock skew window (primer.WebhookSignedAtWithinSkew).
  • Body limit: 1 MiB (maxPrimerWebhookBodyBytes).

Primer Payments

  • Path: POST /webhooks/primer/payments on port 8087
  • Auth: same HMAC scheme as disputes.
  • Behaviour: feeds the unified payment processor (internal/app/services/billing/payments/processor.go).

Ondato KYC

  • Path: POST /webhooks/ondato/verification-status on port 8087
  • Auth: shared secret SIRLOIN_ONDATO_WEBHOOK_SECRET.

Examples

Terminal window
# health probe
curl -fsS http://localhost:50051/health
# gRPC reflection (dev only — sirloin docker-compose ships grpcui on :8820 too)
grpcurl -plaintext localhost:50051 list
grpcurl -plaintext localhost:50051 sirloin.v5.BillingService/ListProducts

Versioning

Proto package is pinned at sirloin.v5. Backwards-incompatible changes require a new package version; field deprecation follows documentation standard and auth-model for auth changes. TODO(@zen): no formal deprecation policy doc exists yet — confirm or add ADR.

TODO(@zen)

  • TODO(@zen): is there a documented sirloin.v5 deprecation policy beyond proto file conventions?
  • Foxy360 MCP routes are internal-only. The ${SIRLOIN_FOXY360_BASE_PATH}/* surface is gated by Clerk verification (SIRLOIN_FOXY360_CLERK_API_KEY) through an OAuth proxy and exposes admin/analytics tooling. Source: apps/sirloin/internal/app/foxy360/server.go:1 and registration in apps/sirloin/cmd/app/main.go (mcpHTTPServer).
  • Primer payments webhook uses the same 1 MiB body cap as disputes. maxPrimerPaymentBodyBytes = 1 * 1024 * 1024 in apps/sirloin/internal/app/services/billing/webhooks/primerpaymentwebhook.go:22, matching maxPrimerWebhookBodyBytes in apps/sirloin/internal/app/services/billing/disputes/primerwebhook.go:26.