{"record":{"id":"cdd3204703cf7e40","repo":"chenhg5/cc-connect","slug":"delete-reaction-failed-status-d-body-s","errorCode":null,"errorMessage":"delete reaction failed: status=%d body=%s","messagePattern":"delete reaction failed: status=(.+?) body=(.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"platform/wps-xiezuo/wpsxiezuo.go","lineNumber":996,"sourceCode":"\tbody, _ := json.Marshal(reactionRequest{ReactionType: reactionType})\n\turl := fmt.Sprintf(\"%s/v7/chats/%s/messages/%s/reactions/delete\", p.baseURL, rctx.ChatID, rctx.MessageID)\n\n\treq, err := http.NewRequestWithContext(ctx, http.MethodPost, url, bytes.NewReader(body))\n\tif err != nil {\n\t\treturn err\n\t}\n\treq.Header.Set(\"Authorization\", \"Bearer \"+token)\n\treq.Header.Set(\"Content-Type\", \"application/json\")\n\n\tresp, err := http.DefaultClient.Do(req)\n\tif err != nil {\n\t\treturn err\n\t}\n\tdefer resp.Body.Close()\n\n\tif resp.StatusCode != http.StatusOK {\n\t\trespBody, _ := io.ReadAll(resp.Body)\n\t\treturn fmt.Errorf(\"delete reaction failed: status=%d body=%s\", resp.StatusCode, string(respBody))\n\t}\n\treturn nil\n}\n\n// --- Optional interface: ReplyContextReconstructor ---\n\nfunc (p *Platform) ReconstructReplyCtx(sessionKey string) (any, error) {\n\t// Formats:\n\t//   wps-xiezuo:{company_id}:{chat_id}             - group or legacy P2P\n\t//   wps-xiezuo:{company_id}:{chat_id}:{sender_id} - P2P, user-scoped\n\tparts := strings.SplitN(sessionKey, \":\", 4)\n\tif len(parts) < 3 || parts[0] != \"wps-xiezuo\" {\n\t\treturn nil, fmt.Errorf(\"wps-xiezuo: invalid session key %q\", sessionKey)\n\t}\n\trc := replyContext{\n\t\tChatID:    parts[2],\n\t\tCompanyID: parts[1],\n\t}","sourceCodeStart":978,"sourceCodeEnd":1014,"githubUrl":"https://github.com/chenhg5/cc-connect/blob/4000b2338aa6e850c99df54f8b0ed6ed7460b401/platform/wps-xiezuo/wpsxiezuo.go#L978-L1014","documentation":"The WPS Xiezuo (协作) API returned a non-200 status for the reaction-delete call — the server rejected removing a reaction (expired message, missing permission, or invalid token), with the response body included for diagnosis.","triggerScenarios":"Calling the delete-reaction operation when the reaction ID is wrong/already deleted, the token is expired, or permissions on the doc/comment are insufficient.","commonSituations":"Stale reaction ID cached after another user removed the reaction; expired access token after hours of runtime; bot lacking edit permission on the document.","solutions":["Read the status and body in the error: 401/403 means refresh the token or fix permissions; 404 means the reaction no longer exists","Refresh the OAuth access token and retry","Verify the reaction ID is current; re-fetch reactions before deleting","Check the bot/user has permission to modify the target document"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"if resp.StatusCode == http.StatusUnauthorized { token = refreshToken(); retry() }","typeGuard":null,"tryCatchPattern":"if err := deleteReaction(id); err != nil { var httpErr = err; if strings.Contains(err.Error(), \"status=404\") { return nil /* already deleted */ }; if strings.Contains(err.Error(), \"status=401\") { refreshToken(); retry() }; return httpErr }","preventionTips":["Refresh access tokens proactively before expiry","Re-fetch reaction lists before deleting to ensure IDs are current","Verify bot permissions on the target document","Log the response body for every non-200"],"tags":["http","api","wps"],"backgroundTag":"http-error-response","analyzedSha":"4000b2338aa6e850c99df54f8b0ed6ed7460b401","analyzedAt":"2026-09-06T11:45:09.575Z","contentChangedAt":"2026-09-06T11:45:09.575Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}