# First of all

If there is an AGENTS-local.md，refer to it. Follow AGENTS-local.md if it conflicts with AGENTS.md.

# Repository Guidelines

## Project Structure & Module Organization
- `src/` hosts the `tici-server` binary and core modules (`meta/`, `worker/`, `status_server/`, `common/`, `config/`).
- `components/` contains workspace crates such as `tici_shard`, `tici_common`, `tici_grpc`, `tici_import`, `searchlib`, and `tici_integration_tests`.
- `tests/` holds script-driven suites and fixtures; `components/tici_integration_tests/tests/` contains Rust integration tests.
- `grafana/` stores dashboard sources (`.jsonnet`) and generated `.json` files.
- `ci/` includes the Dockerfile and configuration templates used by CI and local runs.
- `docs/design/` contains design documents for features and modules.
- `skills/` stores Codex skills such as `skills/manual_test.skill` for manual testing flows.

## Make Commands
- `make build` builds the workspace with `openssl-vendored` and `failpoints`.
- `make dev` formats, runs checks, and builds integration test targets.
- `make fmt` runs `cargo fmt` plus `cargo sort`; `make clippy` runs the repo clippy script.
- `make build-test-image` builds the test container; `make ut`, `make it`, `make e2e` run unit, integration, and e2e tests in it.

## Coding Style & Naming Conventions
You MUST follow the rules in `STYLE.md`.

## Testing Guidelines
- When a test (or test-only helper) needs a mock or in-memory implementation of `storage_backend` (`BackendStorage` and related types in `components/storage_backend/`), **prefer the shared utilities in `tici_shard::test_utils`**, especially `MockBackendStorage` in `components/tici_shard/src/test_utils/mock_backend_storage.rs` and helpers re-exported from the same module (for example `test_create_backend_storage`). Add a `dev-dependency` on `tici_shard` in the crate under test if needed, or extend the shared test utils if something is missing—do not introduce a parallel ad-hoc `BackendStorage` mock in another crate by default.
- Unit tests are crate-scoped. Test with `cargo test -p <crate>`.
- Integration tests for service discovery are placed under `components/tici_service_discovery`. Follow the etcd setup and cleanup commands in `components/tici_service_discovery/AGENTS.md` (set `ETCD_ADDR` accordingly).
- Integration suites live in `components/tici_integration_tests/tests/` and are driven by `make it`. They are also required.
    + Tests in `components/tici_integration_tests/tests/e2e/` are e2e tests that will test the external behavior of TiCI by running against real workloads and then sending grpc requests/FFI calls. If your changes modify TiCI's external behavior, you must add new e2e tests or update existing ones accordingly. You do not mock meta service, searchlib, shard writer, shard compactor in these tests.
    + Tests in folders other than `e2e/` under `components/tici_integration_tests/tests/` are integration tests. These tests validate the behavior of specific TiCI modules or features (e.g., shard compaction, worker scheduling). You must add new integration tests when introducing new features. You must update existing tests when behavior changes.
    + Shared utilities for integration tests are provided in `components/tici_test_utils`. Prefer using these utilities when writing or updating integration tests. If existing utilities are insufficient, extend or improve them instead of duplicating logic in individual tests.
- E2E scripts are under `tests/scripts/e2e` and run via `make e2e`.
- If you are asked to do manual testing, consult `skills/manual_test.skill` and follow its input requirements.

You may use `export CARGO_TARGET_DIR=...` to build tests in other folders, for potential permission problems.

## Commit & Pull Request Guidelines
- Recent history favors short, imperative subjects with a scope prefix and optional PR number, e.g. `skills: introduce ... (#682)` or `*: Replace ... (#680)`.
- PRs should describe affected components, list tests run, and call out config/dashboard changes (e.g., `ci/*.toml`, `grafana/*.jsonnet` + regenerated `.json`).
- Use the `gh` tool to access to issue or pull request instead of fetching the URL by http request.

## Configuration & Security Notes
- Config templates live in `ci/`; use them as the baseline for local runs.
- When touching Grafana dashboards, edit `.jsonnet` and run `grafana/generate_json.sh` to regenerate `.json`.
- Avoid committing credentials; local S3-compatible storage is typically MinIO (see `README.md`).

## Definition of Done (DoD)
You MUST NOT mark a task as complete or ask for my review until:
1. The code compiles without errors (`make format && make check`).
2. All tests pass (`make ci-ut`).

## The Verification Loop
When you modify any `.rs` file, you MUST strictly follow this autonomous loop:

1.  **Syntax Check (Fast Fail)**:
    - Run: `make format && make check`
    - If it fails: Read the compiler error, fix the code, and **restart Step 1**.
    - *Tip: Trust the Rust compiler's suggestions.*

2.  **Logic Verification**:
    - Run: `make ci-ut`
    - If it fails: Analyze the panic/assertion failure, fix the logic, and **go back to Step 1** (to ensure syntax is still valid).

3.  **Completion**:
    - ONLY when `make ci-ut` outputs "test result: ok", present the code to me.

## Constraints
- Do not ask for confirmation between build fixes.
- If you encounter a lifetime (borrow checker) error that you cannot solve after 3 attempts, STOP and ask me for help.
