5

我正在尝试将 C# 代码中的 SQLXMLBulkLoader4 用于 SQL 2008 DB。但是由于某种原因,尽管没有抛出任何错误,但它根本不会插入任何行。我使用了 bulkloads 自己的 ErrorLog 文件(检查可能不会导致崩溃的任何错误),但没有报告错误。

我有一个从供应商处下载的 XML 文件(基本上是产品列表),我编写了一个 XSD 以将字段与我们的数据库匹配。没有其他任何东西写入这些特定的表,也没有使用这些文件。

我的 BulkLoad 代码如下所示(我删除了实际的连接字符串值):

public void Bulkload(string schemaFile, string xmlFile, string source)
    {
        SQLXMLBULKLOADLib.SQLXMLBulkLoad4 bulkload = new SQLXMLBULKLOADLib.SQLXMLBulkLoad4();

        try
        {
            bulkload.ConnectionString = "Provider=sqloledb;server=X;database=X;uid=X;pwd=X";
            bulkload.ErrorLogFile = k_ArticleInfoDirectory + source + "BulkLoadError.log";
            bulkload.KeepIdentity = false;
            bulkload.Execute(schemaFile, xmlFile);
        }
        catch (Exception e)
        {
            Console.WriteLine("Fel i BL: " + e);
            throw;
        }
        finally
        {
            bulkload = null;
        }

    }

XML 看起来像这样(精简,下面的所有内容只是更多的产品字段,然后是更多的产品):

<?xml version="1.0" encoding="utf-8"?>
<GetProductsResult xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <Status xmlns="http://schemas.servicestack.net/types">
    <Code>0</Code>
    <Message>Ok</Message>
  </Status>
  <NumberOfProducts xmlns="http://schemas.servicestack.net/types">9826</NumberOfProducts>
  <Products xmlns="http://schemas.servicestack.net/types">
    <Product>
      <ProductID>1000002</ProductID>
      <CreatedDate>2011-11-24 15:54</CreatedDate>
      <UpdatedDate>2011-11-24 15:54</UpdatedDate>
      <Title>Vi tolererar inga förlorare - klanen Kennedy</Title>
      <Publisher>Piratförlaget</Publisher>
      ... And some more fields per Product

我写的 XSD 看起来像这样(再次缩短):

<?xml version="1.0" encoding="iso-8859-1"?>
<xs:schema targetNamespace="http://schemas.servicestack.net/types" xmlns:xs="http://www.w3.org/2001/XMLSchema" attributeFormDefault="qualified" elementFormDefault="qualified" xmlns:sql="urn:schemas-microsoft-com:mapping-schema">

<xs:annotation>
    <xs:appinfo>

        <sql:relationship name="Status"
        parent="tblElibProduct"
        parent-key="id"
        child="tblElibStatus"
        child-key="product_id" />
                    ... + Several other sql:relationships
            </xs:appinfo>
</xs:annotation>
    <xs:element name="GetProductsResult" sql:is-constant="1">
    <xs:complexType>
        <xs:sequence>
            <xs:element name="Status" sql:is-constant="1">
                <xs:complexType>
                    <xs:sequence>
                        <xs:element name="Code" type="xs:integer" minOccurs="0" />
                        <xs:element name="Message" type="xs:string" minOccurs="0" />
                    </xs:sequence>
                </xs:complexType>
            </xs:element>
            <xs:element name="NumberOfProducts" type="xs:string" sql:is-constant="1"/>
            <xs:element name="Products" sql:is-constant="1">
                <xs:complexType>
                    <xs:sequence>
                        <xs:element minOccurs="0" maxOccurs="unbounded" name="Product" sql:relation="tblElibProduct">
                            <xs:complexType>
                                <xs:sequence>
                                    <xs:element minOccurs="1" maxOccurs="1" name="CreatedDate" type="xs:date" sql:field="created_date" />
                                    <xs:element minOccurs="1" maxOccurs="1" name="UpdatedDate" type="xs:date" sql:field="updated_date" />
                                    <xs:element minOccurs="1" maxOccurs="1" name="Title" type="xs:string" sql:field="title" />

我对命名空间视而不见,但它们对我来说是正确的。(阅读许多类似的错误,其中不同的名称空间是原因)。代码在我的计算机上运行,​​我的计算机和带有数据库的计算机都可以访问包含 XML 和 XSD 文件的网络文件夹。

我已经尝试故意更改两个文件中的一些字段名称,并且 BulkLoader 突然在我刚刚更改的字段上引发错误。

我已经将我的 BulkLoader 代码和 XSD 与我在网上找到的示例进行了比较,但我找不到任何可以解释这种行为的差异。
我可能很容易忽略它,但我只是没有看到它。

任何为我指明正确方向的帮助都深受欢迎。

先感谢您!

(PS对不起,如果帖子以某种方式关闭,这是我第一次在这里发帖,但是我确实做了我的研究,我确实尝试遵循关于如何发布的指南=))

4

2 回答 2

1

跟进您怀疑可能存在命名空间问题...

对于实例中限定的元素,命名空间确实匹配(在元素实例和元素声明之间)。

但它们并不都在另一个方向上匹配。模式声明了一个扩展名为 {http://schemas.servicestack.net/types}GetProductsResult 的元素,但输入实例中没有出现这样的元素(有一个 GetProductsResult,但它不是命名空间限定的)。

您可能想看看如果更改 XML 以使第一个开始标记读取会发生什么

<GetProductsResult 
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
  xmlns:xsd="http://www.w3.org/2001/XMLSchema"
  xmlns="http://schemas.servicestack.net/types" >
于 2012-10-10T15:41:27.063 回答
1

应始终遵循的第一条规则是:根据您的 XSD 验证您的 XML。在您的情况下,这听起来更像是您必须更改您的 XSD 而不是您的 XML,因为您似乎试图使您的 XSD 与您的 XML 相匹配——您说过downloaded from a supplier。您的解决方案应该使用供应商的文件,因为如果您希望稍后重新加载他们的文件,您不想继续更改它以适应似乎有问题的 XSD。

实际上,您似乎至少需要两个 XSD 文件:一个定义了一个没有目标命名空间的架构,它导入了另一个以http://schemas.servicestack.net/types. 有很多选项可让您从 XML 生成 XSD,并根据 XSD 验证 XML。

于 2012-10-10T17:03:40.193 回答