剥离PostgreSQL中的HTML标记

sam*_*ach 5 regex postgresql

如何在PostgreSQL中删除HTML标签,以便保留标签内的数据?

我通过谷歌搜索找到了一些解决方案,但他们也在标签之间删除了文本!

aco*_*hen 13

select regexp_replace(content, E'<[^>]+>', '', 'gi') from message;
Run Code Online (Sandbox Code Playgroud)

  • 我真的很想知道为什么这个解决方案被低估了.这是问题的确切答案,而且效果很好.上面的所有警告都是有序的,但是对于这样的请求有一些有效的用例,比如在测试或开发场景中,您只想在Web界面中查看某些数据而不创建任何PostgreSQL或其他代码.为了这个目的,它就像魅力一样.+1 (6认同)
  • @Olaf 投反对票,因为这对于例如索引而言无论如何都不够-您至少必须处理诸如“"”之类的实体和其他可能被转义的特殊字符,因此这种方法可能太天真而无法实现-世界使用。 (6认同)

Pet*_*uss 11

使用xpath

使用XML数据类型提供数据库,而不是使用"第二类"TEXT,因为将HTML转换为XHTML非常简单(请参阅HTML-Tidy或标准DOM loadHTML()saveXML()方法).

!这很快,而且非常安全!

共同信息检索需要,不是一个完整的内容,而是XHTML中的一些东西,所以xpath功能很好.

示例:使用以下命令检索所有段落 class="fn":

  WITH needinfo AS (
    SELECT *, xpath('//p[@class="fn"]//text()', xhtml)::text[] as frags
    FROM t 
  ) SELECT array_to_string(frags,' ') AS my_p_fn2txt
    FROM needinfo
    WHERE array_length(frags , 1)>0
  -- for full content use xpath('//text()',xhtml)
Run Code Online (Sandbox Code Playgroud)

正则表达式解决方案......

我不推荐,因为它不是一个"信息检索"解决方案......而且,正如@James和其他人在这里评论的那样,正则表达式解决方案并非如此.

我喜欢"纯SQL",对我来说比使用Perl(se @ Daniel的解决方案)或其他更好.

 CREATE OR REPLACE FUNCTION strip_tags(TEXT) RETURNS TEXT AS $$
     SELECT regexp_replace(
        regexp_replace($1, E'(?x)<[^>]*?(\s alt \s* = \s* ([\'"]) ([^>]*?) \2) [^>]*? >', E'\3'), 
       E'(?x)(< [^>]*? >)', '', 'g')
 $$ LANGUAGE SQL;
Run Code Online (Sandbox Code Playgroud)

看到这一点,许多其他变化的siafoo.net,eskpee.wordpress,......并在这里#1.


Dan*_*ité 8

选择不仅限于使用基于不充分的正则表达式的弱解析器在服务器端执行,或者使用强大的解析器在客户端执行它.它也可以通过强大的解析器在服务器端实现.

这是PL/PerlU中的一个例子,它利用了CPAN的 HTML模块.

CREATE FUNCTION extract_contents_from_html(text) returns text AS $$
  use HTML::TreeBuilder;
  use HTML::FormatText;
  my $tree = HTML::TreeBuilder->new;
  $tree->parse_content(shift);
  my $formatter = HTML::FormatText->new(leftmargin=>0, rightmargin=>78);
  $text = $formatter->format($tree);
$$ LANGUAGE plperlu;
Run Code Online (Sandbox Code Playgroud)

演示:

select extract_contents_from_html('<html><body color="white">Hi there!<br>How are you?</body></html>') ;
Run Code Online (Sandbox Code Playgroud)

输出:

     extract_contents_from_html 
    ----------------------------
     Hi there!
     How are you?

一个需要注意的的警告来与不可信的语言,虽然.

  • 这种技术的一个优点是,如果您将实际的HTML存储在数据库中但想要仅对内容进行文本搜索,则无需将内容冗余地存储到HTML中.您可以在(例如)`to_tsvector('english',extract_contents_from_html(html_text))上创建GiST或GIN索引` - 我使用引用poppler的函数从数据库中的PDF文件中提取文本时做了类似的事情.图书馆. (3认同)

Win*_*ail 6

在RDBMS中执行的任何解决方案都将涉及字符串处理或正则表达式:据我所知,没有办法在数据库中以符合标准的安全方式操作HTML.重申一下,你所要求的是非常非常不安全的.

更好的选择是在您的应用程序中执行此操作.这是应用程序逻辑,而不是存储层的工作或关注点.

一个很好的方法(在PHP中,至少)是HTML净化器. 不要在JavaScript中执行此操作,用户可以非常轻松地篡改它.

  • 这是典型的狂热。我们生活在一个广阔的世界中,有时做一些在某些情况下可能危险的事情可以安全地用于提供巨大的性能提升,而无需完全重新构建现有的解决方案。这为原始发帖人提供了宝贵的建议,但这并不是重点——谷歌将您带到这里了解一般情况,并且其他解决方案可以满足有效的用例。 (2认同)