简体   繁体   English

如何在 SQL Server 中读取格式化的 xml 文件

[英]How to read formated xml file in SQL Server

I have XML file that need to read some data from it by SQL Server 2008.我有需要通过 SQL Server 2008 从中读取一些数据的 XML 文件。

Please guide me to to solve this problem.请指导我解决这个问题。

My XML file like that:我的 XML 文件是这样的:

<?xml version="1.0" encoding="utf-8"?>
<DataSet xmlns="http://tempuri.org/">
  <xs:schema id="NewDataSet" xmlns="" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
    <xs:element name="NewDataSet" msdata:IsDataSet="true" msdata:UseCurrentLocale="true">
      <xs:complexType>
        <xs:choice minOccurs="0" maxOccurs="unbounded">
          <xs:element name="Table">
            <xs:complexType>
              <xs:sequence>
                <xs:element name="CI_CODE" type="xs:decimal" minOccurs="0" />
                <xs:element name="CI_NAME" type="xs:string" minOccurs="0" />
                <xs:element name="CI_PISH_CODE" type="xs:string" minOccurs="0" />
              </xs:sequence>
            </xs:complexType>
          </xs:element>
        </xs:choice>
      </xs:complexType>
    </xs:element>
  </xs:schema>
  <diffgr:diffgram xmlns:msdata="urn:schemas-microsoft-com:xml-msdata" xmlns:diffgr="urn:schemas-microsoft-com:xml-diffgram-v1">
    <NewDataSet xmlns="">
      <Table diffgr:id="Table1" msdata:rowOrder="0">
        <CI_CODE>1</CI_CODE>
        <CI_NAME>Kerman</CI_NAME>
        <CI_PISH_CODE>34</CI_PISH_CODE>
      </Table>
      <Table diffgr:id="Table2" msdata:rowOrder="1">
        <CI_CODE>2</CI_CODE>
        <CI_NAME>Anar</CI_NAME>
        <CI_PISH_CODE>34</CI_PISH_CODE>
      </Table>
      <Table diffgr:id="Table3" msdata:rowOrder="2">
        <CI_CODE>3</CI_CODE>
        <CI_NAME>Baft</CI_NAME>
        <CI_PISH_CODE>34</CI_PISH_CODE>
      </Table>
    </NewDataSet>
  </diffgr:diffgram>
</DataSet>

I need to help to read this XML in SQL Server 2008.我需要帮助在 SQL Server 2008 中阅读此 XML。

I need tags <CI_CODE> and <CI_NAME> and <CI_PISH_CODE> data.我需要标签<CI_CODE><CI_NAME><CI_PISH_CODE>数据。

Please guide me请指导我

Assuming your XML is stored in a variable called @Data XML , you can use this XQuery go get your data.假设您的 XML 存储在名为@Data XML的变量中,您可以使用此 XQuery 来获取您的数据。

The XPath expression "navigates" down the tree of nodes to give you a "virtual" table of XML fragments - one for each <Table> XML element. XPath 表达式在节点树中“导航”,为您提供一个 XML 片段的“虚拟”表 - 每个<Table> XML 元素一个。 From that XML element, you can then fetch the individual data items using the .value() XQuery expression.然后,您可以使用.value() XQuery 表达式从该 XML 元素中获取各个数据项。

You need to be especially vigilant about using the correct XML namespaces for each element.您需要特别警惕为每个元素使用正确的XML 名称空间。

;WITH XMLNAMESPACES('http://tempuri.org/' AS ns, 
                    'urn:schemas-microsoft-com:xml-diffgram-v1' AS dg)
SELECT
    CI_CODE = XC.value('(CI_CODE)[1]', 'int'),
    CI_NAME = XC.value('(CI_NAME)[1]', 'varchar(50)'),
    CI_PISH_CODE = XC.value('(CI_PISH_CODE)[1]', 'int')
FROM
    @Data.nodes('/ns:DataSet/dg:diffgram/NewDataSet/Table') AS XT(XC)

This produces this output on my PC:这会在我的 PC 上产生以下输出:

在此处输入图片说明

In general I'd advise you to be as specific as possible.一般来说,我建议您尽可能具体。 In this case you have unclean namespaces (empty default namespace at schema level), which makes it difficult to query this correctly.在这种情况下,您有不干净的命名空间( schema级别的空默认命名空间),这使得很难正确查询。

Try it wild wildcarded namespace ( *: ):试试通配名称空间( *: ):

EDIT: simplified编辑:简化

--Your XML in a variable --您在变量中的 XML

DECLARE @xml XML=
'Copy your XML here';

--The query --查询

SELECT dgt.value('(@*:id)[1]','nvarchar(max)') AS DiffgramTable
      ,dgt.value('(*:CI_CODE)[1]','int') AS Diffgram_CI_CODE
      ,dgt.value('(*:CI_NAME)[1]','nvarchar(max)') AS Diffgram_CI_NAME
      ,dgt.value('(*:CI_PISH_CODE)[1]','int') AS Diffgram_CI_CODE
FROM @xml.nodes('/*:DataSet') AS A(ds)
OUTER APPLY ds.nodes('*:diffgram') AS C(dg)
OUTER APPLY dg.nodes('*:NewDataSet/*:Table') AS D(dgt)

First we pick the "DataSet" and call it "ds".首先,我们选择“DataSet”并将其称为“ds”。 Below this we pick "diffgram" ("dg").在此之下,我们选择“diffgram”(“dg”)。 Below "dg" we pick all "Table" ("dgt")在“dg”下面我们选择所有“表”(“dgt”)

The select will read all information out of the nearest node select 将从最近的节点读取所有信息

The result结果

+---------------+------------------+------------------+------------------+
| DiffgramTable | Diffgram_CI_CODE | Diffgram_CI_NAME | Diffgram_CI_CODE |
+---------------+------------------+------------------+------------------+
| Table1        | 1                | Kerman           | 34               |
+---------------+------------------+------------------+------------------+
| Table2        | 2                | Anar             | 34               |
+---------------+------------------+------------------+------------------+
| Table3        | 3                | Baft             | 34               |
+---------------+------------------+------------------+------------------+

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM