← Back to PRs

#8022: feat: implement before_model_select plugin hook

by dead-pool-aka-wilson open 2026-02-03 13:27 View on GitHub →
stale
## Summary Implements the `before_model_select` plugin hook that allows plugins to intercept and modify model selection before it's finalized. This enables intelligent routing based on prompt content (e.g., local Ollama classification for model routing). ## Changes - **Types** (`src/plugins/types.ts`): - Added `PluginHookBeforeModelSelectEvent` type with `provider`, `model`, `sessionKey`, `allowedModelKeys`, `prompt` - Added `PluginHookBeforeModelSelectResult` type with optional `provider` and `model` - Added `"before_model_select"` to `PluginHookName` union - Added handler signature to `PluginHookHandlerMap` - **Hook Runner** (`src/plugins/hooks.ts`): - Added `runBeforeModelSelect()` function using `runModifyingHook` pattern - Merges results from multiple handlers (last non-undefined wins for each field) - Re-exports new types for consumers - **Integration** (`src/auto-reply/reply/model-selection.ts`): - Added `prompt?: string` parameter to `createModelSelectionState` - Hook is called after stored override resolution - Hook results are validated against allowlist (strict enforcement) - Backward compatible - no change when no plugins registered ## Test Coverage - 8 tests for hook runner (`src/plugins/hooks.before-model-select.test.ts`) - 8 tests for integration (`src/auto-reply/reply/model-selection.before-model-select.test.ts`) ## Hook Behavior - **Type**: Modifying (sequential execution, result merging) - **Event Data**: `{ provider, model, sessionKey?, allowedModelKeys, prompt? }` - **Result**: `{ provider?, model? }` - partial results allowed - **Allowlist**: Strict - hook results validated against `allowedModelKeys` - **Priority**: Higher priority handlers execute first ## Use Case Enables plugins to implement intelligent model routing: ```typescript hooks: [{ hookName: "before_model_select", handler: async (event, ctx) => { // Classify prompt with local Ollama const category = await classifyPrompt(event.prompt); // Route to appropriate model return category === "code" ? { provider: "anthropic", model: "claude-sonnet-4-20250514" } : { provider: "openai", model: "gpt-4o-mini" }; } }] ``` <!-- greptile_comment --> <h2>Greptile Overview</h2> <h3>Greptile Summary</h3> Adds a new plugin lifecycle hook, `before_model_select`, allowing plugins to intercept and modify the resolved provider/model before it’s finalized. This includes: - New hook event/result types and registration signature in `src/plugins/types.ts`. - Hook runner support via `createHookRunner().runBeforeModelSelect()` in `src/plugins/hooks.ts`, using the existing sequential “modifying hook” pattern. - Integration into model selection (`src/auto-reply/reply/model-selection.ts`), passing `{ provider, model, sessionKey, allowedModelKeys, prompt? }` and enforcing that hook-provided selections must be allowlisted. - Focused unit tests for both the hook runner and the model-selection integration. <h3>Confidence Score: 4/5</h3> - This PR looks safe to merge; changes are localized and well-tested, with only minor semantic clarifications recommended. - The new hook is implemented using existing hook-runner patterns and is covered by targeted tests. Main concerns are around potentially confusing precedence semantics (priority vs last-wins) and provider-only hook results being silently ignored in some cases, which are correctness/UX for plugin authors rather than core runtime stability issues. - src/auto-reply/reply/model-selection.ts; src/plugins/hooks.ts <!-- greptile_other_comments_section --> <sub>(4/5) You can add custom instructions or style guidelines for the agent [here](https://app.greptile.com/review/github)!</sub> **Context used:** - Context from `dashboard` - CLAUDE.md ([source](https://app.greptile.com/review/custom-context?memory=fd949e91-5c3a-4ab5-90a1-cbe184fd6ce8)) - Context from `dashboard` - AGENTS.md ([source](https://app.greptile.com/review/custom-context?memory=0d0c8278-ef8e-4d6c-ab21-f5527e322f13)) <!-- /greptile_comment -->

Most Similar PRs