{"record":{"id":"387f02e7a4c91327","repo":"TryGhost/Ghost","slug":"failed-to-fetch-replies","errorCode":null,"errorMessage":"Failed to fetch replies","messagePattern":"Failed to fetch replies","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"apps/comments-ui/src/utils/api.ts","lineNumber":213,"sourceCode":"                }\n\n                if (afterReplyId) {\n                    params.set('filter', `id:>'${afterReplyId}'`);\n                }\n\n                const url = endpointFor({type: 'members', resource: `comments/${commentId}/replies`, params: `?${params.toString()}`});\n                const res = await makeRequest({\n                    url,\n                    method: 'GET',\n                    headers: {\n                        'Content-Type': 'application/json'\n                    },\n                    credentials: 'same-origin'\n                });\n                if (res.ok) {\n                    return res.json();\n                } else {\n                    throw new Error('Failed to fetch replies');\n                }\n            },\n            add({comment}: {comment: AddComment}) {\n                const body = {\n                    comments: [comment]\n                };\n                const url = endpointFor({type: 'members', resource: 'comments'});\n                return makeRequest({\n                    url,\n                    method: 'POST',\n                    headers: {\n                        'Content-Type': 'application/json'\n                    },\n                    body: JSON.stringify(body)\n                }).then(function (res) {\n                    if (res.ok) {\n                        return res.json();\n                    } else {","sourceCodeStart":195,"sourceCodeEnd":231,"githubUrl":"https://github.com/TryGhost/Ghost/blob/47d8b0e2ad2fd4757d3bc45f46c3ac165ff8a1fe/apps/comments-ui/src/utils/api.ts#L195-L231","documentation":"comments.replies() GETs /members/api/comments/{commentId}/replies to load paginated replies for a parent comment. The async/await variant (unlike the .then variant used by browse) checks res.ok and throws on non-ok. When limit is 'all', replies() recurses page-by-page and any page failure propagates the throw.","triggerScenarios":"The replies GET returns 4xx/5xx. The commentId does not exist or was deleted (404), the member lacks permission (401/403), the server errors (5xx), or a page cursor is out of range. In 'all' mode, a failure on page 2+ aborts the whole accumulation after some replies were already fetched.","commonSituations":"A user opens a comment whose parent was deleted between the thread render and the replies fetch. The session expires mid-pagination. A deep 'load all replies' request hits a transient 502 on an inner page.","solutions":["Check the Network tab for the replies GET status code and the specific commentId in the URL.","If 404, the parent comment no longer exists — handle gracefully by hiding the reply toggle.","For 'all' mode failures, consider catching per-page and returning partial results with a retry option.","If 401, re-establish the member session before retrying."],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"function isValidCommentId(commentId: string): boolean {\n  return typeof commentId === 'string' && commentId.length > 0;\n}","typeGuard":null,"tryCatchPattern":"try {\n  const data = await api.comments.replies({commentId});\n} catch (e) {\n  if (e instanceof Error && e.message === 'Failed to fetch replies') {\n    // hide the replies section or show retry\n  }\n}","preventionTips":["Validate commentId before calling replies().","For 'all' mode, wrap each page fetch to return partial results on inner failure rather than aborting.","Handle 404 by removing the parent comment from local state."],"tags":["network","fetch","comments-ui","replies","pagination"],"backgroundTag":null,"analyzedSha":"47d8b0e2ad2fd4757d3bc45f46c3ac165ff8a1fe","analyzedAt":"2026-08-13T01:25:26.651Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}