基于动态正则表达式的XPath搜索

Man*_*glu 2 java xml xslt xpath xpath-2.0

我有一个类似下面的XML:

    <?xml version="1.0" encoding="UTF-8"?>
    <Configuration>
        <Destinations>
            <Destination name="DEST1" >
                <From>AMA*</From>
            </Destination>

            <Destination name="DEST2" >
                <From>AMAZON</From>
            </Destination>

                           <Destination name="DEST3" >
                <From>EBAY</From>
            </Destination>

                           <Destination name="DEST4" >
                <From>*</From>
            </Destination>

        </Destinations>
    </Configuration>
Run Code Online (Sandbox Code Playgroud)

我想查询并找出与提供的输入匹配的所有设计.

如果我指定EBAY我希望xpath返回节点名称= DEST3和DEST4(它不关心值)但是如果我指定AMAZON它需要返回DEST1,DEST2和DEST4,因为DEST1中的AMA*支持通配符.

到目前为止,我的XPath看起来像这样:

/目的地[(From ='''或From ='*')))/ @ name

如果指定了input,则动态创建XPATH表达式并将传入值插入 领域

除了From之外,我的XML中还有其他元素.

感谢是否有人可以指出这一点.

谢谢,Manglu

Dim*_*hev 7

以下XPath 2.0表达式表示所需的选择:

  /*/*/*[From[matches($pPat, replace(., '\*', '.*'))]]
Run Code Online (Sandbox Code Playgroud)

说明:

  1. $pPat变量包含搜索模式(如"EBAY","AMAZON"等).

  2. 标准XPath 2.0函数matches()用于将任何From元素的值与字符串模式匹配.

  3. 任何From元素的值都将转换为XPath 2.0支持的标准正则表达式.为此目的,任何出现'*'("\*"为了不被视为正则'*'表达式中使用的特殊字符而是作为普通字符而被转义)将被字符串替换".*"

测试:

我使用了以下XSLT 2.0转换并验证了上面的XPath 2.0表达式按预期选择了元素.要使用它,请将全局参数$ pPat的值替换为任何所需的值.

<xsl:stylesheet version="2.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema">
    <xsl:output omit-xml-declaration="yes"/>

    <xsl:param name="pPat" as="xs:string"
     select="'AMAZON'"/>

    <xsl:variable name="vsrchResult" as="element()*"
     select="/*/*/*[From[matches($pPat, replace(., '\*', '.*'))]]"/>

    <xsl:template match="/">
      <xsl:copy-of select="$vsrchResult"/>
    </xsl:template>
</xsl:stylesheet>
Run Code Online (Sandbox Code Playgroud)

将此转换应用于最初提供的XML文档时:

<Configuration>
    <Destinations>
        <Destination name="DEST1" >
            <From>AMA*</From>
        </Destination>
        <Destination name="DEST2" >
            <From>AMAZON</From>
        </Destination>
        <Destination name="DEST3" >
            <From>EBAY</From>
        </Destination>
        <Destination name="DEST4" >
            <From>*</From>
        </Destination>
    </Destinations>
</Configuration>
Run Code Online (Sandbox Code Playgroud)

生成所需的输出:

<Destination name="DEST1">
            <From>AMA*</From>
        </Destination><Destination name="DEST2">
            <From>AMAZON</From>
        </Destination><Destination name="DEST4">
            <From>*</From>
        </Destination>
Run Code Online (Sandbox Code Playgroud)