# Backend Agent Guidelines These instructions extend the repository-wide rules in the root `AGENTS.md` and apply whenever a task adds or modifies backend code, including Go and protobuf files under `backend/`. Before completing the task, review the entire backend diff produced by the current task, fix every in-scope issue found, and then perform the required validation. Use the [`$review-backend-change`](../.agents/skills/review-backend-change/SKILL.md) skill to perform this completion workflow. ## Reuse existing definitions - Search the repository before introducing a protobuf message, enum, Go struct, interface, or shared domain type. - Reuse or extend the canonical existing definition when its semantics match. Do not create parallel representations or conversion layers for the same concept without a clear architectural reason. - Avoid naming stutter in packages, types, fields, parameters, and access paths. Each nested name should add meaning instead of repeating its parent context. For example, prefer a concise path such as `payment.Details.ID` over `payment.Payment.PaymentID`. ## Reuse shared database and messaging infrastructure - All database integrations must use the existing shared database wrappers in `backend/shared/database`. Do not bypass them with direct database clients or create feature-local replacements. - All NATS connections must use shared messaging drivers owned by the `backend/shared` library module. Keep reusable NATS drivers in `backend/shared/messaging`; executable modules must consume that package. Do not open direct NATS connections or implement separate connection management in a feature or service. - If the shared messaging package is missing, consolidate the existing driver into `backend/shared/messaging` and reuse it. Do not create another feature-local driver or import a sibling executable module's infrastructure. - Search for the existing wrappers, drivers, and their usage before implementing an integration. Reuse their connection lifecycle, configuration, retries, and other infrastructure behavior instead of copying or rewriting it. - If an integration needs a capability the shared infrastructure does not yet expose, extend the canonical wrapper or driver. Keep reusable infrastructure there and domain-specific behavior in the owning module. - During review, check that database and NATS integrations use these shared paths and remove any duplicated infrastructure introduced by the task. ## Use the project error model - Do not introduce `fmt.Errorf` or `errors.New`. Use the constructors and wrapping helpers in `backend/shared/errors`. - Preserve the underlying cause when adding context by using an appropriate `merrors` wrapping helper. - When no suitable project error exists, add the smallest generally useful definition or helper to `backend/shared/errors` instead of creating an ad hoc error elsewhere. ## Keep modules cohesive and names concise - Review touched files for excessive size, mixed responsibilities, duplicated logic, and poor separation of concerns. - Refactor oversized contributions into focused, cohesive files or packages. Do not split code mechanically; organize it along clear domain or architectural boundaries. - Avoid repeating directory or package context in child directory and file names. For example, prefer `payment/widget.dart` over `payment/payment_widget.dart`. ## Review implementation quality - Review the current task's backend contribution for correctness, readability, maintainability, testability, and consistency with the surrounding architecture. - Keep public APIs and module boundaries small and intentional. Remove unnecessary indirection, duplication, dead code, and speculative abstractions. - Add or update tests for changed behavior, edge cases, and failure paths. - Fix all findings caused by the current task before reporting completion. ## Review logging - Ensure the contribution has sufficient structured logging at meaningful operational and domain boundaries. Include useful identifiers and context, but never log credentials, secrets, or sensitive payment data. - Follow the repository's logging style and use levels consistently: - `Debug`: fine-grained runtime execution tracking useful during debugging. - `Info`: important payment-domain events, module-boundary operations, effective module configuration, and noteworthy but expected deviations from the usual path. - `Warn`: runtime errors and unexpected conditions from which the service can continue or which are returned to a caller. - `Error`: unrecoverable failures that cause, or imminently lead to, service or component termination. - Avoid logging the same error repeatedly at multiple layers. Log it where the layer has enough context to make the event actionable. ## Required validation - From the repository root, run `make test` and `make lint-backend`, plus every applicable command from the root `AGENTS.md` change-scoped security requirements, after all review fixes are complete. - All commands must succeed before the task is reported as complete. Fix failures introduced by the current task; do not silently skip, suppress, or weaken checks. - Report the commands run and their outcomes in the final response. If an external or environmental blocker prevents a command from running, report the exact command, failure, and blocker explicitly; do not claim successful validation. ## SXCHNGE provider boundary SXCHNGE owns auth, sessions and customer management. SXCHNGE is one organization inside Sendico. This organization reference belongs only in the public provider adapter configuration. Local customers have no organizations, tenant IDs, membership, roles or policy engine. Do not copy platform scaffolding to satisfy unused dependencies; remove those dependencies from the selected components. Copied BFF components are locally owned and may diverge. Use only Sendico's public HTTP API for platform operations. Never import sibling Sendico modules or access its database, internal gRPC APIs, discovery or message bus. Keep consumed public wire contracts inside the owning adapter, separate from local DTOs and models. Do not copy unused API snapshots. Resolve the configured provider organization and customer resource ownership on the server. Never treat all customers as the backend integration principal. Use the copied structured logger, injected at operational boundaries. ## Go module structure `backend/` groups independent Go modules; it is not itself a Go module. `product/` is the customer-facing executable and owns its `main.go` and `go.mod`. `shared/` is a library module for reusable infrastructure and has no entry point. Backoffice belongs in its own executable module (`backoffice/`) when implemented, with its own entry point and configuration, not inside the product executable. Keep feature models, storage, services and transport together inside their owning module. Shared infrastructure must not import a product or backoffice module.