janhq/jan · error · Error

model-errors:createModelFailed

Error message

model-errors:createModelFailed

What it means

Thrown when `this.createModelOrAbort(...)` rejects with a non-AbortError during message send. The catch block preserves AbortError identity (user pressed Stop) but wraps every other failure through i18n key `model-errors:createModelFailed` with `describeEngineError(error)` as the reason. This is the umbrella error for any model-load/creation failure across all providers.

Source

Thrown at web-app/src/lib/custom-chat-transport.ts:1210

        updatedProvider ?? provider,
        mergedParams,
        providerId,
        options.abortSignal
      )
      useAppState.getState().updateLoadingModel(false)
      useAppState.getState().updateThreadLoadingModel(threadId, false)
      useAppState.getState().updateModelLoadProgress(undefined)
      useAppState.getState().updateThreadModelLoadProgress(threadId, undefined)
    } catch (error) {
      useAppState.getState().updateLoadingModel(false)
      useAppState.getState().updateThreadLoadingModel(threadId, false)
      useAppState.getState().updateModelLoadProgress(undefined)
      useAppState.getState().updateThreadModelLoadProgress(threadId, undefined)
      console.error('Failed to create model:', error)
      // Preserve AbortError identity so callers/UI can tell a user-initiated
      // Stop from an actual model-load failure.
      if (error instanceof Error && error.name === 'AbortError') throw error
      throw new Error(
        i18n.t('model-errors:createModelFailed', {
          reason: describeEngineError(error),
        })
      )
    }

    await this.refreshTools(options.abortSignal)

    // Split assistant turns that place text after tool calls into separate
    // messages. Required by the Claude API (tool_use / tool_result pairing) and
    // it keeps the prompt prefix byte-identical across turns so llama.cpp reuses
    // the KV cache. See `splitAssistantToolWaves`.
    const messagesToConvert = splitAssistantToolWaves(options.messages)

    const inferenceParams = this.getActiveInferenceParams()

    const selectedModel = useModelProvider.getState().selectedModel

View on GitHub (pinned to fad3f12a14)

Solutions

  1. Read the `reason` in the surfaced message and the console — `describeEngineError` extracts the underlying engine message.
  2. For local models: reduce context length / GPU layers, free memory, or use a smaller quantization.
  3. For remote providers: verify the API key and base URL in provider settings.
  4. For GGUF: confirm the file's version is supported by the installed llama.cpp build; re-download if corrupt.
  5. Restart the engine extension if its IPC bridge died.

Example fix

// before
if (error instanceof Error && error.name === 'AbortError') throw error
throw new Error(i18n.t('model-errors:createModelFailed', { reason: describeEngineError(error) }))

// after
if (error instanceof Error && error.name === 'AbortError') throw error
const reason = describeEngineError(error)
console.error('[createModel] full error:', error)
throw new Error(
  i18n.t('model-errors:createModelFailed', {
    reason: reason || 'Unknown error. See console for details.',
  })
)
Defensive patterns

Strategy: try-catch

Type guard

function isAbortError(e: unknown): e is Error {
  return e instanceof Error && e.name === 'AbortError'
}

Try / catch

try {
  this.model = await this.createModelOrAbort(modelId, updatedProvider ?? provider, mergedParams, providerId, options.abortSignal)
} catch (error) {
  useAppState.getState().updateLoadingModel(false)
  useAppState.getState().updateThreadLoadingModel(threadId, false)
  if (isAbortError(error)) throw error // user pressed Stop — preserve identity
  console.error('[createModel] underlying error:', error)
  throw new Error(i18n.t('model-errors:createModelFailed', { reason: describeEngineError(error) }))
}

Prevention

When it happens

Trigger: llama.cpp server failed to load the GGUF (corrupt/unsupported file, OOM, missing mmproj); remote provider returned auth failure during model init (401/403); the model binary path is wrong; the engine extension threw during instantiation; context-length or GPU-layer settings exceed hardware.

Common situations: Insufficient RAM/VRAM to load the model; wrong API key for an OpenAI-compatible provider; GGUF version unsupported by the installed llama.cpp build; model file truncated/corrupted; engine extension crashed and its IPC bridge is down.

Related errors


AI-assisted analysis of janhq/jan@fad3f12a14 (2026-08-12). Data as JSON: /api/errors/220d53dd28ea4b5e. Report an issue: GitHub.