{"record":{"id":"cf4556b64c9fa827","repo":"Tencent/WeKnora","slug":"mineru-cloud-poll-w","errorCode":null,"errorMessage":"MinerU Cloud poll: %w","messagePattern":"MinerU Cloud poll: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/infrastructure/docparser/mineru_cloud_converter.go","lineNumber":90,"sourceCode":"\t\text = \".pdf\"\n\t}\n\tfileName := strings.TrimSuffix(req.FileName, ext) + ext\n\tif fileName == ext {\n\t\tfileName = \"document\" + ext\n\t}\n\n\tbatchID, uploadURL, err := c.applyUploadURLs(ctx, fileName, ext)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"MinerU Cloud apply upload URLs: %w\", err)\n\t}\n\n\tif err := c.uploadFile(ctx, uploadURL, content); err != nil {\n\t\treturn nil, fmt.Errorf(\"MinerU Cloud file upload: %w\", err)\n\t}\n\n\tmdContent, imageRefs, err := c.pollBatchResult(ctx, batchID)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"MinerU Cloud poll: %w\", err)\n\t}\n\n\tmdContent, imageRefs = ensureOriginalImageRef(req, mdContent, imageRefs)\n\n\treturn &types.ReadResult{\n\t\tMarkdownContent: mdContent,\n\t\tImageRefs:       imageRefs,\n\t}, nil\n}\n\n// --- batch upload API ---\n\ntype batchApplyResponse struct {\n\tCode int    `json:\"code\"`\n\tMsg  string `json:\"msg\"`\n\tData struct {\n\t\tBatchID  string   `json:\"batch_id\"`\n\t\tFileURLs []string `json:\"file_urls\"`","sourceCodeStart":72,"sourceCodeEnd":108,"githubUrl":"https://github.com/Tencent/WeKnora/blob/988cbb03305e055d8ebb7d46d9ac6cc0803cd074/internal/infrastructure/docparser/mineru_cloud_converter.go#L72-L108","documentation":"Once uploaded, Read polls pollBatchResult until MinerU finishes converting the batch; any failure or terminal error state is wrapped as \"MinerU Cloud poll: %w\". This covers both transport errors while polling and the job ending in a failed/expired state.","triggerScenarios":"Read -> pollBatchResult returned an error: polling HTTP request failed, context deadline exceeded while waiting, or the batch reached a failed/unknown state instead of producing markdown.","commonSituations":"Conversion job failed server-side (unsupported/corrupt document); context timeout shorter than conversion duration for big PDFs; MinerU service degraded during polling; batch ID invalid or job expired before completion.","solutions":["Inspect the wrapped cause: if the job state is 'failed', check the MinerU dashboard/logs for the document-level error (often an unsupported or corrupted file).","Increase the context timeout so large documents have time to convert before polling gives up.","Validate the input document opens correctly locally (not corrupt/encrypted PDF).","Retry Read on transient 5xx/network errors during polling.","Retry with a smaller document if conversions consistently time out."],"exampleFix":"// before: too-short timeout kills long conversions\nctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)\n// after: allow several minutes for cloud conversion\nctx, cancel := context.WithTimeout(context.Background(), 10*time.Minute)","handlingStrategy":"retry","validationCode":"if encryptedOrCorruptPDF(path) { // e.g. try opening with a PDF lib\n    return fmt.Errorf(\"%s is corrupt/encrypted; MinerU conversion will fail\", path)\n}\nctx, cancel := context.WithTimeout(ctx, 10*time.Minute) // allow long conversions\ndefer cancel()","typeGuard":null,"tryCatchPattern":"res, err := converter.Read(ctx, req)\nif err != nil {\n    if strings.Contains(err.Error(), \"MinerU Cloud poll\") {\n        if errors.Is(ctx.Err(), context.DeadlineExceeded) {\n            return fmt.Errorf(\"conversion timed out; increase context timeout or split the document\")\n        }\n        return retryWithBackoff(ctx, 2, func() error { return readAgain(ctx, req) })\n    }\n    return err\n}","preventionTips":["Budget a generous context timeout proportional to document size (minutes, not seconds).","Validate input documents open correctly (not encrypted/truncated) before cloud conversion.","Check batch state in the MinerU dashboard when polling fails — server-side job failures are reported there.","Split very large documents so individual conversions finish within the polling window."],"tags":["polling","cloud-api","timeout","async-job"],"backgroundTag":"job-polling-failed","analyzedSha":"988cbb03305e055d8ebb7d46d9ac6cc0803cd074","analyzedAt":"2026-09-02T14:41:08.344Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}