internal XPathNodeViewPropertyDescriptor(Shape rowShape, Shape colShape, int colIndex) : base( colShape.Name, null) { this.rowShape = rowShape; this.colShape = colShape; this.colIndex = colIndex; }
public void AddAttrShapeAt(Shape shape, int pos) { if (null == this.subShapes) this.subShapes = new ArrayList(); this.subShapes.Insert(pos, shape); }
internal XPathNodeViewPropertyDescriptor(Shape rowShape) : base( rowShape.Name, null) { this.rowShape = rowShape; this.colShape = rowShape; this.colIndex = 0; }
internal XPathDocumentView(XPathNode root, ArrayList rows, Shape rowShape) { this.rows = rows; this.rowShape = rowShape; this.ndRoot = root; }
public void AddSubShape(Shape shape) { if (null == this.subShapes) this.subShapes = new ArrayList(); this.subShapes.Add(shape); foreach (object p in shape.Particles) { XmlSchemaElement xse = p as XmlSchemaElement; if (null != xse) AddParticle(xse); } }
void DeriveShapeFromRows() { object schemaInfo = null; for (int i=0; (i<rows.Count) && (null==schemaInfo); i++) { XPathNode nd = rows[i] as XPathNode; Debug.Assert(null != nd && (XPathNodeType.Attribute == nd.NodeType || XPathNodeType.Element == nd.NodeType)); if (null != nd) { if (XPathNodeType.Attribute == nd.NodeType) schemaInfo = nd.SchemaAttribute; else schemaInfo = nd.SchemaElement; } } if (0 == rows.Count) { throw new NotImplementedException("XPath failed to match an elements"); } if (null == schemaInfo) { rows.Clear(); throw new XmlException(Res.XmlDataBinding_NoSchemaType, (string[])null); } ShapeGenerator shapeGen = new ShapeGenerator(this.namespaceResolver); XmlSchemaElement xse = schemaInfo as XmlSchemaElement; if (null != xse) this.rowShape = shapeGen.GenerateFromSchema(xse); else this.rowShape = shapeGen.GenerateFromSchema((XmlSchemaAttribute)schemaInfo); }
public ContentIterator(XPathNode nd, Shape shape) { this.node = nd; XmlSchemaElement xse = shape.XmlSchemaElement; Debug.Assert(null != xse); SchemaElementDecl decl = xse.ElementDecl; Debug.Assert(null != decl); this.contentValidator = decl.ContentValidator; this.currentState = new ValidationState(); this.contentValidator.InitValidation(this.currentState); this.currentState.ProcessContents = XmlSchemaContentProcessing.Strict; if (nd != null) Advance(); }
object FillColumn(ContentIterator iter, Shape shape) { object val; switch (shape.BindingType) { case BindingType.Element: val = iter.Node; iter.Next(); break; case BindingType.ElementNested: { ArrayList rows = new ArrayList(); rows.Add(iter.Node); iter.Next(); val = new XPathDocumentView(null, rows, shape.NestedShape); break; } case BindingType.Repeat: { ArrayList rows = new ArrayList(); Shape subShape = shape.SubShape(0); if (subShape.BindingType == BindingType.ElementNested) { Shape nestShape = subShape.NestedShape; XPathDocumentView xivc = new XPathDocumentView(null, null, nestShape); XPathNode nd; while (null != (nd = iter.Node) && subShape.IsParticleMatch(iter.Particle)) { rows.Add(nd); iter.Next(); } xivc.SetRows(rows); val = xivc; } else { XPathDocumentView xivc = new XPathDocumentView(null, null, subShape); XPathNode nd; while (null != (nd = iter.Node) && shape.IsParticleMatch(iter.Particle)) { rows.Add(xivc.FillSubRow(iter, subShape, null)); } xivc.SetRows(rows); val = xivc; } break; } case BindingType.Sequence: case BindingType.Choice: case BindingType.All: { XPathDocumentView docview = new XPathDocumentView(null, null, shape); ArrayList rows = new ArrayList(); rows.Add(docview.FillSubRow(iter, shape, null)); docview.SetRows(rows); val = docview; break; } default: case BindingType.Text: case BindingType.Attribute: throw new NotSupportedException(); } return val; }
XPathNodeView FillSubRow(ContentIterator iter, Shape shape, object[] columns) { if (null == columns) { int colCount = shape.SubShapes.Count; if (0 == colCount) colCount = 1; columns = new object[colCount]; } switch (shape.BindingType) { case BindingType.Element: columns[0] = FillColumn(iter, shape); break; case BindingType.Sequence: { int iPrev = -1; int i; while (null != iter.Node) { i = shape.FindMatchingSubShape(iter.Particle); if (i <= iPrev) break; columns[i] = FillColumn(iter, shape.SubShape(i)); iPrev = i; } break; } case BindingType.All: { while (null != iter.Node) { int i = shape.FindMatchingSubShape(iter.Particle); if (-1 == i || null != columns[i]) break; columns[i] = FillColumn(iter, shape.SubShape(i)); } break; } case BindingType.Choice: { int i = shape.FindMatchingSubShape(iter.Particle); if (-1 != i) { columns[i] = FillColumn(iter, shape.SubShape(i)); } break; } case BindingType.Repeat: default: // should not map to a row throw new NotSupportedException(); } return new XPathNodeView(this, null, columns); }
XPathNodeView FillRow(XPathNode ndRow, Shape shape) { object[] columns; XPathNode nd; switch (shape.BindingType) { case BindingType.Text: case BindingType.Attribute: columns = new object[1]; columns[0] = ndRow; return new XPathNodeView(this, ndRow, columns); case BindingType.Repeat: columns = new object[1]; nd = TreeNavigationHelper.GetContentChild(ndRow); columns[0] = FillColumn(new ContentIterator(nd, shape), shape); return new XPathNodeView(this, ndRow, columns); case BindingType.Sequence: case BindingType.Choice: case BindingType.All: int subShapesCount = shape.SubShapes.Count; columns = new object[subShapesCount]; if (shape.BindingType == BindingType.Sequence && shape.SubShape(0).BindingType == BindingType.Attribute) { FillAttributes(ndRow, shape, columns); } Shape lastSubShape = (Shape)shape.SubShapes[subShapesCount - 1]; if (lastSubShape.BindingType == BindingType.Text) { //Attributes followed by simpe content or mixed content columns[subShapesCount - 1] = ndRow; return new XPathNodeView(this, ndRow, columns); } else { nd = TreeNavigationHelper.GetContentChild(ndRow); return FillSubRow(new ContentIterator(nd, shape), shape, columns); } default: // should not map to a row #if DEBUG throw new NotSupportedException("Unable to bind row to: "+shape.BindingType.ToString()); #else throw new NotSupportedException(); #endif } }
void FillAttributes(XPathNode nd, Shape shape, object[] cols) { int i = 0; while (i < cols.Length) { Shape attrShape = shape.SubShape(i); if (attrShape.BindingType != BindingType.Attribute) break; XmlQualifiedName name = attrShape.AttributeName; XPathNode ndAttr = nd.GetAttribute( name.Name, name.Namespace ); if (null != ndAttr) cols[i] = ndAttr; i++; } }
Shape ProcessParticle(XmlSchemaParticle xsp, Shape parent) { Shape s; if (xsp == XmlSchemaParticle.Empty) { return null; } if (xsp is XmlSchemaElement) { s = ProcessParticleElement((XmlSchemaElement)xsp); } else if (xsp is XmlSchemaSequence) { s = ProcessParticleGroup((XmlSchemaSequence)xsp, BindingType.Sequence); } else if (xsp is XmlSchemaChoice) { s = ProcessParticleGroup((XmlSchemaChoice)xsp, BindingType.Choice); } else if (xsp is XmlSchemaAll) { s = ProcessParticleGroup((XmlSchemaAll)xsp, BindingType.All); } else { //XmlSchemaAny return null; //Ignore Any in the content model } if (xsp.MaxOccurs > 1) { Shape rep = new Shape(s.Name, BindingType.Repeat); rep.AddSubShape(s); s = rep; } if (parent != null) parent.AddSubShape(s); return s; }
public Shape GenerateFromSchema(XmlSchemaAttribute xsa) { Shape s = new Shape(GenName(xsa.QualifiedName), BindingType.Attribute); s.AddParticle(xsa); return s; }
public Shape GenerateFromSchema(XmlSchemaElement xse) { XmlQualifiedName xseName = xse.QualifiedName; XmlSchemaType schemaType = xse.ElementSchemaType; XmlSchemaComplexType complexType = schemaType as XmlSchemaComplexType; if (null != complexType) { XmlSchemaParticle particle = null; Shape rootShape = null; XmlSchemaContentType contentType = complexType.ElementDecl.ContentValidator.ContentType; switch (contentType) { case XmlSchemaContentType.Mixed: case XmlSchemaContentType.TextOnly: rootShape = new Shape(GenName(xseName) + "_Text", BindingType.Text); rootShape.AddParticle(xse); break; case XmlSchemaContentType.Empty: rootShape = new Shape(null, BindingType.Sequence); break; case XmlSchemaContentType.ElementOnly: particle = complexType.ContentTypeParticle; rootShape = ProcessParticle(particle, null); break; } Debug.Assert(rootShape != null); if (complexType.AttributeUses.Values.Count > 0) { if (rootShape.BindingType != BindingType.Sequence) { Shape s = new Shape(null, BindingType.Sequence); s.AddSubShape(rootShape); rootShape = s; } int pos = 0; string[] names = rootShape.SubShapeNames(); ICollection attributes = complexType.AttributeUses.Values; XmlSchemaAttribute[] xsaArray = new XmlSchemaAttribute[attributes.Count]; attributes.CopyTo(xsaArray, 0); Array.Sort(xsaArray, new XmlSchemaAttributeComparer()); foreach(XmlSchemaAttribute xsa in xsaArray) { string name = GenAttrName(xsa.QualifiedName, names); Shape attrShape = new Shape(name, BindingType.Attribute); attrShape.AddParticle(xsa); rootShape.AddAttrShapeAt(attrShape, pos++); } } if (rootShape.BindingType != BindingType.Text) { rootShape.Name = GenName(xseName); rootShape.ContainerDecl = xse; } return rootShape; } else { // simple type Shape s = new Shape(GenName(xseName), BindingType.Text); s.AddParticle(xse); return s; } }
Shape ProcessParticleGroup(XmlSchemaGroupBase xsg, BindingType bt) { Shape s = new Shape(null, bt); StringBuilder sb = new StringBuilder(); foreach (XmlSchemaParticle xsp in xsg.Items) { Shape sub = ProcessParticle(xsp, s); if (sub != null) { //sub can be null if the child particle is xs:any if (sb.Length > 0) sb.Append('_'); sb.Append(sub.Name); } } // need to also test if paretn != null for this to work //if (s.IsGroup && s.SubShapes.Count == 1) { // Shape sub = (Shape)s.SubShapes[0]; // s.Clear(); // return sub; //} s.Name = sb.ToString(); return s; }
Shape ProcessParticleElement(XmlSchemaElement xse) { // watch out for recursive schema Shape s = (Shape)this.elementTypesProcessed[xse]; if (null != s) return s; bool complex = xse.ElementSchemaType is XmlSchemaComplexType; s = new Shape(GenName(xse.QualifiedName), complex ? BindingType.ElementNested : BindingType.Element); s.AddParticle(xse); if (complex) { this.elementTypesProcessed.Add(xse, s); s.NestedShape = GenerateFromSchema(xse); this.elementTypesProcessed.Remove(xse); } return s; }