使用SQL删除XML文件中的空节点

时间:2015-04-13 06:18:45

标签: sql-server ssis sqlxml

您好我在SQL中使用XML Auto创建了XML文件。该文件基于六个表中的记录创建。如果关联表中没有值,则创建空节点。有没有办法删除SSIS或SQL中的空节点?

以下是使用的查询

select
(select 

      Opp.OPPORTUNITYID as OPPORTUNITYID,
      Opp.CREATEDATE as RequestDate,
      (select USERNAME from sysdba.USERINFO where USERID=Opp.ACCOUNTMANAGERID) as RepName,
      (select Account from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID )as Account,
      (select ACCOUNTID from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID ) as AccountID,
      (select MDRPID from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID ) as MDRPID,
      (select Coalesce(acc1.accountid,acc.accountid) from sysdba.ACCOUNT  acc  left  join sysdba.ACCOUNT acc1 on acc.UNIVERSITYID = acc1.accountid where acc.ACCOUNTID=Opp.ACCOUNTID ) as UniversityID,
      (select Coalesce(acc1.account,acc.account) from sysdba.ACCOUNT  acc  left  join sysdba.ACCOUNT acc1 on acc.UNIVERSITYID = acc1.accountid where acc.ACCOUNTID=Opp.ACCOUNTID ) as University,
      (Opp.STARTDATE) as StartDate,
      (opp.enddate) as EndDate,
     Coalesce ( opp.PROMOCODE,'') as Promocode,
      Opp.MICROSITEURLKEY as MicrositeURLKey,
      opp.modifydate as ModifyDate,
      (select GUID from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID ) as LocationID,
      OppProduct.OPPPRODUCTID as OppProductID,
        OppProduct.PRICE as Price,
      OppProduct.CALCPRICE as CalculatedPrice,
      OppProduct.discount as Discount,
     (select pro.ISBN from sysdba.C_PRODUCT pro join sysdba.OPPORTUNITY_PRODUCT opppro on pro.C_PRODUCTID=opppro.PRODUCTID where opppro.OPPPRODUCTID=OppProduct.OPPPRODUCTID ) as ISBN,
      (select pro.TITLE from sysdba.C_PRODUCT pro join sysdba.OPPORTUNITY_PRODUCT opppro on pro.C_PRODUCTID=opppro.PRODUCTID where opppro.OPPPRODUCTID=OppProduct.OPPPRODUCTID ) as Title,
      AccCourse.ACCOUNTCOURSEID  AS ACCOUNTCOURSEID,
      AccCourse.COURSENAME as CourseName,
      AccCourse.MDRCLGCOURSE as CLGCourse,
      Contact.CONTACTID  as CONTACTID,
      Contact.FIRSTNAME as FirstName,
      Contact.LASTNAME as LastName,
      Contact.EMAIL as Email


from sysdba.OPPORTUNITY Opp
 join sysdba.OPPORTUNITY_PRODUCT OppProduct on Opp.OPPORTUNITYID = OppProduct.OPPORTUNITYID
left join sysdba.C_PRODUCT Product on OppProduct.PRODUCTID = Product.C_PRODUCTID
left join sysdba.OPPPRODUCTCOURSE ProductCourse on OppProduct.OPPPRODUCTID = ProductCourse.OPPPRODUCTID
left join sysdba.OPPORTUNITYCOURSE OppCourse on ProductCourse.OPPORTUNITYCOURSEID = OppCourse.OPPORTUNITYCOURSEID
left join sysdba.ACCOUNTCOURSE AccCourse on OppCourse.ACCOUNTCOURSEID = AccCourse.ACCOUNTCOURSEID
left join sysdba.OPPCOURSECONTACT OppContact on OppCourse.OPPORTUNITYCOURSEID = OppContact.OPPORTUNITYCOURSEID
left join sysdba.CONTACT contact on contact.CONTACTID=OppContact.CONTACTID
For XML AUTO, ROOT('INFO'))as col

输出:

<INFO>
  <Opp LocationID="1594743" ModifyDate="2015-04-01T23:50:01" MicrositeURLKey="O6UJ9A03XT6J" MDRPID="1594743" AccountID="A6UJ9A00OS1L" Account="Marquette University " RepName="Maggie Dolan" RequestDate="2015-04-01T23:48:07" OPPORTUNITYID="O6UJ9A03XT6J">
    <OppProduct Title="prepU for Jensen's Nursing Health Assessment: A Best Practice Approach, Ecommerce, 3 Month Access (PREPU)" ISBN="9781469895727" Price="0.0000" OppProductID="Q6UJ9A15NMSF">
      <AccCourse>
        <contact />
      </AccCourse>
    </OppProduct>
    <OppProduct Title="Lippincott CoursePoint for Nursing Health Assessment: A Best Approach, Ecommerce Version, 12 Month Access (CoursePoint)" ISBN="9781496303134" Price="0.0000" OppProductID="Q6UJ9A15NMSG">
      <AccCourse>
        <contact />
      </AccCourse>
    </OppProduct>
  </Opp>
</INFO>

如果节点为空,有没有办法删除它?例如<Contact><AccCourse>

3 个答案:

答案 0 :(得分:1)

你可以使用像这样的代码行

    SET @testXML.modify('delete  /INFO//*[not(@*)]')

这将删除INFO下没有任何属性的所有节点。

完整代码示例

    DECLARE @testXML XML
    SET @testXML=            
                   ' <INFO>
      <Opp LocationID="1594743" ModifyDate="2015-04-01T23:50:01" MicrositeURLKey="O6UJ9A03XT6J" MDRPID="1594743" AccountID="A6UJ9A00OS1L" Account="Marquette University " RepName="Maggie Dolan" RequestDate="2015-04-01T23:48:07" OPPORTUNITYID="O6UJ9A03XT6J">
        <OppProduct Title="prepU for Jensen''s Nursing Health Assessment: A Best Practice Approach, Ecommerce, 3 Month Access (PREPU)" ISBN="9781469895727" Price="0.0000" OppProductID="Q6UJ9A15NMSF">
          <AccCourse>
            <contact />
          </AccCourse>
        </OppProduct>
        <OppProduct Title="Lippincott CoursePoint for Nursing Health Assessment: A Best Approach, Ecommerce Version, 12 Month Access (CoursePoint)" ISBN="9781496303134" Price="0.0000" OppProductID="Q6UJ9A15NMSG">
          <AccCourse>
            <contact />
          </AccCourse>
        </OppProduct>
      </Opp>
    </INFO>'
    select @testXML 
    SET @testXML.modify('delete  /INFO//*[not(@*)]')
    select @testXML

答案 1 :(得分:0)

您可以使用XML modify()删除没有属性的节点。像这样的东西。

DECLARE @xml xml =
'<?xml version="1.0"?>
<Opp LocationID="1594743" ModifyDate="2015-04-01T23:50:01" MicrositeURLKey="O6UJ9A03XT6J" MDRPID="1594743" AccountID="A6UJ9A00OS1L" Account="Marquette University " RepName="Maggie Dolan" RequestDate="2015-04-01T23:48:07" OPPORTUNITYID="O6UJ9A03XT6J"><OppProduct Title="prepU for Jensen''s Nursing Health Assessment: A Best Practice Approach, Ecommerce, 3 Month Access (PREPU)" ISBN="9781469895727" Price="0.0000" OppProductID="Q6UJ9A15NMSF"><AccCourse><contact/></AccCourse></OppProduct><OppProduct Title="Lippincott CoursePoint for Nursing Health Assessment: A Best Approach, Ecommerce Version, 12 Month Access (CoursePoint)" ISBN="9781496303134" Price="0.0000" OppProductID="Q6UJ9A15NMSG"><AccCourse ACCOUNTCOURSEID="2"><contact/></AccCourse></OppProduct></Opp>'

SELECT @xml

SET @xml.modify('delete //AccCourse[empty(@ACCOUNTCOURSEID)]')

SELECT @xml

有关更多信息,请参阅delete (XML DML)

答案 2 :(得分:0)

以Arun Gairola为基础回答:

  

你可以使用像这样的代码行

SET @testXML.modify('delete  /INFO//*[not(@*)]') 
     

这将删除INFO下没有任何属性的所有节点。

由于您的XML是从查询生成的,因此您可以将结果设置为变量,然后从变量中删除空节点。使用上面的SQL,您需要执行以下操作:

set @xml xml;
set @xml = (
    select <columns>
    from <tables>
    For XML AUTO, ROOT('INFO')
    )

set @xml.modify('delete  /INFO//*[not(@*)]')
select @xml

使用您在问题中提供的完整sql,您希望这样做:

set @xml xml;
set @xml = (select 
    Opp.OPPORTUNITYID as OPPORTUNITYID,
    Opp.CREATEDATE as RequestDate,
    (select USERNAME from sysdba.USERINFO where USERID=Opp.ACCOUNTMANAGERID) as RepName,
    (select Account from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID )as Account,
    (select ACCOUNTID from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID ) as AccountID,
    (select MDRPID from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID ) as MDRPID,
    (select Coalesce(acc1.accountid,acc.accountid) from sysdba.ACCOUNT  acc  left  join sysdba.ACCOUNT acc1 on acc.UNIVERSITYID = acc1.accountid where acc.ACCOUNTID=Opp.ACCOUNTID ) as UniversityID,
    (select Coalesce(acc1.account,acc.account) from sysdba.ACCOUNT  acc  left  join sysdba.ACCOUNT acc1 on acc.UNIVERSITYID = acc1.accountid where acc.ACCOUNTID=Opp.ACCOUNTID ) as University,
    (Opp.STARTDATE) as StartDate,
    (opp.enddate) as EndDate,
    Coalesce ( opp.PROMOCODE,'') as Promocode,
    Opp.MICROSITEURLKEY as MicrositeURLKey,
    opp.modifydate as ModifyDate,
    (select GUID from sysdba.ACCOUNT where ACCOUNTID=Opp.ACCOUNTID ) as LocationID,
    OppProduct.OPPPRODUCTID as OppProductID,
    OppProduct.PRICE as Price,
    OppProduct.CALCPRICE as CalculatedPrice,
    OppProduct.discount as Discount,
    (select pro.ISBN from sysdba.C_PRODUCT pro join sysdba.OPPORTUNITY_PRODUCT opppro on pro.C_PRODUCTID=opppro.PRODUCTID where opppro.OPPPRODUCTID=OppProduct.OPPPRODUCTID ) as ISBN,
    (select pro.TITLE from sysdba.C_PRODUCT pro join sysdba.OPPORTUNITY_PRODUCT opppro on pro.C_PRODUCTID=opppro.PRODUCTID where opppro.OPPPRODUCTID=OppProduct.OPPPRODUCTID ) as Title,
    AccCourse.ACCOUNTCOURSEID  AS ACCOUNTCOURSEID,
    AccCourse.COURSENAME as CourseName,
    AccCourse.MDRCLGCOURSE as CLGCourse,
    Contact.CONTACTID  as CONTACTID,
    Contact.FIRSTNAME as FirstName,
    Contact.LASTNAME as LastName,
    Contact.EMAIL as Email
from sysdba.OPPORTUNITY Opp
join sysdba.OPPORTUNITY_PRODUCT OppProduct on Opp.OPPORTUNITYID = OppProduct.OPPORTUNITYID
left join sysdba.C_PRODUCT Product on OppProduct.PRODUCTID = Product.C_PRODUCTID
left join sysdba.OPPPRODUCTCOURSE ProductCourse on OppProduct.OPPPRODUCTID = ProductCourse.OPPPRODUCTID
left join sysdba.OPPORTUNITYCOURSE OppCourse on ProductCourse.OPPORTUNITYCOURSEID = OppCourse.OPPORTUNITYCOURSEID
left join sysdba.ACCOUNTCOURSE AccCourse on OppCourse.ACCOUNTCOURSEID = AccCourse.ACCOUNTCOURSEID
left join sysdba.OPPCOURSECONTACT OppContact on OppCourse.OPPORTUNITYCOURSEID = OppContact.OPPORTUNITYCOURSEID
left join sysdba.CONTACT contact on contact.CONTACTID=OppContact.CONTACTID
For XML AUTO, ROOT('INFO'))

set @xml.modify('delete  /INFO//*[not(@*)]')
select @xml