===== SKILL.md: platform-packs/kotlin/code-review/bill-kotlin-code-review/SKILL.md =====
---
name: bill-kotlin-code-review
description: Use when conducting a thorough Kotlin PR code review across shared, backend/server, or generic Kotlin code, or when providing the baseline Kotlin review layer for Android/KMP reviews. Select shared Kotlin specialists for architecture, correctness, security, performance, and testing, and add backend-focused specialists for API contracts, persistence, and reliability when server signals are present. Produces a structured review with risk register and prioritized action items. Use when user mentions Kotlin review, review Kotlin PR, Kotlin code review, or asks to review .kt files.
---

## Descriptor

Governed skill: `bill-kotlin-code-review`
Family: `code-review`
Platform pack: `kotlin` (Kotlin)
Description: Use when reviewing Kotlin changes across code-review specialists.

## Execution

You are an experienced Kotlin architect conducting a code review.

This skill owns the baseline Kotlin review layer. It covers shared Kotlin concerns for libraries, CLIs, shared utilities, and the common Kotlin layer that platform-specific review overrides build on top of.
---

### Kotlin-Family Classification

Inspect both the changed files and repo markers (`build.gradle*`, `settings.gradle*`, `gradle/libs.versions.toml`, `pom.xml`, `application.yml`, `application.conf`, source layout, module names, imports).

Classify the review as one of:
- `kotlin`
- `kmp-baseline`

#### Additional Backend/Server Signals

- `io.ktor.server`, `routing {}`, `Application.module`
- `spring-boot`, `@RestController`, `@Controller`, `@Service`, `@Repository`, `@Transactional`
- Micronaut, Quarkus, http4k, Javalin, gRPC server code
- `application.yml`, `application.yaml`, `application.conf`
- SQL/ORM/data-access layers: Exposed, jOOQ, Hibernate/JPA, JDBC, R2DBC, Flyway, Liquibase
- Queues, schedulers, consumers, caches, metrics, tracing, server auth middleware

#### Decision Rules

- If this skill is invoked from `bill-kmp-code-review`, accept Android/KMP scope and classify it as `kmp-baseline`. In that mode, review only shared Kotlin concerns and let `bill-kmp-code-review` add mobile-specific specialists.
- If strong Android/KMP markers are present and this skill is invoked standalone, clearly say that `bill-kmp-code-review` is required for full Android/KMP coverage. Continue only if the caller explicitly wants the baseline Kotlin layer.
- Backend/server markers stay on the `kotlin` route. Select backend-focused Kotlin specialists for API contracts, persistence, and reliability when backend/server signals are present.
- Otherwise use the `kotlin` route.

---

### Dynamic Specialist Selection

#### Step 1: Always include `bill-kotlin-code-review-architecture`

Architecture review is relevant for every non-trivial change.

#### Step 2: Choose route baseline

- `kotlin`: baseline is `architecture` + `bill-kotlin-code-review-platform-correctness`
- `kmp-baseline`: baseline is `architecture` + `bill-kotlin-code-review-platform-correctness`

#### Step 3: Analyze the diff and select additional specialist reviews

| Signal in the diff                                                                                                                                                  | Specialist review to run                       |
|---------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------------------|
| `launch`, `Flow`, `StateFlow`, `viewModelScope`, `LifecycleOwner`, `DispatcherProvider`, `Mutex`, `Semaphore`, `suspend fun`, coroutine scopes, concurrent mutation | `bill-kotlin-code-review-platform-correctness` |
| Auth, tokens, keys, passwords, encryption, HTTP clients, interceptors, sensitive data                                                                               | `bill-kotlin-code-review-security`             |
| Heavy computation, blocking I/O, retry/polling loops, bulk data processing, redundant I/O                                                                           | `bill-kotlin-code-review-performance`          |
| Test files modified (`*Test.kt`), new test classes, mock setup changes, coverage-padding or tautological tests                                                      | `bill-kotlin-code-review-testing`              |
| Routes/controllers, request/response DTOs, serializers, content negotiation, validation, status-code mapping, OpenAPI/schema changes                                | `bill-kotlin-code-review-api-contracts`        |
| Repositories/DAOs, SQL, ORM mappings, transactions, migrations, optimistic locking, upserts, bulk writes                                                            | `bill-kotlin-code-review-persistence`          |
| Timeouts, retries, circuit breakers, queues, schedulers, idempotency, caching, metrics, tracing, startup/shutdown lifecycle                                         | `bill-kotlin-code-review-reliability`          |

#### Step 4: Apply minimum

- Minimum 2 agents (architecture + at least one other)
- If no additional triggers match, include `bill-kotlin-code-review-platform-correctness` as the default second specialist review
- Maximum 8 agents so backend-heavy Kotlin diffs can include the restored server specialists without dropping shared Kotlin coverage
- Do not run KMP-only specialists from this skill; leave those to the platform-specific override that owns them

#### Step 5: Scale review depth

- For small, low-risk Kotlin diffs, keep the review compact.
- For larger or higher-risk diffs, split the work into focused specialist passes so each lane can inspect the files most relevant to it.

#### Step 5.5: Scope diff per specialist when review depth increases

When the review is split into focused specialist passes, build a per-specialist file list first:

1. Scan each changed file's name and imports for the routing-table signals from Step 3
2. Map each file to the specialists whose signals it matches
3. `bill-kotlin-code-review-architecture` always receives all changed files
4. Every other specialist receives only files matching its routing-table signals
5. If a non-architecture specialist's scoped file list is empty, drop it from the selected set
6. After scoping, re-check the minimum-2-specialist requirement; if only architecture remains, add `bill-kotlin-code-review-platform-correctness` with all changed files as the default second

This is a lightweight file-level classification (names + imports), not a full review.

#### Step 6: Run selected specialist reviews

- Spawn each selected specialist lane against its scoped files.
- Read each specialist skill file as the primary rubric for that lane.
- Keep findings attributed to each specialist before merging and deduplicating them into the final review.
- When the selected set is larger than the host runtime can run concurrently, run specialists in deterministic waves and merge all wave outputs before the final review.

### Subagent Spawn Runtime Notes

Specialist spawn instructions in this orchestrator are runtime-neutral. Each phrase such as "spawn the `bill-kotlin-code-review-api-contracts` subagent" maps to the native subagent surface of the host runtime (parent skill: `bill-kotlin-code-review`). The per-runtime paragraphs below are imperative: the orchestrator MUST follow the paragraph that matches the runtime it is running in, including how it collects the subagent's `RESULT:` JSON. Picking a different mechanism (for example, emitting a natural-language "please spawn" message instead of calling the listed tool) causes the workflow to stall because no subagent actually runs and no `RESULT:` is ever returned.

**On Claude (Claude Code, Anthropic SDK agents).** The orchestrator MUST invoke the built-in `Agent` tool with `subagent_type` set to the matching specialist name (for example, `subagent_type: "bill-kotlin-code-review-api-contracts"` for that role in `bill-kotlin-code-review`) and pass the per-phase briefing as the tool's `prompt`. Call the tool in the **foreground** (the default — do NOT pass `run_in_background: true`). The `Agent` tool blocks until the subagent finishes and returns the subagent's final text message as the tool result; the orchestrator parses the `RESULT:` JSON directly from that returned message in the same turn. Do NOT sleep, poll, ping, re-call, or otherwise check on the subagent — Claude's `Agent` tool surfaces completion synchronously and any polling loop is both unnecessary and explicitly discouraged by the tool contract. If the tool returns and the message is missing a `RESULT:` block or contains malformed JSON, fall through to the `RESULT:` block parsing tolerance rules (best-effort recovery, then exactly one corrective re-spawn via another foreground `Agent` call) instead of waiting.

**On Codex.** The spawn is a natural-language directive in the orchestrator's turn. Codex resolves the subagent by `name` against the installed TOML files in the Codex user agents directory (with the legacy Agents agents fallback), respecting `agents.max_threads` and `agents.max_depth`. Because Codex runs subagents asynchronously, the orchestrator MUST poll for completion between turns before consuming the subagent's `RESULT:` block — do not proceed to the next phase until the subagent has visibly finished and its `RESULT:` JSON is available in the conversation.

**On OpenCode.** The spawn resolves by filename-derived `name` against markdown agents installed in the OpenCode user agents directory; operators can also invoke the same specialists manually with `@bill-kotlin-code-review-api-contracts`, `@bill-kotlin-code-review-architecture`, `@bill-kotlin-code-review-performance`, `@bill-kotlin-code-review-persistence`, `@bill-kotlin-code-review-platform-correctness`, `@bill-kotlin-code-review-reliability`, `@bill-kotlin-code-review-security`, `@bill-kotlin-code-review-testing`. Like Codex, OpenCode runs the spawn asynchronously, so the orchestrator MUST wait for the subagent to finish (checking between turns) and only then read its `RESULT:` JSON before advancing.

Selected fan-out exceeds Codex's `agents.max_threads = 6` default; run waves of at most 6 specialists, with the orchestrator merging wave outputs before final review.

OpenCode does not document a different native concurrency cap; keep the conservative limit of 6 or fewer specialists per wave.

## Ceremony

Follow the shell ceremony in [shell-ceremony.md](shell-ceremony.md).

Determine the review scope using [review-scope.md](review-scope.md).

When stack routing applies, follow [stack-routing.md](stack-routing.md).

When delegated specialist review applies, use [specialist-contract.md](specialist-contract.md).

When delegated review execution applies, follow [review-delegation.md](review-delegation.md).

When review reporting applies, follow [review-orchestrator.md](review-orchestrator.md).

When telemetry applies, follow [telemetry-contract.md](telemetry-contract.md).

===== pointer: platform-packs/kotlin/code-review/bill-kotlin-code-review/review-orchestrator.md =====
../../../../orchestration/review-orchestrator/PLAYBOOK.md

===== pointer: platform-packs/kotlin/code-review/bill-kotlin-code-review/review-delegation.md =====
../../../../orchestration/review-delegation/PLAYBOOK.md

===== pointer: platform-packs/kotlin/code-review/bill-kotlin-code-review/review-scope.md =====
../../../../orchestration/review-scope/PLAYBOOK.md

===== pointer: platform-packs/kotlin/code-review/bill-kotlin-code-review/shell-ceremony.md =====
../../../../orchestration/shell-content-contract/shell-ceremony.md

===== pointer: platform-packs/kotlin/code-review/bill-kotlin-code-review/specialist-contract.md =====
../../../../orchestration/review-orchestrator/specialist-contract.md

===== pointer: platform-packs/kotlin/code-review/bill-kotlin-code-review/stack-routing.md =====
../../../../orchestration/stack-routing/PLAYBOOK.md

===== pointer: platform-packs/kotlin/code-review/bill-kotlin-code-review/telemetry-contract.md =====
../../../../orchestration/telemetry-contract/PLAYBOOK.md
