首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >选择不同命名空间中的节点的XPath

选择不同命名空间中的节点的XPath
EN

Stack Overflow用户
提问于 2015-07-10 15:27:06
回答 2查看 3.4K关注 0票数 1

我需要一些帮助才能找到一个正确的XPath表达式来从XML.中提取值。

但是,我可以使用jaxb获得值,但我需要xpath,因为我有一个决策表类型的映射规则,我希望将其外部化,如果我使用jaxb,将导致大量嵌套if / get语句,这是我想要避免的,因此需要xpath方法。

我有一个xml文件,它是根据至少4个模式构造的。我的意思是根模式在特定的点上有一个元素,上面写着xs:any和这个位置,一个基于不同模式的xml被注入,这反过来又有一个类似的xs:任何注入另一个xml以构建我所使用的最终/实际xml的xml。

这是我正在处理的实际XML结构(我有意修改了值)。

代码语言:javascript
运行
复制
<?xml version="1.0"?>
<env:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:env="CDTS-SUBMIT">
  <env:Body>
    <cdtPrefix>
      <cdtprVersion>01</cdtprVersion>
      <cdtprOperation>SUBMIT</cdtprOperation>
      <cdtprFunction>GCAMS1O</cdtprFunction>
      <cdtprDirectionFlag>O</cdtprDirectionFlag>
    </cdtPrefix>
    <cdtDataDescription>
      <cdtddVersion>01</cdtddVersion>
      <cdtddFirmId>ABC</cdtddFirmId>
      <cdtddBusinessDataFormat>GCAMS1O-XML</cdtddBusinessDataFormat>
      <cdtddReferenceNum>123</cdtddReferenceNum>
      <cdtddTrackingNum>123</cdtddTrackingNum>
      <cdtddDestination>AQ</cdtddDestination>
      <cdtddSeqNum>0000000</cdtddSeqNum>
      <cdtddCycleNum>00</cdtddCycleNum>
      <cdtddBusinessDate>00000000</cdtddBusinessDate>
    </cdtDataDescription>
    <cdtBusinessData>
      <AppHdr xmlns="urn:iso:std:iso:20022:tech:xsd:head.001.001.01" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
        <Fr>
          <FIId>
            <FinInstnId>
              <BICFI>ABC</BICFI>
            </FinInstnId>
          </FIId>
        </Fr>
        <To>
          <FIId>
            <FinInstnId>
              <BICFI>ABC   </BICFI>
            </FinInstnId>
          </FIId>
        </To>
        <BizMsgIdr>ABC</BizMsgIdr>
        <MsgDefIdr>seev.031.002.05</MsgDefIdr>
        <BizSvc>CSD</BizSvc>
        <CreDt>9999-99-99T00:02:17Z</CreDt>
      </AppHdr>
      <Document xmlns="urn:swift:xsd:seev.031.002.05" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
        <CorpActnNtfctn>
          <NtfctnGnlInf>
            <NtfctnTp>REPL</NtfctnTp>
            <PrcgSts>
              <Cd>
                <EvtCmpltnsSts>COMP</EvtCmpltnsSts>
                <EvtConfSts>CONF</EvtConfSts>
              </Cd>
            </PrcgSts>
          </NtfctnGnlInf>
          <PrvsNtfctnId>
            <Id>00000000</Id>
          </PrvsNtfctnId>
          <EvtsLkg>
            <EvtId>
              <LkdOffclCorpActnEvtId>US8</LkdOffclCorpActnEvtId>
            </EvtId>
            <LkgTp>
              <Cd>INFO</Cd>
            </LkgTp>
          </EvtsLkg>
          <CorpActnGnlInf>
            <CorpActnEvtId>000</CorpActnEvtId>
            <OffclCorpActnEvtId>US7</OffclCorpActnEvtId>
            <EvtPrcgTp>
              <Cd>DISN</Cd>
            </EvtPrcgTp>
            <EvtTp>
              <Cd>INTR</Cd>
            </EvtTp>
            <MndtryVlntryEvtTp>
              <Cd>CHOS</Cd>
            </MndtryVlntryEvtTp>
            <UndrlygScty>
              <FinInstrmId>
                <OthrId>
                  <Id>J54675AA1</Id>
                  <Tp>
                    <Cd>CUSP</Cd>
                  </Tp>
                </OthrId>
                <Desc>JASDFKASDFADSFAFADSF</Desc>
              </FinInstrmId>
              <ClssfctnTp>
                <ClssfctnFinInstrm>DBXXXX</ClssfctnFinInstrm>
              </ClssfctnTp>
            </UndrlygScty>
          </CorpActnGnlInf>
          <AcctDtls>
            <ForAllAccts>
              <IdCd>GENR</IdCd>
            </ForAllAccts>
          </AcctDtls>
          <CorpActnDtls>
            <DtDtls>
              <RcrdDt>
                <Dt>
                  <Dt>0000-04-03</Dt>
                </Dt>
              </RcrdDt>
            </DtDtls>
            <RateAndAmtDtls>
              <Intrst>
                <Rate>0</Rate>
              </Intrst>
            </RateAndAmtDtls>
            <IntrstAcrdNbOfDays>0</IntrstAcrdNbOfDays>
          </CorpActnDtls>
          <CorpActnOptnDtls>
            <OptnNb>001</OptnNb>
            <OptnTp>
              <Cd>CASH</Cd>
            </OptnTp>
            <DfltPrcgOrStgInstr>
              <DfltOptnInd>true</DfltOptnInd>
            </DfltPrcgOrStgInstr>
            <DtDtls>
              <RspnDdln>
                <Dt>
                  <DtTm>0000-04-10T20:00:00-04:00</DtTm>
                </Dt>
              </RspnDdln>
            </DtDtls>
            <PrdDtls>
              <ActnPrd>
                <Prd>
                  <StartDt>
                    <Dt>
                      <DtTm>0000-04-06T00:00:00-04:00</DtTm>
                    </Dt>
                  </StartDt>
                  <EndDt>
                    <NotSpcfdDt>UKWN</NotSpcfdDt>
                  </EndDt>
                </Prd>
              </ActnPrd>
            </PrdDtls>
            <CshMvmntDtls>
              <CdtDbtInd>CRDT</CdtDbtInd>
              <IncmTp>
                <Id>0004</Id>
                <Issr>IRSX</Issr>
              </IncmTp>
              <DtDtls>
                <PmtDt>
                  <Dt>
                    <Dt>0000-04-18</Dt>
                  </Dt>
                </PmtDt>
              </DtDtls>
              <RateAndAmtDtls>
                <IntrstRateUsdForPmt>
                  <RateTpAndAmtAndRateSts>
                    <RateTp>
                      <Cd>SCHD</Cd>
                    </RateTp>
                    <Amt Ccy="USD">21.17125</Amt>
                  </RateTpAndAmtAndRateSts>
                </IntrstRateUsdForPmt>
                <WhldgOfLclTax>
                  <Rate>15.315</Rate>
                </WhldgOfLclTax>
              </RateAndAmtDtls>
            </CshMvmntDtls>
          </CorpActnOptnDtls>
          <CorpActnOptnDtls>
            <OptnNb>002</OptnNb>
            <OptnTp>
              <Cd>CASH</Cd>
            </OptnTp>
            <OptnFeatrs>
              <Cd>ASVO</Cd>
            </OptnFeatrs>
            <DfltPrcgOrStgInstr>
              <DfltOptnInd>false</DfltOptnInd>
            </DfltPrcgOrStgInstr>
            <DtDtls>
              <RspnDdln>
                <Dt>
                  <DtTm>0000-04-10T20:00:00-04:00</DtTm>
                </Dt>
              </RspnDdln>
            </DtDtls>
            <PrdDtls>
              <ActnPrd>
                <Prd>
                  <StartDt>
                    <Dt>
                      <DtTm>0000-04-06T00:00:00-04:00</DtTm>
                    </Dt>
                  </StartDt>
                  <EndDt>
                    <NotSpcfdDt>UKWN</NotSpcfdDt>
                  </EndDt>
                </Prd>
              </ActnPrd>
            </PrdDtls>
            <CshMvmntDtls>
              <CdtDbtInd>CRDT</CdtDbtInd>
              <IncmTp>
                <Id>0004</Id>
                <Issr>IRSX</Issr>
              </IncmTp>
              <DtDtls>
                <PmtDt>
                  <Dt>
                    <Dt>0000-04-18</Dt>
                  </Dt>
                </PmtDt>
              </DtDtls>
              <RateAndAmtDtls>
                <IntrstRateUsdForPmt>
                  <RateTpAndAmtAndRateSts>
                    <RateTp>
                      <Cd>SCHD</Cd>
                    </RateTp>
                    <Amt Ccy="USD">25</Amt>
                  </RateTpAndAmtAndRateSts>
                </IntrstRateUsdForPmt>
                <WhldgOfLclTax>
                  <Rate>0</Rate>
                </WhldgOfLclTax>
              </RateAndAmtDtls>
            </CshMvmntDtls>
          </CorpActnOptnDtls>
          <AddtlInf>
            <AddtlTxt>
              <UpdDt>0000-04-04</UpdDt>
              <AddtlInf> adfafadfasdfasdfasdfsdafadfdsafdf</AddtlInf>
            </AddtlTxt>
          </AddtlInf>
          <Regar>
            <NmAndAdr>
              <Nm>Not Available</Nm>
            </NmAndAdr>
          </Regar>
          <SplmtryData>
            <Envlp>
              <Document xmlns="urn:swift:xsd:supl.001.001.05" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
                <DTCCCANOCSDDataSD1>
                  <NtfctnGnlInf>
                    <PlcAndNm>/Document/CorpActnNtfctn/NtfctnGnlInf</PlcAndNm>
                    <CretDtAndTm>0000-04-24T11:34:09</CretDtAndTm>
                    <UpdDtAndTm>0000-04-24T20:02:16</UpdDtAndTm>
                  </NtfctnGnlInf>
                  <CorpActnGnlInf>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnGnlInf</PlcAndNm>
                    <EDSMsggElgbltyFlg>true</EDSMsggElgbltyFlg>
                    <DTCFCPElctnFlg>false</DTCFCPElctnFlg>
                    <AsstSvcrPrcgFlg>true</AsstSvcrPrcgFlg>
                  </CorpActnGnlInf>
                  <UndrlygScty>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnGnlInf/UndrlygScty</PlcAndNm>
                    <CtryOfListg>DE</CtryOfListg>
                    <IncmSrcCtry>JP</IncmSrcCtry>
                    <DTCAsstClss>CRPB</DTCAsstClss>
                    <DTCAsstTp>S500</DTCAsstTp>
                  </UndrlygScty>
                  <CorpActnDtls>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnDtls</PlcAndNm>
                    <CutOffDays>0</CutOffDays>
                    <EDSMsggCtryCd>JP</EDSMsggCtryCd>
                    <RDPRefNb>yyyyyyJ54675xxxxxxxxxxxxxxxxxxxx</RDPRefNb>
                  </CorpActnDtls>
                  <CorpActnDtDtls>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnDtls/DtDtls</PlcAndNm>
                    <DTCPosCaptrDt>0000-04-03</DTCPosCaptrDt>
                  </CorpActnDtDtls>
                  <OptnDtls>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnOptnDtls[1]</PlcAndNm>
                    <XtndedOptnFeatrs>FORU</XtndedOptnFeatrs>
                    <DfltOptnFlg>true</DfltOptnFlg>
                    <RDPRefNb>yyyyyyJ54675xxxxxxxxxxxxxxxxxxxx</RDPRefNb>
                  </OptnDtls>
                  <OptnDtls>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnOptnDtls[2]</PlcAndNm>
                    <XtndedOptnFeatrs>FORX</XtndedOptnFeatrs>
                    <RDPRefNb>yyyyyyJ54675xxxxxxxxxxxxxxxxxxxx</RDPRefNb>
                  </OptnDtls>
                  <CshMvmntDtls>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnOptnDtls[1]/CshMvmntDtls[1]</PlcAndNm>
                    <DTCPayMtd>1</DTCPayMtd>
                    <DTCPayOrdr>0</DTCPayOrdr>
                    <NRATaxRptblFlg>false</NRATaxRptblFlg>
                    <DclrdGrssRate>
                      <AmtPricPerFinInstrmQty>
                        <AmtPricTp>ACTU</AmtPricTp>
                        <PricVal Ccy="USD">25</PricVal>
                        <FinInstrmQty>
                          <FaceAmt>1000</FaceAmt>
                        </FinInstrmQty>
                      </AmtPricPerFinInstrmQty>
                    </DclrdGrssRate>
                    <RDPRefNb>yyyyyyJ54675xxxxxxxxxxxxxxxxxxxx</RDPRefNb>
                  </CshMvmntDtls>
                  <CshMvmntDtls>
                    <PlcAndNm>/Document/CorpActnNtfctn/CorpActnOptnDtls[2]/CshMvmntDtls[1]</PlcAndNm>
                    <DTCPayMtd>1</DTCPayMtd>
                    <DTCPayOrdr>0</DTCPayOrdr>
                    <NRATaxRptblFlg>false</NRATaxRptblFlg>
                    <RDPRefNb>yyyyyyJ54675xxxxxxxxxxxxxxxxxxxx</RDPRefNb>
                  </CshMvmntDtls>
                  <Agt>
                    <PlcAndNm>/Document/CorpActnNtfctn/Regar/NmAndAdr</PlcAndNm>
                    <AgtId>00009910</AgtId>
                  </Agt>
                </DTCCCANOCSDDataSD1>
              </Document>
            </Envlp>
          </SplmtryData>
        </CorpActnNtfctn>
      </Document>
    </cdtBusinessData>
  </env:Body>
</env:Envelope>

我在提取像/env:Envelope/env:Body/cdtBusinessData这样的前几个元素时没有问题

cdtBusinessData是接受xs的主模式中的元素:任何 .The模式片段如下所示

代码语言:javascript
运行
复制
                <xs:element name="cdtBusinessData" form="unqualified">
                    <xs:complexType>
                        <xs:sequence>
                            <xs:any minOccurs="0"/>
                        </xs:sequence>
                    </xs:complexType>
                </xs:element>

正是从这一点出发,xpath查询的工作方式与我所期望的不一样。

也就是说,当我尝试/env:Envelope/env:Body/cdtBusinessData/Document时,它并不认为它是jxpath上的适当路径。在为选定节点提供xpath (如xpather/firepath/xpath xpather)的不同工具上,我得到不同的值,xpath没有接受这些值。

请您帮助我理解如何从上述xml中的两个嵌入式节点中提取值。

我与此斗争了相当长一段时间,并最终在这里寻求帮助。如果您能帮我纠正这个路径//env:Envelope/env:Body/cdtBusinessData/Document,我会很感激的。

更新

这是我根据您的建议提出的,我使用的是jxpath 1.3。我在这里做错什么了?我在sysouts旁边有一些评论来表示我得到了什么。

代码语言:javascript
运行
复制
package com.testbed;

import java.io.ByteArrayInputStream;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;

import org.apache.commons.jxpath.JXPathContext;

import com.xyz.ib.pb.dtcc.util.FileUtils;

public class TestJXPathApproach {

    public static void main(String a[]) throws Exception {              
        String xmlMsg = FileUtils.readFileContents("C:\\dtcc-stuff\\SR\\1.xml");
        //xmlMsg = StringUtils.remove(xmlMsg, "<?xml version=\"1.0\"?>");
        TestJXPathApproach myTest = new TestJXPathApproach();
        myTest.testJxPathExpressions(xmlMsg);
    }

    private void testJxPathExpressions(String xmlMsg) {
        org.w3c.dom.Document doc = null;
        try {
            DocumentBuilder builder = DocumentBuilderFactory.newInstance().newDocumentBuilder();
            ByteArrayInputStream bais = new ByteArrayInputStream(xmlMsg.getBytes("UTF8"));
            doc = builder.parse(bais);
            bais.close();
            JXPathContext context = JXPathContext.newContext(doc);
            context.setLenient(true);
            context.registerNamespace("d", "urn:swift:xsd:seev.031.002.05");
            context.registerNamespace("dd", "urn:swift:xsd:supl.001.001.05");


            String cdtddTrackingNumVal = (String)context.getValue("/env:Envelope/env:Body/cdtDataDescription/cdtddTrackingNum");
            System.out.println("cdtddTrackingNumVal : "+cdtddTrackingNumVal); // prints the value correctly


            String cdVal = (String)context.getValue("/env:Envelope/env:Body/cdtBusinessData/d:Document/CorpActnNtfctn/CorpActnGnlInf/EvtTp/Cd");
            System.out.println("cdVal : "+cdVal);// prints null with namespace mappping specified

            cdVal = (String)context.getValue("/env:Envelope/env:Body/cdtBusinessData/Document/CorpActnNtfctn/CorpActnGnlInf/EvtTp/Cd");
            System.out.println("cdVal : "+cdVal);// prints null with no namespace mapping 

            cdVal = (String)context.getValue("/env:Envelope/env:Body/cdtBusinessData/*:Document/CorpActnNtfctn/CorpActnGnlInf/EvtTp/Cd");
            System.out.println("cdVal : "+cdVal);// prints null with wildcard namespace mapping 

            Object nodeObj  = context.selectSingleNode("/env:Envelope/env:Body/cdtBusinessData/d:Document/CorpActnNtfctn");
            System.out.println("nodeObj : "+nodeObj);// prints null


        }catch(Exception e) {
            e.printStackTrace();
        }
    }

}
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-07-10 17:07:41

如果您希望能够选择其中之一,请为文档使用名称空间通配符:

代码语言:javascript
运行
复制
/env:Envelope/env:Body/cdtBusinessData/*:Document

...or,要在一个查询中获取两个文档:

代码语言:javascript
运行
复制
//*:Document

请参阅完整的XQuery文档,您可以自己运行,以便在https://gist.github.com/charles-dyfis-net/983d4054f4f9424a1698上运行

上述版本与XPath 1.0 (感谢@kjhughes)兼容:

代码语言:javascript
运行
复制
/env:Envelope/env:Body/cdtBusinessData/*[local-name()='Document']

...or...

代码语言:javascript
运行
复制
//*[local-name() = 'Document']
票数 6
EN

Stack Overflow用户

发布于 2015-07-10 17:00:38

如果您在已注册中使用了JXPath中的下列名称空间前缀,

代码语言:javascript
运行
复制
JXPathContext.registerNamespace("sw", "urn:swift:xsd:seev.031.002.05")
JXPathContext.registerNamespace("env", "CDTS-SUBMIT")

然后是下面的XPath,

代码语言:javascript
运行
复制
/env:Envelope/env:Body/cdtBusinessData/sw:Document

将成功地在Document命名空间中选择urn:swift:xsd:seev.031.002.05元素。

更新

如果要在其他名称空间中选择Document元素,请类似地为新命名空间注册一个前缀,并在XPath中使用它。

使用注册名称空间前缀的通常更倾向于实践,但如果您想忽略名称空间,则可以在XPath 2.0中使用*:Document技术查尔斯·达菲

XPath 1.0中,*:技术不能工作,而是可以根据元素的本地名称进行测试:

代码语言:javascript
运行
复制
//*[local-name() = 'Document']

将选择所有Document元素,而不管名称空间(以及遗产)。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/31344621

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档