You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

goquery爬取script标签内容写文件为空,如何修正代码?

goquery爬虫内容可打印但文件写入为空问题修复方案

问题根因

  • 选择器匹配规则过于宽松:原代码doc.Find("script")匹配页面所有script标签,且仅判断是否存在type属性,未校验type值是否为目标的myjson,导致匹配到无内容的无关script标签
  • 文件写入逻辑存在覆盖问题:循环内每次匹配到符合条件的标签都会调用os.Create,该方法会直接清空目标路径已有文件内容,先写入的空内容会覆盖后续有效内容,或后续内容写入被异常中断

修复方案

方案1:使用精准属性选择器(推荐)

goquery支持CSS属性选择器,可直接定位到type="myjson"的目标script标签,无需遍历所有标签,代码更简洁高效:

// 直接精准匹配目标script标签
targetScript := doc.Find(`script[type="myjson"]`).First()
if targetScript.Length() == 0 {
    panic("未找到目标myjson标签")
}
content := targetScript.Text()
// 确认内容非空再写入文件
if content != "" {
    filepath := "mypath"
    file, err := os.Create(filepath)
    if err != nil {
        panic("COULD NOT CREATE FILE")
    }
    // 写入内容
    _, err = file.WriteString(content)
    if err != nil {
        panic("写入文件失败")
    }
    // 主动刷缓存到磁盘
    _ = file.Sync()
    file.Close()
    fmt.Println(content)
}

方案2:修正原有遍历逻辑的判断条件

如果需要保留遍历逻辑,可在原有判断中新增type值校验,同时避免循环内重复创建覆盖同一文件:

var targetContent string
doc.Find("script").Each(func(i int, element *goquery.Selection) {
    typeVal, exists := element.Attr("type")
    // 同时校验type存在且值为myjson
    if exists && typeVal == "myjson" {
        targetContent = element.Text()
        // 找到目标后可提前终止遍历
        return
    }
})
if targetContent == "" {
    panic("未找到有效内容")
}
// 统一执行文件写入逻辑
filepath := "mypath"
file, err := os.Create(filepath)
if err != nil {
    panic("COULD NOT CREATE FILE")
}
defer file.Close()
_, err = file.WriteString(targetContent)
if err != nil {
    panic("写入文件失败")
}
_ = file.Sync()
fmt.Println(targetContent)

注意事项

  • 尽量使用defer file.Close()保证文件句柄正常关闭,避免资源泄漏
  • 写入后调用file.Sync()主动将内存缓存写入磁盘,避免操作系统缓存延迟导致的文件空内容问题
  • 匹配到内容后再执行文件创建逻辑,避免空内容覆盖有效文件

内容的提问来源于stack exchange,提问作者Lorenzo Romani

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 17:27:02