0

我正在尝试使用 GoQuery 从页面中获取内容,但由于某些原因,我无法在换行符 (br) 上进行拆分。

HTML 看起来像这样:

<ul>
    <li>I'm skipped</li>

    <li> 
        Text Into  - <p>Whatever</p>
        <p>
            Line 1<br />
            Line 2<br />
            Line 3<br />
            Line 4<br />
            Line N
        </p>
    </li> 
</ul>

去代码:

doc, err := goquery.NewDocumentFromReader(res.Body)
if err != nil {
    panic(err)
}

doc.Find("ul").Each(func(i int, s *goquery.Selection) {

    str := s.Find("li p").Next().Text()

    fmt.Println(str, "--")

})

由于某种原因,我无法将每一行(由 p 标签中的 break 分隔)作为单个项目。上面的代码输出是:

Line1Line2Line3Line4LineN--

但我试图实现的输出应该是这样的:

Line1--
Line2--
Line3--
Line4--
LineN--

由于我是新手,如果有不清楚的地方,请在评论中告诉我,所以我会尽可能多地解释它。

谢谢。

4

4 回答 4

1

我运行了您显示的代码,并且在字符串中得到了换行符。假设您使用的是最新版本的 goquery,除非您的 html 不是

<p>
    Line 1<br />
    Line 2<br />
    Line 3<br />
    Line 4<br />
    Line N
</p>

但实际上是这样的:

<p>
    Line 1<br />Line 2<br />Line 3<br />Line 4<br />Line N
</p>

(请记住,例如,当您打开 chrome 开发工具时,它可能会将其显示为前者,即使实际来源是后者)

在这种情况下,这是预期的行为:

let html_1 = $(`<p>
        Line 1<br />
        Line 2<br />
        Line 3<br />
        Line 4<br />
        Line N
    </p>`);

let html_2 = $(`<p>
        Line 1<br />Line 2<br />Line 3<br />Line 4<br />Line N
    </p>`);
    
console.log({html1: html_1.text(), html2: html_2.text()});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

要解决,您可能只需执行以下操作:

p := s.Find("li p").Next()
p.SetHtml(strings.Replace(p.Html(), "<br />", "<br />\n", -1)).Text()

虽然,您可能不得不考虑是否使用<br/><br /><br>因为我不确定它会如何渲染它。

于 2018-05-08T19:06:39.470 回答
1

.Text()将要:

Text 获取匹配元素集中每个元素的组合文本内容,包括它们的后代。

所以你真正想要做的是获取内容并过滤掉任何 br 标签。正如戴夫的回答所说,那里有换行符,所以我也修剪了那些:

package main

import (
    "fmt"
    "github.com/PuerkitoBio/goquery"
    "strings"
)

var input string = `
<ul>
    <li>I'm skipped</li>

    <li> 
        Text Into  - <p>Whatever</p>
        <p>
            Line 1<br />
            Line 2<br />
            Line 3<br />
            Line 4<br />
            Line N
        </p>
    </li> 
</ul>
`

func main() {
    doc, err := goquery.NewDocumentFromReader(strings.NewReader(input))
    if err != nil {
        panic(err)
    }

    doc.Find("ul").Each(func(i int, s *goquery.Selection) {

        p := s.Find("li p").Next()
        p.Contents().Each(func(i int, s *goquery.Selection) {
            if !s.Is("br") {
                fmt.Println(strings.TrimSpace(s.Text()), "--")
            }

        })

    })
}

生产:

Line 1 --
Line 2 --
Line 3 --
Line 4 --
Line N --
于 2018-05-08T19:40:36.027 回答
0

我认为如果在调用方法<br/>之前只替换为 '\n' 或 '--'会更好。.Text()

    // html is the result of `.Html()` method
    str := strings.Replace(html, "<br/>", "\\n", -1)
    doc, err := goquery.NewDocumentFromReader(strings.NewReader(str))
    if err != nil {
        return ""
    }
    return doc.Text()
于 2019-06-04T02:39:20.323 回答
0

好的,我设法找到了一个解决方案。不确定它是否正确,所以如果有人有更好的东西 - 请分享。

所以我基本上,将值存储li p为 HTML,然后在每个标签上使用strings.Split中断,并且由于返回字符串切片,我只是循环遍历它。brstrings.Split

title, err := s.Find("li p").Next().Html()
if err != nil {
    panic(err)
}

splittedTitles := strings.Split(title, "<br/>")

for _, str := range splittedTitles {
    fmt.Println(str, "--")
}
于 2018-05-08T19:05:30.333 回答