美文网首页工具
iOS HTML解析库Ono的一个缺陷

iOS HTML解析库Ono的一个缺陷

作者: 知傲 | 来源:发表于2018-02-23 16:59 被阅读382次

    以前写的,不知道怎么就不见了,重发
    Ono是iOS & OS X平台一个优秀的XML、HTML解析库,内部其实是对libxml2的封装。最近在使用的时候遇到了一个bug缺陷。
    业务代码如下:

    ONOXMLDocument *document = [ONOXMLDocument HTMLDocumentWithString:htmlString encoding:NSUTF8StringEncoding error:nil];
    ONOXMLElement *element = [document firstChildWithXPath:@"/html/body/div"];
    NSString *htmlContent = element.description;
    

    这段代码的目的是提取html中的第一个div元素,通过XPath找到元素后调用description方法获得元素的html字符串。然而,解析之后发现<tag></tag>这样的空内容标签变成了<tag />。这种变化对XML来说没什么影响,但是对HTML影响很大,举个例子:

    <h1></h1><p>hello world</p>
    

    代码效果差不多是这样的


    调用description之后的html
    <h1/><p>hello world</p>
    

    效果差不多是这样的


    后面的<p>标签被加上<h1>的效果。
    问题就出在description方法上,它的实现是这样的

    - (NSString *)description {
        xmlBufferPtr buffer = xmlBufferCreate();
        xmlNodeDump(buffer, self.xmlNode->doc, self.xmlNode, 0, false);
        NSString *rawXMLString = @((const char *)xmlBufferContent(buffer));
        xmlBufferFree(buffer);
        return rawXMLString;
    }
    

    xmlNodeDump得到的是去除空标签的buff。经过一番搜索,网上提到要使用xmlsave模块,保存的时候options加上XML_SAVE_NO_EMPTY。修改之后的代码;

    - (NSString *)description {
        xmlBufferPtr buffer = xmlBufferCreate();
        xmlSaveCtxtPtr saveCtxtPtr = xmlSaveToBuffer(buffer,NULL, XML_SAVE_NO_EMPTY);
        long result = xmlSaveTree(saveCtxtPtr, self.xmlNode);
        xmlSaveClose(saveCtxtPtr);
        NSString *rawXMLString = result < 0 ? nil : @((const char *)xmlBufferContent(buffer));
        xmlBufferFree(buffer);
        return rawXMLString;
    }
    

    一个挺简单的问题解决,希望能帮到遇到同样问题的人。

    相关文章

      网友评论

        本文标题:iOS HTML解析库Ono的一个缺陷

        本文链接:https://www.haomeiwen.com/subject/wdbxxftx.html