{"record":{"id":"26d52305533b51df","repo":"antiwork/gumroad","slug":"something-went-wrong-26d523","errorCode":null,"errorMessage":"Something went wrong.","messagePattern":"Something went wrong\\.","errorType":"exception","errorClass":"ResponseError","httpStatus":null,"severity":"error","filePath":"app/javascript/data/comments.ts","lineNumber":112,"sourceCode":"  return typia.assert<{ deleted_comment_ids: string[] }>(json).deleted_comment_ids;\n};\n\ntype FetchPaginatedCommentsArgs = {\n  commentable_id: string;\n  purchase_id: null | string;\n  page: null | number;\n};\nexport const fetchPaginatedComments = async ({\n  commentable_id,\n  purchase_id,\n  page,\n}: FetchPaginatedCommentsArgs): Promise<PaginatedComments> => {\n  const response = await request({\n    method: \"GET\",\n    accept: \"json\",\n    url: Routes.custom_domain_post_comments_path(commentable_id, { purchase_id, page }),\n  });\n  if (!response.ok) throw new ResponseError();\n  return typia.assert<PaginatedComments>(await response.json());\n};\n","sourceCodeStart":94,"sourceCodeEnd":115,"githubUrl":"https://github.com/antiwork/gumroad/blob/afeacbd394069a1cbf0c6c50ee8e900925050370/app/javascript/data/comments.ts#L94-L115","documentation":"ResponseError (\"Something went wrong.\") is thrown by Gumroad's data layer when an endpoint answers non-2xx. This line in fetchPaginatedComments fires when GET /posts/:commentable_id/comments (custom_domain_post_comments_path with purchase_id and page) returns an error status. Because the shared request() wrapper already converts 5xx, 429, aborts, and network failures into their own error types before this line runs, reaching line 112 in practice means a 4xx: post gone (404), purchase_id no longer granting access (401/403), or a malformed request (400/422).","triggerScenarios":"Loading a post's comments with a purchase_id that was refunded or revoked so the access check fails; the commentable post was unpublished/deleted after the page rendered; the reader's session expired on a custom-domain post; passing page as NaN or a string because it was never normalized from the URL query.","commonSituations":"Reader tabs left open overnight while the post is deleted or the purchase refunded; custom-domain proxies/CDNs returning 404 for moved posts; hand-built comment URLs with wrong ids; permalink changes leaving stale commentable ids in cached pages.","solutions":["Open DevTools → Network and inspect the failing /comments request — the status code narrows it immediately (404 vs 403 vs 422).","404: the post no longer exists — stop rendering the comment thread and show an empty/unavailable state instead of retrying.","401/403: the purchase_id no longer grants access — send the reader to re-authenticate or repurchase rather than showing a generic failure.","422/400: log the purchase_id/page values actually sent and normalize page to null | number before calling fetchPaginatedComments."],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"const ok =\n  typeof commentable_id === \"string\" && commentable_id.length > 0 &&\n  typeof purchase_id === \"string\" && purchase_id.length > 0 &&\n  (page === null || (Number.isInteger(page) && page >= 1));\nif (!ok) throw new Error(\"Comment thread is missing a post or purchase reference.\");\nawait fetchPaginatedComments({ commentable_id, purchase_id, page });","typeGuard":"import { ResponseError } from \"$app/utils/request\";\nconst isResponseError = (e: unknown): e is ResponseError => e instanceof ResponseError;","tryCatchPattern":"import { assertResponseError } from \"$app/utils/request\";\ntry {\n  const comments = await fetchPaginatedComments({ commentable_id, purchase_id, page });\n} catch (e) {\n  assertResponseError(e);\n  setCommentsUnavailable(); // render an empty state, do not break the post page\n}","preventionTips":["Normalize page from the URL to null | number before calling; NaN serializes into a 422.","Take commentable_id and purchase_id from server-rendered data for the current post, never from hand-built URLs.","On reader-facing pages, degrade to a hidden comment section instead of a generic error toast."],"tags":["comments","custom-domain","pagination","purchase-access","http","fetch"],"backgroundTag":"http-4xx-response","analyzedSha":"afeacbd394069a1cbf0c6c50ee8e900925050370","analyzedAt":"2026-08-21T17:58:52.159Z","schemaVersion":2},"datasetVersion":"2026-08-21T18:17:14.833Z"}