chenhg5/cc-connect · error
max: cannot reconstruct reply ctx from %q
Error message
max: cannot reconstruct reply ctx from %q
What it means
ReconstructReplyCtx rebuilds a replyContext from a session key of the form "max:{chatID}" or "max:{chatID}:{userID}" so the engine can reply to a restored session. If the key does not carry the required "max:" prefix, the platform cannot recognize it as a MAX session and returns this error. It guards against feeding keys produced by other platforms into the MAX reconstructor.
Source
Thrown at platform/max/max.go:741
// MAX-supported markdown syntax.
func (p *Platform) FormattingInstructions() string {
return `Formatting rules for MAX messenger:
- **bold** and _italic_ are supported
- Inline code: ` + "`code`" + ` and fenced code blocks (` + "```" + `) are supported
- Bullet lists with - or * are supported as plain text
- Do NOT use headers (# ## ###)
- Do NOT use horizontal rules (--- or ***)
- Do NOT use tables
- Do NOT use HTML tags
Keep responses concise and use plain text where possible.`
}
// ReconstructReplyCtx implements core.ReplyContextReconstructor.
// Session key format: "max:{chatID}" or "max:{chatID}:{userID}".
func (p *Platform) ReconstructReplyCtx(sessionKey string) (any, error) {
rest, ok := strings.CutPrefix(sessionKey, "max:")
if !ok {
return nil, fmt.Errorf("max: cannot reconstruct reply ctx from %q", sessionKey)
}
chatID, _, _ := strings.Cut(rest, ":")
if chatID == "" {
return nil, fmt.Errorf("max: cannot reconstruct reply ctx from %q", sessionKey)
}
return replyContext{chatID: chatID}, nil
}
// --- MAX API types ---
type maxButton struct {
Type string `json:"type"`
Text string `json:"text"`
Payload string `json:"payload"`
}
// maxOutAttachment is the generic outgoing attachment wrapper used for both
// inline_keyboard (with maxKbPayload) and image/file/video/audio (withView on GitHub (pinned to 4000b2338a)
Solutions
- Pass only session keys that begin with "max:"; filter or route keys to the correct platform's reconstructor first.
- Inspect the offending key in the error message (%q) to identify which platform produced it and use that platform's ReconstructReplyCtx.
- If keys predate a rename, migrate stored keys to the current "max:{chatID}" format.
- Normalize the key: if it is a bare numeric chat id, wrap it as "max:"+chatID before calling.
Example fix
// before (any key goes to max)
ctx, err := maxPlatform.ReconstructReplyCtx(sessionKey)
// after: dispatch by prefix
var ctx any
switch {
case strings.HasPrefix(sessionKey, "max:"):
ctx, err = maxPlatform.ReconstructReplyCtx(sessionKey)
case strings.HasPrefix(sessionKey, "feishu:"):
ctx, err = feishuPlatform.ReconstructReplyCtx(sessionKey)
default:
err = fmt.Errorf("unknown session key format: %q", sessionKey)
} Defensive patterns
Strategy: type-guard
Validate before calling
// Route by prefix before calling the MAX reconstructor
func isMaxSessionKey(key string) bool { return strings.HasPrefix(key, "max:") }
if !isMaxSessionKey(sessionKey) {
return fmt.Errorf("not a max session key: %q", sessionKey)
} Type guard
func isMaxKey(s string) bool {
rest, ok := strings.CutPrefix(s, "max:")
if !ok { return false }
chatID, _, _ := strings.Cut(rest, ":")
return chatID != ""
} Try / catch
ctx, err := p.ReconstructReplyCtx(sessionKey)
if err != nil {
slog.Warn("max: cannot restore session", "key", sessionKey, "err", err)
// fall back to starting a fresh session for this chat
return startNewSession(chatID)
} Prevention
- Namespace all session keys with the platform prefix and enforce it at write time.
- Keep a registry mapping platform prefix → ReconstructReplyCtx so keys are dispatched correctly.
- Migrate legacy unprefixed keys after any platform rename.
- Test key round-tripping (format → reconstruct) for every platform in CI.
When it happens
Trigger: Calling ReconstructReplyCtx with a session key like "feishu:oc_123" or a bare chat id "12345" (no "max:" prefix), typically from a session store mixing multiple platform keys, or after a config change that renamed the platform.
Common situations: Cross-platform session stores where keys from Telegram/Feishu are passed to the MAX platform; hand-crafted keys in tests or tooling missing the prefix; a platform name change leaving legacy keys without "max:".
Understand the failure class
Background: "Invalid ... format", "must be in format X", "does not look like a ..." — invalid argument format errors across CLI tools and libraries — this error's family across 17 libraries.
Related errors
- cdn upload: no token in response: %s
- tuitui: invalid session key %q
- webex: cannot reconstruct reply ctx from %q
- acp: session/new: %w
- acp: session/new: empty sessionId
AI-assisted analysis of chenhg5/cc-connect@4000b2338a (2026-09-06).
Data as JSON: /api/errors/4e877a8a2fb3529e.
Report an issue: GitHub.