{"record":{"id":"09e996702868cfce","repo":"shadow1ng/fscan","slug":"webscan-poc-file-read-failed","errorCode":"webscan_poc_file_read_failed","errorMessage":"webscan_poc_file_read_failed %s: %w","messagePattern":"webscan_poc_file_read_failed (.+?): %w","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"webscan/lib/Client.go","lineNumber":438,"sourceCode":"\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"%s %s: %w\", i18n.GetText(\"webscan_poc_parse_failed\"), fileName, err)\n\t}\n\n\t// 转换为fscan内部格式\n\tpoc, err := universalPoc.ToFscanPoc()\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"%s %s: %w\", i18n.GetText(\"webscan_poc_convert_failed\"), fileName, err)\n\t}\n\n\treturn poc, nil\n}\n\n// LoadPoc 从内嵌文件系统加载单个POC\nfunc LoadPoc(fileName string, Pocs embed.FS) (*Poc, error) {\n\t// 读取POC文件内容\n\tyamlFile, err := Pocs.ReadFile(\"pocs/\" + fileName)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"%s %s: %w\", i18n.GetText(\"webscan_poc_file_read_failed\"), fileName, err)\n\t}\n\n\t// 解析YAML内容\n\treturn parsePocYAML(yamlFile, fileName)\n}\n\n// SelectPoc 根据名称关键字选择POC文件\nfunc SelectPoc(Pocs embed.FS, pocname string) []string {\n\tentries, err := Pocs.ReadDir(\"pocs\")\n\tif err != nil {\n\t\tcommon.LogError(i18n.Tr(\"webscan_poc_dir_read_failed\", err))\n\t}\n\n\tvar foundFiles []string\n\t// 查找匹配关键字的POC文件\n\tfor _, entry := range entries {\n\t\tif strings.Contains(entry.Name(), pocname) {\n\t\t\tfoundFiles = append(foundFiles, entry.Name())","sourceCodeStart":420,"sourceCodeEnd":456,"githubUrl":"https://github.com/shadow1ng/fscan/blob/95cc12e753bf43de7004e5aef42a9ffba3934303/webscan/lib/Client.go#L420-L456","documentation":"LoadPoc reads a POC from an embedded filesystem (embed.FS) at path \"pocs/<fileName>\" and wraps any ReadFile error under webscan_poc_file_read_failed. It fires when the embedded FS has no such entry, i.e. the file was not compiled into the binary or the name is wrong.","triggerScenarios":"LoadPoc(fileName, Pocs) where \"pocs/\"+fileName does not exist in the embed.FS — wrong filename, missing pocs/ prefix handling, or the POC file was added to disk but the binary wasn't rebuilt after the embed.","commonSituations":"Typo in POC filename or case mismatch, loading a POC that exists on disk but is not embedded (embed only includes files matching the //go:embed pattern at build time), calling LoadPoc with a full path instead of a bare filename.","solutions":["Verify the file exists at pocs/<fileName> in the source tree and matches the //go:embed pocs/* pattern","Rebuild the binary after adding new POC files (embed is compile-time)","Pass only the bare filename (e.g. \"tomcat.yml\"), not \"pocs/tomcat.yml\" or an absolute path","Use LoadPocbyPath instead if you need to load from the real filesystem"],"exampleFix":"// before (full path passed to embedded FS loader)\npoc, err := LoadPoc(\"pocs/tomcat.yml\", pocsFS)\n// after (bare filename)\npoc, err := LoadPoc(\"tomcat.yml\", pocsFS)\n// or for on-disk files:\npoc, err := LoadPocbyPath(\"/path/to/tomcat.yml\")","handlingStrategy":"fallback","validationCode":"if _, err := pocsFS.ReadFile(\"pocs/\" + fileName); err != nil {\n    return fmt.Errorf(\"poc %q not embedded: %w\", fileName, err)\n}","typeGuard":null,"tryCatchPattern":"poc, err := LoadPoc(name, pocsFS)\nif err != nil {\n    if _, statErr := os.Stat(filepath.Join(\"pocs\", name)); statErr == nil {\n        poc, err = LoadPocbyPath(filepath.Join(\"pocs\", name))\n    }\n}","preventionTips":["Rebuild after adding POC files — embed.FS is compile-time only","Pass bare filenames; LoadPoc prepends \"pocs/\" itself","Match the //go:embed pattern exactly (watch case sensitivity)"],"tags":["go","embed","poc","file-read","webscan"],"backgroundTag":"file-not-found","analyzedSha":"95cc12e753bf43de7004e5aef42a9ffba3934303","analyzedAt":"2026-09-06T17:07:30.094Z","contentChangedAt":"2026-09-06T17:07:30.094Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}