Esempio n. 1
0
        internal XmlReadMode ReadXml(XmlReader reader, XmlReadMode mode, bool denyResolving)
        {
            DataTable.RowDiffIdUsageSection rowDiffIdUsage = new DataTable.RowDiffIdUsageSection();
            try {
                bool fSchemaFound = false;
                bool fDataFound = false;
                bool fIsXdr = false;
                int iCurrentDepth = -1;
                XmlReadMode ret = mode;

                // Dev11 904428: prepare and cleanup rowDiffId hashtable
                rowDiffIdUsage.Prepare(this);

                if (reader == null)
                    return ret;

                bool originalEnforceConstraint  = false;
                if (this.DataSet != null) {
                    originalEnforceConstraint  = this.DataSet.EnforceConstraints;
                    this.DataSet.EnforceConstraints = false;
                }
                else {
                    originalEnforceConstraint  = this.EnforceConstraints;
                    this.EnforceConstraints = false;
                }

                if (reader is XmlTextReader)
                    ((XmlTextReader) reader).WhitespaceHandling = WhitespaceHandling.Significant;

                XmlDocument xdoc = new XmlDocument(); // we may need this to infer the schema

                if ((mode != XmlReadMode.Fragment) && (reader.NodeType == XmlNodeType.Element))
                    iCurrentDepth = reader.Depth;

                reader.MoveToContent();
                if (Columns.Count == 0) {
                    if (IsEmptyXml(reader)) {
                        reader.Read();
                        return ret;
                    }
                }

                XmlDataLoader xmlload = null;

                if (reader.NodeType == XmlNodeType.Element) {
                    XmlElement topNode = null;
                    if (mode == XmlReadMode.Fragment) {
                        xdoc.AppendChild(xdoc.CreateElement("ds_sqlXmlWraPPeR"));
                        topNode = xdoc.DocumentElement;
                    }
                    else { //handle the top node
                        if ((reader.LocalName == Keywords.DIFFGRAM) && (reader.NamespaceURI == Keywords.DFFNS)) {
                            if ((mode == XmlReadMode.DiffGram) || (mode == XmlReadMode.IgnoreSchema)) {
                                if (Columns.Count == 0) {
                                    if(reader.IsEmptyElement) {
                                        reader.Read();
                                        return XmlReadMode.DiffGram;
                                    }
                                    throw ExceptionBuilder.DataTableInferenceNotSupported();
                                }
                                this.ReadXmlDiffgram(reader);
                                // read the closing tag of the current element
                                ReadEndElement(reader);
                            }
                            else {
                                reader.Skip();
                            }
                            RestoreConstraint(originalEnforceConstraint);
                            return ret;
                        }

                        if (reader.LocalName == Keywords.XDR_SCHEMA && reader.NamespaceURI==Keywords.XDRNS) {
                            // load XDR schema and exit
                            if ((mode != XmlReadMode.IgnoreSchema) && (mode != XmlReadMode.InferSchema)) {
                                ReadXDRSchema(reader);
                            }
                            else {
                                reader.Skip();
                            }
                            RestoreConstraint(originalEnforceConstraint);
                            return ret; //since the top level element is a schema return
                        }

                        if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI==Keywords.XSDNS) {
                            // load XSD schema and exit
                            if ((mode != XmlReadMode.IgnoreSchema) && (mode != XmlReadMode.InferSchema))  {
                                ReadXmlSchema(reader, denyResolving);
                            }
                            else
                                reader.Skip();
                            RestoreConstraint(originalEnforceConstraint);
                            return ret; //since the top level element is a schema return
                        }

                        if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI.StartsWith(Keywords.XSD_NS_START, StringComparison.Ordinal))  {
                             if (this.DataSet != null) { // we should not throw for constraint, we already will throw for unsupported schema, so restore enforce cost, but not via property
                                 this.DataSet.RestoreEnforceConstraints(originalEnforceConstraint);
                             }
                             else {
                                this.enforceConstraints = originalEnforceConstraint;
                            }
                            throw ExceptionBuilder.DataSetUnsupportedSchema(Keywords.XSDNS);
                        }

                        // now either the top level node is a table and we load it through dataReader...
                        // ... or backup the top node and all its attributes
                        topNode = xdoc.CreateElement(reader.Prefix, reader.LocalName, reader.NamespaceURI);
                        if (reader.HasAttributes) {
                            int attrCount = reader.AttributeCount;
                            for (int i=0;i<attrCount;i++) {
                                reader.MoveToAttribute(i);
                                if (reader.NamespaceURI.Equals(Keywords.XSD_XMLNS_NS))
                                    topNode.SetAttribute(reader.Name, reader.GetAttribute(i));
                                else {
                                    XmlAttribute attr = topNode.SetAttributeNode(reader.LocalName, reader.NamespaceURI);
                                    attr.Prefix = reader.Prefix;
                                    attr.Value = reader.GetAttribute(i);
                                }
                            }
                        }
                        reader.Read();
                    }

                    while(MoveToElement(reader, iCurrentDepth)) {

                        if (reader.LocalName == Keywords.XDR_SCHEMA && reader.NamespaceURI==Keywords.XDRNS) {
                            // load XDR schema
                       	    if (!fSchemaFound && !fDataFound && (mode != XmlReadMode.IgnoreSchema) && (mode != XmlReadMode.InferSchema))  {
                                ReadXDRSchema(reader);
                                fSchemaFound = true;
                                fIsXdr = true;
                            }
                            else {
                                reader.Skip();
                            }
                            continue;
                        }

                        if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI==Keywords.XSDNS) {
                        // load XSD schema and exit
                            if ((mode != XmlReadMode.IgnoreSchema) && (mode != XmlReadMode.InferSchema))  {
                                ReadXmlSchema(reader, denyResolving);
                                fSchemaFound = true;
                            }
                            else {
                                reader.Skip();
                            }
                            continue;
                        }

                        if ((reader.LocalName == Keywords.DIFFGRAM) && (reader.NamespaceURI == Keywords.DFFNS)) {
                            if ((mode == XmlReadMode.DiffGram) || (mode == XmlReadMode.IgnoreSchema)) {
                                if (Columns.Count == 0) {
                                    if(reader.IsEmptyElement) {
                                        reader.Read();
                                        return XmlReadMode.DiffGram;
                                    }
                                    throw ExceptionBuilder.DataTableInferenceNotSupported();
                                }
                                this.ReadXmlDiffgram(reader);
                                ret = XmlReadMode.DiffGram;
                            }
                            else {
                                reader.Skip();
                            }
                            continue;
                        }

                        if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI.StartsWith(Keywords.XSD_NS_START, StringComparison.Ordinal))  {
                            if (this.DataSet != null) { // we should not throw for constraint, we already will throw for unsupported schema, so restore enforce cost, but not via property
                                 this.DataSet.RestoreEnforceConstraints(originalEnforceConstraint);
                            }
                            else {
                                this.enforceConstraints = originalEnforceConstraint;
                            }
                            throw ExceptionBuilder.DataSetUnsupportedSchema(Keywords.XSDNS);
                        }

                        if (mode == XmlReadMode.DiffGram) {
                            reader.Skip();
                            continue; // we do not read data in diffgram mode
                        }

                        // if we are here we found some data
                        fDataFound = true;

                        if (mode == XmlReadMode.InferSchema) { //save the node in DOM until the end;
                            XmlNode node = xdoc.ReadNode(reader);
                            topNode.AppendChild(node);
                        }
                        else {
                            if (Columns.Count == 0) {
                                throw ExceptionBuilder.DataTableInferenceNotSupported();
                            }
                            if (xmlload == null)
                                xmlload = new XmlDataLoader(this, fIsXdr, topNode,  mode == XmlReadMode.IgnoreSchema);
                            xmlload.LoadData(reader);
                        }
                    } //end of the while

                    // read the closing tag of the current element
                    ReadEndElement(reader);

                    // now top node contains the data part
                    xdoc.AppendChild(topNode);

                    if (xmlload == null)
                        xmlload = new XmlDataLoader(this, fIsXdr, mode == XmlReadMode.IgnoreSchema);

                    if (mode == XmlReadMode.DiffGram) {
                        // we already got the diffs through XmlReader interface
                        RestoreConstraint(originalEnforceConstraint);
                        return ret;
                    }
    //todo
                    // Load Data
                    if (mode == XmlReadMode.InferSchema) {
                        if (Columns.Count == 0) {
                            throw ExceptionBuilder.DataTableInferenceNotSupported();
                        }

    // [....]                    xmlload.InferSchema(xdoc, null);
    // [....]                    xmlload.LoadData(xdoc);
                    }
                }
                RestoreConstraint(originalEnforceConstraint);

                return ret;
            }
            finally {
                // Dev11 904428: prepare and cleanup rowDiffId hashtable
                rowDiffIdUsage.Cleanup();
            }
        }
Esempio n. 2
0
        internal XmlReadMode ReadXml(XmlReader reader, bool denyResolving)
        {
            IntPtr hscp;
            Bid.ScopeEnter(out hscp, "<ds.DataTable.ReadXml|INFO> %d#, denyResolving=%d{bool}\n", ObjectID, denyResolving);
            try {

              DataTable.RowDiffIdUsageSection rowDiffIdUsage = new DataTable.RowDiffIdUsageSection();
              try {
                bool fDataFound = false;
                bool fSchemaFound = false;
                bool fDiffsFound = false;
                bool fIsXdr = false;
                int iCurrentDepth = -1;
                XmlReadMode ret = XmlReadMode.Auto;

                // clear the hashtable to avoid conflicts between diffgrams, SqlHotFix 782
                rowDiffIdUsage.Prepare(this);

                if (reader == null)
                    return ret;
                bool originalEnforceConstraint = false;
                if (this.DataSet != null) {
                    originalEnforceConstraint = this.DataSet.EnforceConstraints;
                    this.DataSet.EnforceConstraints = false;
                }
                else {
                    originalEnforceConstraint = this.EnforceConstraints;
                    this.EnforceConstraints = false;
                }

                if (reader is XmlTextReader)
                    ((XmlTextReader) reader).WhitespaceHandling = WhitespaceHandling.Significant;

                XmlDocument xdoc = new XmlDocument(); // we may need this to infer the schema
                XmlDataLoader xmlload = null;


                reader.MoveToContent();
                if (Columns.Count == 0) {
                    if (IsEmptyXml(reader)) {
                        reader.Read();
                        return ret;
                    }
                }

                if (reader.NodeType == XmlNodeType.Element) {
                    iCurrentDepth = reader.Depth;

                    if ((reader.LocalName == Keywords.DIFFGRAM) && (reader.NamespaceURI == Keywords.DFFNS)) {
                        if (Columns.Count == 0) {
                            if (reader.IsEmptyElement) {
                                reader.Read();
                                return XmlReadMode.DiffGram;
                            }
                            throw ExceptionBuilder.DataTableInferenceNotSupported();
                        }
                        this.ReadXmlDiffgram(reader);
                        // read the closing tag of the current element
                        ReadEndElement(reader);

                        RestoreConstraint(originalEnforceConstraint);
                        return XmlReadMode.DiffGram;
                    }

                    // if reader points to the schema load it
                    if (reader.LocalName == Keywords.XDR_SCHEMA && reader.NamespaceURI==Keywords.XDRNS) {
                        // load XDR schema and exit
                        ReadXDRSchema(reader);

                        RestoreConstraint(originalEnforceConstraint);
                        return XmlReadMode.ReadSchema; //since the top level element is a schema return
                    }

                    if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI==Keywords.XSDNS) {
                        // load XSD schema and exit
                        ReadXmlSchema(reader, denyResolving);
                        RestoreConstraint(originalEnforceConstraint);
                        return XmlReadMode.ReadSchema; //since the top level element is a schema return
                    }

                    if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI.StartsWith(Keywords.XSD_NS_START, StringComparison.Ordinal)) {
                        if (this.DataSet != null) { // we should not throw for constraint, we already will throw for unsupported schema, so restore enforce cost, but not via property
                            this.DataSet.RestoreEnforceConstraints(originalEnforceConstraint);
                        }
                        else {
                            this.enforceConstraints = originalEnforceConstraint;
                        }

                        throw ExceptionBuilder.DataSetUnsupportedSchema(Keywords.XSDNS);
                    }

                    // now either the top level node is a table and we load it through dataReader...

                    // ... or backup the top node and all its attributes because we may need to InferSchema
                    XmlElement topNode = xdoc.CreateElement(reader.Prefix, reader.LocalName, reader.NamespaceURI);
                    if (reader.HasAttributes) {
                        int attrCount = reader.AttributeCount;
                        for (int i=0;i<attrCount;i++) {
                            reader.MoveToAttribute(i);
                            if (reader.NamespaceURI.Equals(Keywords.XSD_XMLNS_NS))
                                topNode.SetAttribute(reader.Name, reader.GetAttribute(i));
                            else {
                                XmlAttribute attr = topNode.SetAttributeNode(reader.LocalName, reader.NamespaceURI);
                                attr.Prefix = reader.Prefix;
                                attr.Value = reader.GetAttribute(i);
                            }
                        }
                    }
                    reader.Read();

                    while(MoveToElement(reader, iCurrentDepth)) {

                        if ((reader.LocalName == Keywords.DIFFGRAM) && (reader.NamespaceURI == Keywords.DFFNS)) {
                            this.ReadXmlDiffgram(reader);
                            // read the closing tag of the current element
                            ReadEndElement(reader);
                            RestoreConstraint(originalEnforceConstraint);
                            return XmlReadMode.DiffGram;
                        }

                        // if reader points to the schema load it...


                        if (!fSchemaFound && !fDataFound && reader.LocalName == Keywords.XDR_SCHEMA && reader.NamespaceURI==Keywords.XDRNS) {
                            // load XDR schema and exit
                            ReadXDRSchema(reader);
                            fSchemaFound = true;
                            fIsXdr = true;
                            continue;
                        }

                        if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI==Keywords.XSDNS) {
                            // load XSD schema and exit
                            ReadXmlSchema(reader, denyResolving);
                            fSchemaFound = true;
                            continue;
                        }

                        if (reader.LocalName == Keywords.XSD_SCHEMA && reader.NamespaceURI.StartsWith(Keywords.XSD_NS_START, StringComparison.Ordinal))  {
                            if (this.DataSet != null) { // we should not throw for constraint, we already will throw for unsupported schema, so restore enforce cost, but not via property
                                this.DataSet.RestoreEnforceConstraints(originalEnforceConstraint);
                            }
                            else {
                                this.enforceConstraints = originalEnforceConstraint;
                            }
                            throw ExceptionBuilder.DataSetUnsupportedSchema(Keywords.XSDNS);
                        }

                        if ((reader.LocalName == Keywords.DIFFGRAM) && (reader.NamespaceURI == Keywords.DFFNS)) {
                            this.ReadXmlDiffgram(reader);
                            fDiffsFound = true;
                            ret = XmlReadMode.DiffGram;
                        }
                        else {
                            // we found data here
                            fDataFound = true;

                            if (!fSchemaFound && Columns.Count == 0) {
                                XmlNode node = xdoc.ReadNode(reader);
                                topNode.AppendChild(node);
                            }
                            else {
                                if (xmlload == null)
                                    xmlload = new XmlDataLoader(this, fIsXdr, topNode, false);
                                xmlload.LoadData(reader);
                                if (fSchemaFound)
                                    ret = XmlReadMode.ReadSchema;
                                else
                                    ret = XmlReadMode.IgnoreSchema;
                            }
                        }

                    }
                    // read the closing tag of the current element
                    ReadEndElement(reader);

                    // now top node contains the data part
                    xdoc.AppendChild(topNode);

                    if (!fSchemaFound && Columns.Count == 0) {
                        if (IsEmptyXml(reader)) {
                            reader.Read();
                            return ret;
                        }
                        throw ExceptionBuilder.DataTableInferenceNotSupported();
                    }

                    if (xmlload == null)
                        xmlload = new XmlDataLoader(this, fIsXdr, false);

                    // so we InferSchema
                    if (!fDiffsFound) {// we need to add support for inference here
                    }
                }
                RestoreConstraint(originalEnforceConstraint);
                return ret;
              }
              finally {
                rowDiffIdUsage.Cleanup();
              }
            }
            finally{
                Bid.ScopeLeave(ref hscp);
            }
        }