{"record":{"id":"f378acc825cc2168","repo":"mastra-ai/mastra","slug":"failed-to-rename-session-res-status","errorCode":null,"errorMessage":"Failed to rename session (${res.status})","messagePattern":"Failed to rename session \\((.+?)\\)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"mastracode/factory-ui/src/ui/domains/workspaces/services/user-sessions.ts","lineNumber":97,"sourceCode":"  return normalizeUserSession(body.session);\n}\n\nexport async function deleteUserSession(baseUrl: string, sessionId: string): Promise<void> {\n  const res = await fetch(`${baseUrl}/web/user-sessions/${encodeURIComponent(sessionId)}`, {\n    method: 'DELETE',\n    credentials: 'include',\n  });\n  if (!res.ok && res.status !== 404) throw new Error(`Failed to delete session (${res.status})`);\n}\n\n/** Ask the title model to re-name a session's conversation. Resolves to the new title. */\nexport async function regenerateSessionTitle(baseUrl: string, sessionId: string): Promise<string> {\n  const res = await fetch(`${baseUrl}/web/user-sessions/${encodeURIComponent(sessionId)}/title`, {\n    method: 'POST',\n    credentials: 'include',\n  });\n  const body: { title?: string; error?: string } = await res.json().catch(() => ({}));\n  if (!res.ok || !body.title) throw new Error(body.error ?? `Failed to rename session (${res.status})`);\n  return body.title;\n}\n","sourceCodeStart":79,"sourceCodeEnd":100,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/mastracode/factory-ui/src/ui/domains/workspaces/services/user-sessions.ts#L79-L100","documentation":"regenerateSessionTitle in mastracode/factory-ui/src/ui/domains/workspaces/services/user-sessions.ts throws this when the POST to `${baseUrl}/web/user-sessions/${sessionId}/title` either returns non-OK or returns OK but the JSON body lacks a `title` field. The server can supply a specific `error` string in the body, which takes precedence over the generic message; the fallback embeds the HTTP status.","triggerScenarios":"POST returns 401/403 (bad or expired session cookie), 404 (sessionId no longer exists), 429 (title-model rate limit), 500 while invoking the rename model, or 200 with a malformed/empty body (no title, no error) due to a server/serialization bug.","commonSituations":"User clicks 'regenerate title' on a session that was deleted in another tab (404); the LLM-backed rename endpoint rate-limits rapid clicks (429); the backend model call times out and returns 500; a proxy strips the JSON body so body.title is undefined even on 200.","solutions":["Check the `error` field the server returned — the thrown message already prefers it; use it to pick the fix.","On 404, refresh the session list — the session no longer exists.","On 429, wait/back off before retrying; debounce the regenerate button.","On 401/403, re-authenticate; the credentials: 'include' cookie has expired or lacks scope.","If status is OK but title is missing, inspect the endpoint response shape — likely a server regression."],"exampleFix":"// before: throws on empty body with generic message\nconst body: { title?: string; error?: string } = await res.json().catch(() => ({}));\nif (!res.ok || !body.title) throw new Error(body.error ?? `Failed to rename session (${res.status})`);\n// after: retry once on 429/5xx before failing\nif ((res.status === 429 || res.status >= 500) && attempt === 0) return regenerateSessionTitle(baseUrl, sessionId);\nif (!res.ok || !body.title) throw new Error(body.error ?? `Failed to rename session (${res.status})`);","handlingStrategy":"try-catch","validationCode":"const sessions = await fetchUserSessions(baseUrl);\nif (!sessions.some(s => s.id === sessionId)) throw new Error('Session not found; refresh the list');","typeGuard":"function hasTitle(v: unknown): v is { title: string } {\n  return typeof v === 'object' && v !== null && typeof (v as { title?: unknown }).title === 'string' && (v as { title: string }).title.length > 0;\n}","tryCatchPattern":"try {\n  const title = await regenerateSessionTitle(baseUrl, sessionId);\n} catch (err) {\n  const msg = err instanceof Error ? err.message : String(err);\n  if (msg.includes('(429)')) await backoff(() => regenerateSessionTitle(baseUrl, sessionId));\n  else if (msg.includes('(404)')) invalidateSessionList();\n  else showToast(`Rename failed: ${msg}`);\n}","preventionTips":["Debounce/disable the regenerate button to avoid 429 rate limits from rapid clicks.","Validate the session still exists before renaming.","Handle empty-body 200 responses defensively — check the returned title before using it."],"tags":["http","fetch","rename","network","llm"],"backgroundTag":"http-request-failed","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T03:17:51.788Z"}