主要使用SQL Server 2016.

我有XML格式的数据可用,但我需要能够将这些数据连接到SQL Server数据库中的其他表.

我四处查看了一下,但我找到的示例在XML中使用了不同的数据布局.这些示例在文档中具有不同的 node 名称.我的XML有一个名为metadata的 node ,它定义了每个数据item的名称、数据类型和长度.在data node 中,每个row具有value个 node ,其对应于metadata个 node 中的item个 node .另外,我的XML使用名称空间.我找到的例子中没有一个是这样的.我在完成的其他SQL/XML任务中遇到过命名空间方面的问题,所以这可能很重要.

我如何使用SQL来转换类似这样的内容...

<?xml version="1.0" encoding="utf-8"?>
<dataset  xmlns="http://developer.cognos.com/schemas/xmldata/1/"  xmlns:xs="http://www.w3.org/2001/XMLSchema-instance">
<!--
<dataset
    xmlns="http://developer.cognos.com/schemas/xmldata/1/"
    xmlns:xs="http://www.w3.org/2001/XMLSchema-instance"
    xs:schemaLocation="http://developer.cognos.com/schemas/xmldata/1/ xmldata.xsd"
>
-->
    <metadata>
          <item name="Task" type="xs:string" length="-1"/>
          <item name="Task Number" type="xs:string" length="-1"/>
          <item name="Group" type="xs:string" length="-1"/>
          <item name="Work Order" type="xs:string" length="-1"/>
    </metadata>
    <data>
        <row>
            <value>3361B11</value>
            <value>1</value>
            <value>01</value>
            <value>MS7579</value>
        </row>
        <row>
            <value>3361B11</value>
            <value>2</value>
            <value>50</value>
            <value>MS7579</value>
        </row>
        <row>
            <value>3361B11</value>
            <value>3</value>
            <value>02</value>
            <value>JA0520</value>
        </row>
    </data>
</dataset>

...转换成表格格式,如...

Task Task Number Group Work Order
3361B11 1 01 MS7579
3361B11 2 50 MS7579
3361B11 3 02 JA0520

...这样我就可以把它和其他数据连接起来.

我认为第一步应该是查询metadata个 node ,以获得列名、数据类型和长度.

输入(简而言之)

<?xml version="1.0" encoding="utf-8"?>
<dataset  xmlns="http://developer.cognos.com/schemas/xmldata/1/"  xmlns:xs="http://www.w3.org/2001/XMLSchema-instance">
    <metadata>
          <item name="Task" type="xs:string" length="-1"/>
          <item name="Task Number" type="xs:string" length="-1"/>
          <item name="Group" type="xs:string" length="-1"/>
          <item name="Work Order" type="xs:string" length="-1"/>
    </metadata>
</dataset>

输出

id name type length
1 Task string -1
2 Task Number string -1
3 Group string -1
4 Work Order string -1

一旦获得,将使用这些值动态生成下一个部件.

如果它对摆弄有帮助,下面是一条产生所需结果的SQL语句:

with
xlTask as (
  select *
  from (
    values
      ('3361B11', '1', '01', 'MS7579')
    , ('3361B11', '2', '50', 'MS7579')
    , ('3361B11', '3', '02', 'JA0520')
  ) q ([Task], [Task Number], [Group], [Work Order])
)
select *
from xlTask

推荐答案

以下是来自您的示例数据的动态解决方案:

DECLARE @SQL NVARCHAR(MAX)

;WITH XMLNAMESPACES(DEFAULT 'http://developer.cognos.com/schemas/xmldata/1/')
SELECT  @SQL = N'WITH XMLNAMESPACES(DEFAULT ''http://developer.cognos.com/schemas/xmldata/1/'')
SELECT '
 + STRING_AGG('c.value(''(value[' + T.X.value('let $i := . return count(/dataset/metadata/item[. << $i]) + 1', 'NVARCHAR(MAX)') + N']/text())[1]'', ''VARCHAR(20)'') AS '
 + QUOTENAME(T.X.value('@name', 'nvarchar(100)')) , ',')
 + N'
FROM @xml.nodes(''/dataset/data/row'') AS t(c)'
FROM    @xml.nodes('/dataset/metadata/item') as T(X);
EXEC SP_EXECUTESQL @SQL, N'@xml XML', @xml = @xml

它读取元数据并生成读取实际行并创建适当别名的SQL

Sql相关问答推荐

Oracle SQL中的累计总数

当有空单元格时,如何连接列

如何通过比较不同表中相同ID S的值来筛选ID为S的列表?

SQL Oracle条件分组依据

LEFT JOIN不显示计数0我期望的方式

Oracle SQL根据列中的条件 Select 最大记录数

PostgreSQL基于2个COLS的任意组合 Select 唯一行

Django将字符串筛选为整数?

BigQuery-当子查询不返回任何结果时,所有结果为零

PostgreSQL:使用JSONB中的字段使用jsonb_to_Records()填充记录

如何从Spark SQL的JSON列中提取动态数量的键值对

如何创建snowflake表(动态查找数据类型)并从阶段加载(AWS S3)?

当 ansible 变量未定义或为空时,跳过 sql.j2 模板中的 DELETE FROM 查询

MySQL中的递归查询邻接表深度优先?

计算 BigQuery 中列的中值差 - 分析函数不能作为聚合函数的参数

SQL 按 id 运行总计并受条件限制(在窗口上)

如何在一个存储过程中创建全局临时表,并在另一个存储过程中使用它

为每组填写行以进行旋转

为什么 Oracle 在一个查询中对同一张表同时执行 TABLE SCAN 和 INDEX UNIQUE SCAN?

当计数为 0 时显示行