siyuan-note/siyuan · error
AI editor model returned nil stream
Error message
AI editor model returned nil stream
What it means
After CreateOpenAICompletionStream returns nil error, NewAIEditorChatStream defensively checks that a non-nil completion stream was produced. A nil stream with nil error violates the client's contract, so SiYuan cancels the context and throws "AI editor model returned nil stream". This is an internal-invariant error from the OpenAI client layer, not an expected user-facing condition.
Solutions
- Check the provider's `protocol` setting in AI config and set it to a supported value (e.g. OpenAI-compatible)
- Retry the request — transient client-layer conditions may resolve
- Inspect util.CreateOpenAICompletionStream for paths that can return nil,nil and fix if running a modified kernel
- Update SiYuan to the latest version, as this may be a fixed client-layer bug
Defensive patterns
Strategy: try-catch
Try / catch
stream, err := model.NewAIEditorChatStream(ctx, ids, input, action, history)
if err != nil {
if strings.Contains(err.Error(), "nil stream") {
logging.LogErrorf("AI client returned nil stream; check provider protocol config")
}
return err
} Prevention
- Use a supported provider protocol value
- Keep SiYuan updated
- Verify non-standard OpenAI-compatible endpoints behave correctly before relying on them
When it happens
Trigger: util.CreateOpenAICompletionStream returning (nil, nil) for the configured prov.Protocol — an unexpected/unsupported protocol value or a client-layer bug — while the request timer did not fire.
Common situations: Provider `protocol` field set to an unhandled value; a modified or version-mismatched OpenAI client utility returning nil on a code path without an error; protocol-specific quirks of a non-standard OpenAI-compatible endpoint.
Understand the failure class
Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.
Related errors
- capability handler unavailable
- capability validator unavailable
- AI configuration is unavailable
- AI editor action must not be empty
- AI editor action not found
AI-assisted analysis of siyuan-note/siyuan@9f775e8a12 (2026-09-19).
Data as JSON: /api/errors/72c3bbe037588767.
Report an issue: GitHub.
Appendix: source
Thrown at kernel/model/ai.go:202
Stream: true,
}
streamCtx, cancel := context.WithCancel(ctx)
streamCtx = util.ContextWithOpenAIResponsesBaseURL(streamCtx, prov.BaseURL)
requestTimeout := time.Duration(prov.RequestTimeout) * time.Second
requestTimer, requestTimerDone := startAIEditorCancelTimer(requestTimeout, cancel)
client := util.NewOpenAIClientWithModel(prov.APIKey, prov.BaseURL, m.Name, ResolveAIProviderHeaders(prov))
completionStream, err := util.CreateOpenAICompletionStream(streamCtx, client, prov.Protocol, req, nil)
requestTimedOut := stopAIEditorCancelTimer(requestTimer, requestTimerDone)
if requestTimedOut {
err = errors.New("AI editor request timeout")
}
if nil != err {
cancel()
return nil, err
}
if nil == completionStream {
cancel()
return nil, errors.New("AI editor model returned nil stream")
}
return &AIEditorChatStream{
stream: completionStream,
cancel: cancel,
idleTimeout: 120 * time.Second,
}, nil
}
func startAIEditorCancelTimer(timeout time.Duration, cancel context.CancelFunc) (*time.Timer, <-chan struct{}) {
if 0 >= timeout {
return nil, nil
}
done := make(chan struct{})
timer := time.AfterFunc(timeout, func() {
cancel()
close(done)
})
return timer, doneView on GitHub (pinned to 9f775e8a12)