{"record":{"id":"211250f6035b44cc","repo":"fish2018/pansou","slug":"d-d","errorCode":null,"errorMessage":"无效的加密区间 %d:%d","messagePattern":"无效的加密区间 (.+?):(.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"plugin/yingso/yingso.go","lineNumber":330,"sourceCode":"\tif len(data) > maxResponseSize {\n\t\treturn fmt.Errorf(\"响应超过 %d 字节\", maxResponseSize)\n\t}\n\tif resp.StatusCode != http.StatusOK {\n\t\treturn fmt.Errorf(\"HTTP %d: %s\", resp.StatusCode, strings.TrimSpace(string(data)))\n\t}\n\tif err := jsonutil.Unmarshal(data, target); err != nil {\n\t\treturn fmt.Errorf(\"解析响应失败: %w\", err)\n\t}\n\treturn nil\n}\n\nfunc encryptPayload(payload interface{}, config apiConfig) (encryptedPayload, error) {\n\tno, err := randomToken(24)\n\tif err != nil {\n\t\treturn encryptedPayload{}, err\n\t}\n\tif config.Start < 0 || config.End <= config.Start || config.End > len(no) {\n\t\treturn encryptedPayload{}, fmt.Errorf(\"无效的加密区间 %d:%d\", config.Start, config.End)\n\t}\n\n\tencoded, err := jsonutil.MarshalString(payload)\n\tif err != nil {\n\t\treturn encryptedPayload{}, err\n\t}\n\treturn encryptedPayload{\n\t\tNo:   no,\n\t\tInfo: xorUTF16(encoded, no[config.Start:config.End]),\n\t}, nil\n}\n\nfunc randomToken(length int) (string, error) {\n\tconst alphabet = \"0123456789abcdefghijklmnopqrstuvwxyz\"\n\tdata := make([]byte, length)\n\tif _, err := rand.Read(data); err != nil {\n\t\treturn \"\", err\n\t}","sourceCodeStart":312,"sourceCodeEnd":348,"githubUrl":"https://github.com/fish2018/pansou/blob/beaa56133755a548ebc51b090b3816e2ae044aa6/plugin/yingso/yingso.go#L312-L348","documentation":"encryptPayload validates config.Start/End against a 24-byte random token length and fails with '无效的加密区间 %d:%d' when the range is invalid: Start < 0, End <= Start, or End > len(no) (24). This is a configuration validation error inside the plugin, not a network issue.","triggerScenarios":"A yingso apiConfig has Start negative, End less than or equal to Start, or End greater than 24 (the fixed random token length), passed via search or resolveItem.","commonSituations":"Mis-edited config file with wrong start/end offsets; config copied from another plugin with a different token size; assumptions that End indexes a payload field rather than the 24-byte token; off-by-one treating End as inclusive index into a 0..23 slice.","solutions":["Inspect the apiConfig values for Start/End in your config and ensure 0 <= Start < End <= 24","Remember End indexes the 24-byte random token (randomToken(24)), not the payload; cap End at 24","Fix negative or swapped Start/End values (End must be strictly greater than Start)","Validate config at load time with the same predicate used in encryptPayload"],"exampleFix":"// before\nStart: 0, End: 32\n// after\nStart: 0, End: 24 // End must satisfy 0 <= Start < End <= 24","handlingStrategy":"validation","validationCode":"if cfg.Start < 0 || cfg.End <= cfg.Start || cfg.End > 24 {\n    return fmt.Errorf(\"无效的加密区间 %d:%d\", cfg.Start, cfg.End)\n}","typeGuard":"func validRange(start, end int) bool { return start >= 0 && end > start && end <= 24 }","tryCatchPattern":"payload, err := encryptPayload(p, cfg)\nif err != nil {\n    if strings.Contains(err.Error(), \"无效的加密区间\") {\n        return fmt.Errorf(\"配置错误: start/end 必须满足 0 <= start < end <= 24: %w\", err)\n    }\n    return err\n}","preventionTips":["Validate Start/End when loading the plugin config, before any request","Remember the range indexes randomToken(24), so End must never exceed 24","Treat End as an exclusive-style bound strictly greater than Start","Add a unit test covering the boundary values 0, 24, and swapped ranges"],"tags":["config","validation","crypto","bounds"],"backgroundTag":"invalid-config-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"}