{"record":{"id":"0305baf040079b66","repo":"fish2018/pansou","slug":"gzip-reader-w-0305ba","errorCode":null,"errorMessage":"创建gzip reader失败: %w","messagePattern":"创建gzip reader失败: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"plugin/xb6v/xb6v.go","lineNumber":356,"sourceCode":"\n\treturn keywordFilteredResults, nil\n}\n\n// getResponseReader 获取响应读取器（处理gzip压缩）\nfunc (p *Xb6vPlugin) getResponseReader(resp *http.Response) (io.Reader, error) {\n\tvar reader io.Reader = resp.Body\n\n\t// 检查Content-Encoding\n\tcontentEncoding := resp.Header.Get(\"Content-Encoding\")\n\tif p.debugMode {\n\t\tlog.Printf(\"[Xb6v] Content-Encoding: %s\", contentEncoding)\n\t}\n\n\t// 如果是gzip压缩，手动解压\n\tif contentEncoding == \"gzip\" {\n\t\tgzReader, err := gzip.NewReader(resp.Body)\n\t\tif err != nil {\n\t\t\treturn nil, fmt.Errorf(\"创建gzip reader失败: %w\", err)\n\t\t}\n\t\treader = gzReader\n\t}\n\n\treturn reader, nil\n}\n\n// extractDetailURLs 从搜索结果页面提取详情页链接和日期\nfunc (p *Xb6vPlugin) extractDetailURLs(doc *goquery.Document) []DetailPageInfo {\n\tvar detailPages []DetailPageInfo\n\turlMap := make(map[string]bool) // 去重\n\n\t// 只从搜索结果区域提取链接，搜索结果在 ul#post_container 中\n\tdoc.Find(\"ul#post_container li.post\").Each(func(i int, li *goquery.Selection) {\n\t\t// 提取详情页链接\n\t\tlinkEl := li.Find(\"a[href*='.html']\")\n\t\tif linkEl.Length() == 0 {\n\t\t\treturn","sourceCodeStart":338,"sourceCodeEnd":374,"githubUrl":"https://github.com/fish2018/pansou/blob/beaa56133755a548ebc51b090b3816e2ae044aa6/plugin/xb6v/xb6v.go#L338-L374","documentation":"getResponseReader manually decompresses responses whose Content-Encoding header is gzip (the client presumably doesn't auto-decompress). gzip.NewReader(resp.Body) validates the gzip header immediately; if the body isn't actually gzip data, this error wraps 'gzip: invalid header' and the caller aborts.","triggerScenarios":"Server (or an intermediary like a misconfigured proxy/CDN) sends Content-Encoding: gzip but the body is plain text/HTML, chunked garbage, or an error page — gzip.NewReader fails on the first bytes. Called from searchImpl and fetchDetailPageMagnetLinks for every xb6v response.","commonSituations":"Reverse proxy (nginx) double-encoding or mislabeling; site serving brotli/deflate mislabeled as gzip; anti-bot layer returning a plain challenge body with stale compression headers; TLS-terminating proxy altering the body.","solutions":["Retry; if consistent, the mirror/proxy is mislabeling encodings — switch mirrors or bypass the proxy.","Verify with curl -H 'Accept-Encoding: gzip' -v whether the body truly is gzip when the header claims so.","Disable Accept-Encoding: gzip in the plugin's request headers so the server returns identity encoding.","Patch getResponseReader to sniff magic bytes (1f 8b) before creating the gzip reader and fall back to the raw body."],"exampleFix":"// before\nif contentEncoding == \"gzip\" {\n\tgzReader, err := gzip.NewReader(resp.Body)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"创建gzip reader失败: %w\", err)\n\t}\n\treader = gzReader\n}\n// after: sniff magic bytes and fall back to raw body\nif contentEncoding == \"gzip\" {\n\tbr := bufio.NewReader(resp.Body)\n\tmagic, _ := br.Peek(2)\n\tif len(magic) == 2 && magic[0] == 0x1f && magic[1] == 0x8b {\n\t\tgzReader, err := gzip.NewReader(br)\n\t\tif err != nil {\n\t\t\treturn nil, fmt.Errorf(\"创建gzip reader失败: %w\", err)\n\t\t}\n\t\treader = gzReader\n\t} else {\n\t\tlog.Printf(\"[Xb6v] Content-Encoding为gzip但body非gzip，按原文读取\")\n\t\treader = br\n\t}\n}","handlingStrategy":"validation","validationCode":"func isGzip(body []byte) bool { return len(body) >= 2 && body[0] == 0x1f && body[1] == 0x8b }","typeGuard":"func isGzipError(err error) bool { return err != nil && strings.Contains(err.Error(), \"gzip: invalid header\") }","tryCatchPattern":"results, err := pluginSearch(keyword)\nif err != nil && isGzipError(err) {\n\t// server mislabels Content-Encoding — retry without gzip or switch mirror\n}","preventionTips":["Bypass or fix proxies that rewrite Content-Encoding headers.","Verify mirror responses with curl --compressed before relying on them.","Send no Accept-Encoding (identity) if the mirror mishandles gzip."],"tags":["gzip","http","content-encoding","decompression"],"backgroundTag":"invalid-argument-value","analyzedSha":"beaa56133755a548ebc51b090b3816e2ae044aa6","analyzedAt":"2026-09-07T00:31:18.025Z","contentChangedAt":"2026-09-07T00:31:18.025Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}