# Optimization Pipeline

End-to-end flow from optimization request to response.

## 1. Request Entry (`core/shared/optimizer_router.py`)

The `optimize_api` NinjaAPI router receives a POST request with `OptimizeSchema`. It dispatches by `data.language`:
- `"javascript"` / `"typescript"` → `core.languages.js_ts.optimizer.optimize_javascript`
- `"java"` → `core.languages.java.optimizer.optimize_java`
- Default → `core.languages.python.optimizer.optimizer.optimize_python`

All imports are lazy (inside the function body) to avoid circular dependencies.

## 2. Python Optimization (`core/languages/python/optimizer/optimizer.py`)

### `optimize_python(request, data) → (status, response)`

Entry point for Python optimization. Extracts user ID from request, builds context, and calls `optimize_python_code()`.

### `optimize_python_code_single()`

Single LLM optimization call:
1. Builds system + user prompts from `BaseOptimizerContext`
2. Calls `call_llm()` with the optimize model
3. Parses response via `ctx.extract_code_and_explanation_from_llm_res()`
4. Validates via `ctx.parse_and_generate_candidate_schema()`
5. Returns `(OptimizeResponseItemSchema, llm_cost, model_name)` or `(None, cost, model)`

### `optimize_python_code()`

Parallel optimization with multiple models:
1. Gets model distribution via `get_model_distribution(n_candidates, MAX_OPTIMIZER_CALLS)`
2. Runs parallel calls using `asyncio.TaskGroup`
3. Each call gets a `call_sequence` number for tracking
4. Collects results, costs, and model info from all parallel calls

## 3. Context Extraction (`optimizer_context.py`)

- `BaseOptimizerContext.get_dynamic_context()` — factory dispatching to `SingleOptimizerContext` or `MultiOptimizerContext`
- Handles prompt construction with `get_system_prompt()` / `get_user_prompt()`
- `extract_code_and_explanation_from_llm_res()` — parses markdown code blocks from LLM output
- `parse_and_generate_candidate_schema()` — converts extracted code to response schema

## 4. Postprocessing (`postprocess.py`)

- `deduplicate_optimizations()` — AST-based dedup using `ast.parse()` + `ast.dump()`
- `equality_check()` — filters out candidates identical to original code
- Uses `libcst` for all code transformations

## 5. Model Distribution (`optimizer_config.py`)

- `MAX_OPTIMIZER_CALLS = 6`, `MAX_OPTIMIZER_LP_CALLS = 7`
- `get_model_distribution()` splits between OpenAI and Anthropic
- Formula: `claude_calls = (total - 1) // 2`, `gpt_calls = total - claude_calls`
- Returns `[(OPENAI_MODEL, gpt_calls), (ANTHROPIC_MODEL, claude_calls)]`

## 6. Response

Returns `(200, OptimizeResponseSchema)` with list of `OptimizeResponseItemSchema` candidates, or `(400/500, OptimizeErrorResponseSchema)` on failure.

## Key Files

| File | Role |
|------|------|
| `core/shared/optimizer_router.py` | Language dispatch |
| `core/languages/python/optimizer/optimizer.py` | Python optimization flow |
| `core/languages/python/optimizer/context_utils/optimizer_context.py` | Context & prompt management |
| `core/languages/python/optimizer/postprocess.py` | Dedup & validation |
| `core/shared/optimizer_config.py` | Model distribution |
| `core/shared/optimizer_models.py` | Request/response schemas |
