🎯 Use case
This file lives under “hooks/”, which covers reusable UI or integration hooks. On the API surface it exposes useMainLoopModel — mainly functions, hooks, or classes. Dependencies touch React UI. It composes internal code from services, state, and utils (relative imports). What the file header says: The value of the selector is a full model name that can be used directly in API calls. Use this over getMainLoopModel() when the component needs to update upon a model config change.
Generated from folder role, exports, dependency roots, and inline comments — not hand-reviewed for every path.
🧠 Inline summary
The value of the selector is a full model name that can be used directly in API calls. Use this over getMainLoopModel() when the component needs to update upon a model config change.
📤 Exports (heuristic)
useMainLoopModel
📚 External import roots
Package roots from from "…" (relative paths omitted).
react
🖥️ Source preview
import { useEffect, useReducer } from 'react'
import { onGrowthBookRefresh } from '../services/analytics/growthbook.js'
import { useAppState } from '../state/AppState.js'
import {
getDefaultMainLoopModelSetting,
type ModelName,
parseUserSpecifiedModel,
} from '../utils/model/model.js'
// The value of the selector is a full model name that can be used directly in
// API calls. Use this over getMainLoopModel() when the component needs to
// update upon a model config change.
export function useMainLoopModel(): ModelName {
const mainLoopModel = useAppState(s => s.mainLoopModel)
const mainLoopModelForSession = useAppState(s => s.mainLoopModelForSession)
// parseUserSpecifiedModel reads tengu_ant_model_override via
// _CACHED_MAY_BE_STALE (in resolveAntModel). Until GB init completes,
// that's the stale disk cache; after, it's the in-memory remoteEval map.
// AppState doesn't change when GB init finishes, so we subscribe to the
// refresh signal and force a re-render to re-resolve with fresh values.
// Without this, the alias resolution is frozen until something else
// happens to re-render the component — the API would sample one model
// while /model (which also re-resolves) displays another.
const [, forceRerender] = useReducer(x => x + 1, 0)
useEffect(() => onGrowthBookRefresh(forceRerender), [])
const model = parseUserSpecifiedModel(
mainLoopModelForSession ??
mainLoopModel ??
getDefaultMainLoopModelSetting(),
)
return model
}