System.Xml.Schema.XmlSchemaInference.InferElement C# (CSharp) Méthode

InferElement() private méthode

Sets type of the xse based on the currently read element. If the type is already set, verifies that it matches the instance and if not, updates the type to validate the instance.
private InferElement ( XmlSchemaElement xse, bool bCreatingNewType, XmlSchema parentSchema ) : void
xse XmlSchemaElement XmlSchemaElement corresponding to the element just read by the xtr XmlTextReader
bCreatingNewType bool true if the type is newly created, false if the type already existed and matches the current element name
parentSchema XmlSchema
Résultat void
            internal void InferElement(XmlSchemaElement xse, bool bCreatingNewType, XmlSchema parentSchema)
            {
            
                bool bEmptyElement = xtr.IsEmptyElement;
                int lastUsedSeqItem = -1;

                Hashtable table = new Hashtable();
                XmlSchemaType schemaType = GetEffectiveSchemaType(xse, bCreatingNewType);
                XmlSchemaComplexType ct = schemaType as XmlSchemaComplexType;

                //infer type based on content of the current element
                if (xtr.MoveToFirstAttribute())
                {
                    ProcessAttributes(ref xse, schemaType, bCreatingNewType, parentSchema);
                }
                else
                {
                    if (!bCreatingNewType && ct != null) 
                    {   //if type already exists and can potentially have attributes
                        MakeExistingAttributesOptional(ct, null);
                    }
                }
                if (ct == null || ct == XmlSchemaComplexType.AnyType) { //It was null or simple type, after processing attributes, this might have been set
                    ct = xse.SchemaType as XmlSchemaComplexType;
                }
                //xse's type is set either to complex type if attributes exist or null
                if (bEmptyElement)  //<element attr="3232" />
                {
                    if (!bCreatingNewType)
                    {
                        if (null != ct)
                        {
                            if (null!= ct.Particle )

                            {
                                ct.Particle.MinOccurs = 0;
                            }
                            else if (null != ct.ContentModel)
                            {
                                XmlSchemaSimpleContentExtension sce = CheckSimpleContentExtension(ct);
                                sce.BaseTypeName = ST_string;
                                sce.LineNumber = TF_string;
                            }
                        }
                        else if (!xse.SchemaTypeName.IsEmpty)
                        {
                            xse.LineNumber = TF_string;
                            xse.SchemaTypeName = ST_string;
                        }
                    }
                    else
                    {
                        xse.LineNumber = TF_string;
                        //xse.SchemaTypeName = ST_string; //My change
                    }
                    return; //We are done processing this element - all attributes are already added
                }
                bool bWhiteSpace = false;
                do
                { 
                    xtr.Read();
                    if (xtr.NodeType == XmlNodeType.Whitespace) 
                    {
                        bWhiteSpace = true;
                    }
                    if (xtr.NodeType == XmlNodeType.EntityReference) 
                    {
                        throw new XmlSchemaInferenceException(Res.SchInf_entity, 0, 0);
                    }
                } while( (!xtr.EOF) && (xtr.NodeType != XmlNodeType.EndElement) && (xtr.NodeType != XmlNodeType.CDATA)&&(xtr.NodeType != XmlNodeType.Element)&&(xtr.NodeType != XmlNodeType.Text) );

                if (xtr.NodeType == XmlNodeType.EndElement)
                {
                    if (bWhiteSpace) {
                        if (ct != null)
                        {
                            if (null != ct.ContentModel)
                            {
                                XmlSchemaSimpleContentExtension sce = CheckSimpleContentExtension(ct);
                                sce.BaseTypeName = ST_string;
                                sce.LineNumber = TF_string;
                            }
                            else if (bCreatingNewType)
                            {
                                //attributes exist, but both Particle and ContentModel == null - this must be complex type with simpleContent extension
                                XmlSchemaSimpleContent sc = new XmlSchemaSimpleContent();
                                ct.ContentModel = sc;
                                XmlSchemaSimpleContentExtension sce = new XmlSchemaSimpleContentExtension();
                                sc.Content = sce;

                                MoveAttributes(ct, sce, bCreatingNewType);
                                
                                sce.BaseTypeName = ST_string;
                                sce.LineNumber = TF_string;
                            }
                            else
                                ct.IsMixed = true;
                        } 
                        else
                        {
                            xse.SchemaTypeName = ST_string;
                            xse.LineNumber = TF_string;
                        }
                    }
                    if (bCreatingNewType) 
                    {
                        xse.LineNumber = TF_string;
                        //xse.SchemaTypeName = ST_string; //my change
                    }
                    else
                    {
                        if (null != ct)
                        {
                            if (null!= ct.Particle) 
                            {
                                ct.Particle.MinOccurs = 0;
                            }
                            else if (null != ct.ContentModel)
                            {
                                XmlSchemaSimpleContentExtension sce = CheckSimpleContentExtension(ct);
                                sce.BaseTypeName = ST_string;
                                sce.LineNumber = TF_string;
                            }
                        }
                        else if (!xse.SchemaTypeName.IsEmpty)
                        {
                            xse.LineNumber = TF_string;
                            xse.SchemaTypeName = ST_string;
                        }
                    }

                    return; //<element attr="232"></element>
                }
                int iChildNumber = 0;
                bool bCreatingNewSequence = false;
                while (!xtr.EOF && (xtr.NodeType != XmlNodeType.EndElement))
                {
                    bool bNextNodeAlreadyRead = false;  //In some cases we have to look ahead one node. If true means that we did look ahead.
                    iChildNumber++;
                    if ((xtr.NodeType == XmlNodeType.Text) || (xtr.NodeType == XmlNodeType.CDATA) ) //node can be simple type, complex with simple content or complex with mixed content
                    {
                        if (null != ct)
                        {
                            if (null != ct.Particle)
                            {
                                ct.IsMixed = true;
                                if (iChildNumber==1)
                                {
                                    //if this is the only child and other elements do not follow, we must set particle minOccurs="0"
                                    do{ xtr.Read();} while( (!xtr.EOF) && ((xtr.NodeType == XmlNodeType.CDATA)||(xtr.NodeType == XmlNodeType.Text) ||  (xtr.NodeType == XmlNodeType.Comment) || (xtr.NodeType == XmlNodeType.ProcessingInstruction) || (xtr.NodeType == XmlNodeType.Whitespace) || (xtr.NodeType == XmlNodeType.SignificantWhitespace) || (xtr.NodeType == XmlNodeType.XmlDeclaration)));
                                    bNextNodeAlreadyRead = true;
                                    if (xtr.NodeType == XmlNodeType.EndElement)
                                        ct.Particle.MinOccurs=decimal.Zero;
                                }
                            }
                            else if (null!=ct.ContentModel)
                            {   //complexType with simpleContent
                                XmlSchemaSimpleContentExtension sce = CheckSimpleContentExtension(ct);
                                if ((xtr.NodeType == XmlNodeType.Text) && (iChildNumber==1))
                                {
                                    int SimpleType = -1;
                                    if (xse.Parent == null)
                                    {
                                        SimpleType = sce.LineNumber; // we use LineNumber to represent valid type flags
                                    }
                                    else
                                    {
                                        SimpleType = GetSchemaType(sce.BaseTypeName);
                                        xse.Parent = null;
                                    }
                                    sce.BaseTypeName = RefineSimpleType(xtr.Value, ref SimpleType);
                                    sce.LineNumber = SimpleType; // we use LineNumber to represent valid type flags
                                }
                                else
                                {
                                    sce.BaseTypeName = ST_string;
                                    sce.LineNumber = TF_string;
                                }
                            }
                            else
                            {
                                //attributes exist, but both Particle and ContentModel == null - this must be complex type with simpleContent extension
                                XmlSchemaSimpleContent sc = new XmlSchemaSimpleContent();
                                ct.ContentModel = sc;
                                XmlSchemaSimpleContentExtension sce = new XmlSchemaSimpleContentExtension();
                                sc.Content = sce;

                                MoveAttributes(ct, sce, bCreatingNewType);

                                if (xtr.NodeType == XmlNodeType.Text)
                                {
                                    int TypeFlags;
                                    if(!bCreatingNewType)
                                        //previously this was empty element
                                        TypeFlags=TF_string;
                                    else
                                        TypeFlags = -1;
                                    sce.BaseTypeName = RefineSimpleType(xtr.Value, ref TypeFlags);
                                    sce.LineNumber = TypeFlags; // we use LineNumber to store flags of valid types
                                }
                                else
                                {
                                    sce.BaseTypeName = ST_string;
                                    sce.LineNumber = TF_string;
                                }
                                
                            }
                        }
                        else
                        {   //node is currently empty or with SimpleType
                            //node will become simple type
                            if (iChildNumber>1)
                            {
                                //more than one consecutive text nodes probably with PI in between
                                xse.SchemaTypeName = ST_string;
                                xse.LineNumber = TF_string;// we use LineNumber to store flags of valid types
                            }
                            else
                            {
                                int TypeFlags = -1;
                                if (bCreatingNewType)
                                    if (xtr.NodeType == XmlNodeType.Text)
                                    {
                                        xse.SchemaTypeName = RefineSimpleType(xtr.Value, ref TypeFlags);
                                        xse.LineNumber = TypeFlags; // we use LineNumber to store flags of valid types
                                    }
                                    else
                                    {
                                        xse.SchemaTypeName = ST_string;
                                        xse.LineNumber = TF_string;// we use LineNumber to store flags of valid types
                                    }
                                else if (xtr.NodeType == XmlNodeType.Text)
                                {
                                    if (xse.Parent == null)
                                    {
                                        TypeFlags = xse.LineNumber;
                                    }
                                    else
                                    {
                                        TypeFlags = GetSchemaType(xse.SchemaTypeName);
                                        if (TypeFlags == -1 && xse.LineNumber == TF_string) { //Since schemaTypeName is not set for empty elements (<e></e>)
                                            TypeFlags = TF_string;
                                        }
                                        xse.Parent = null;
                                    }
                                    xse.SchemaTypeName = RefineSimpleType(xtr.Value, ref TypeFlags);    //simple type
                                    xse.LineNumber = TypeFlags; // we use LineNumber to store flags of valid types
                                }
                                else
                                {
                                    xse.SchemaTypeName = ST_string;
                                    xse.LineNumber = TF_string;// we use LineNumber to store flags of valid types
                                }
                            }
                        } 
                    }
                    else if (xtr.NodeType == XmlNodeType.Element)
                    {
                        XmlQualifiedName qname = new XmlQualifiedName(xtr.LocalName, xtr.NamespaceURI);
                        bool Maxoccursflag = false;
                        if (table.Contains(qname)) 
                        {
                            Maxoccursflag = true;
                        }
                        else 
                        {
                            table.Add(qname, null);
                        }
                        if (ct==null)
                        { //untill now the element was empty or SimpleType - it now becomes complex type
                            ct = new XmlSchemaComplexType();
                            xse.SchemaType = ct;
                            if (!xse.SchemaTypeName.IsEmpty)
                            {
                                ct.IsMixed=true;
                                xse.SchemaTypeName = XmlQualifiedName.Empty;
                            }
                        }
                        if (ct.ContentModel !=null)
                        {   //type was previously identified as simple content extension - we need to convert it to sequence
                            XmlSchemaSimpleContentExtension sce = CheckSimpleContentExtension(ct);
                            MoveAttributes(sce, ct);
                            ct.ContentModel = null;
                            ct.IsMixed = true;
                            if (ct.Particle != null)
                                throw new XmlSchemaInferenceException(Res.SchInf_particle, 0, 0);
                            ct.Particle = new XmlSchemaSequence();
                            bCreatingNewSequence = true;
                            XmlSchemaElement subelement = AddElement(xtr.LocalName, xtr.Prefix, xtr.NamespaceURI, parentSchema,((XmlSchemaSequence)ct.Particle).Items, -1);
                            lastUsedSeqItem = 0;
                            if (!bCreatingNewType)
                                ct.Particle.MinOccurs=0;    //previously this was simple type so subelements did not exist
                        }
                        else if (ct.Particle == null)
                        {
                            ct.Particle = new XmlSchemaSequence();
                            bCreatingNewSequence = true;
                            XmlSchemaElement subelement = AddElement(xtr.LocalName, xtr.Prefix, xtr.NamespaceURI, parentSchema,((XmlSchemaSequence)ct.Particle).Items, -1);
                            if (!bCreatingNewType)
                            {
                                ((XmlSchemaSequence)ct.Particle).MinOccurs = decimal.Zero;
                                //  subelement.MinOccurs = decimal.Zero;
                            }
                    
                            lastUsedSeqItem = 0;
                        }
                        else
                        {
                            bool bParticleChanged = false;
                            XmlSchemaElement subelement = FindMatchingElement(bCreatingNewType || bCreatingNewSequence, xtr, ct, ref lastUsedSeqItem, ref bParticleChanged, parentSchema, Maxoccursflag);
                        }
                    }
                    else if (xtr.NodeType == XmlNodeType.Text)
                    {
                        if (ct==null)
                            throw new XmlSchemaInferenceException(Res.SchInf_ct, 0, 0);
                        ct.IsMixed = true;
                    }
                    do
                    { 
                        if (xtr.NodeType == XmlNodeType.EntityReference)
                        {
                            throw new XmlSchemaInferenceException(Res.SchInf_entity, 0, 0);

                        }
                        if (!bNextNodeAlreadyRead)
                        {
                            xtr.Read();
                        }
                        else
                        {
                            bNextNodeAlreadyRead = false;
                        }
                    } while( (!xtr.EOF) && (xtr.NodeType != XmlNodeType.EndElement) && (xtr.NodeType != XmlNodeType.CDATA)&&(xtr.NodeType != XmlNodeType.Element)&&(xtr.NodeType != XmlNodeType.Text));
                }
                if (lastUsedSeqItem != -1)
                {
                    //Verify if all elements in a sequence exist, if not set MinOccurs=0
                    while (++lastUsedSeqItem < ((XmlSchemaSequence)ct.Particle).Items.Count)
                    {
                        if (((XmlSchemaSequence)ct.Particle).Items[lastUsedSeqItem].GetType() != typeof (XmlSchemaElement))
                            throw new XmlSchemaInferenceException(Res.SchInf_seq, 0 , 0);
                        XmlSchemaElement subElement = (XmlSchemaElement) ((XmlSchemaSequence)ct.Particle).Items[lastUsedSeqItem];
                        subElement.MinOccurs = 0;
                    }
                }

            }