internal static IEnumerable <DirectRelationship> Connect(IEnumerable <DirectRelationship> relationships) { List <DirectRelationship> rels = new List <DirectRelationship>(relationships); List <DirectRelationship> list = new List <DirectRelationship>(); DirectRelationship rel = rels.First(); rels.Remove(rel); list.Add(rel); Connect(rel, rels, list); if (list.Count < relationships.Count()) { List <string> connList = new List <string>(list.Select(r => r.Entity)) { list.Last().RelatedEntity }; List <string> originalList = new List <string>(relationships.Select(r => r.Entity)) { relationships.Last().RelatedEntity }; List <string> mesgList = new List <string> { string.Join("-", connList) }; mesgList.AddRange(originalList.Except(connList)); throw new SchemaException(string.Format(SchemaMessages.DirectRelationshipsNonConnected, string.Join(",", mesgList))); } return(list); }
protected Relationship(IEnumerable <DirectRelationship> relationships) { IEnumerable <DirectRelationship> rels = DirectRelationship.Connect(relationships); Entity = rels.First().Entity; RelatedEntity = rels.Last().RelatedEntity; DirectRelationships = rels.ToArray(); }
private static void Connect(DirectRelationship relationship, List <DirectRelationship> relationships, List <DirectRelationship> list) { DirectRelationship prev = relationships.FirstOrDefault(r => r.RelatedEntity == relationship.Entity); if (prev == null) { DirectRelationship rel = relationships.FirstOrDefault(r => r.Entity == relationship.Entity); if (rel is OneToOneDirectRelationship) { prev = rel.Reverse(); relationships.Remove(rel); } } else { relationships.Remove(prev); } if (prev != null) { int index = list.IndexOf(relationship); list.Insert(index, prev); Connect(prev, relationships, list); } DirectRelationship next = relationships.FirstOrDefault(r => r.Entity == relationship.RelatedEntity); if (next == null) { DirectRelationship rel = relationships.FirstOrDefault(r => r.RelatedEntity == relationship.RelatedEntity); if (rel is OneToOneDirectRelationship) { next = rel.Reverse(); relationships.Remove(rel); } } else { relationships.Remove(next); } if (next != null) { list.Add(next); Connect(next, relationships, list); } }
private static IEnumerable <T> GenerateDirectRelationships <T>(string value) where T : DirectRelationship { List <T> rels = new List <T>(); KeyValuePair <string, string[]>[] segments = GetSegments(value); string entity = segments[0].Key; string[] properties = segments[0].Value; for (int i = 0; i < segments.Length - 1; i++) { string relatedEntity = segments[i + 1].Key; string[] nextProps = segments[i + 1].Value; string[] relatedProperties = new string[properties.Length]; Array.Copy(nextProps, relatedProperties, properties.Length); string[] remain = new string[nextProps.Length - properties.Length]; Array.Copy(nextProps, properties.Length, remain, 0, remain.Length); DirectRelationship rel; if (typeof(T) == typeof(ManyToOneDirectRelationship)) { rel = new ManyToOneDirectRelationship(entity, relatedEntity, properties, relatedProperties); } else if (typeof(T) == typeof(OneToManyDirectRelationship)) { rel = new OneToManyDirectRelationship(entity, relatedEntity, properties, relatedProperties); } else if (typeof(T) == typeof(OneToOneDirectRelationship)) { rel = new OneToOneDirectRelationship(entity, relatedEntity, properties, relatedProperties); } else { rel = new DirectRelationship(entity, relatedEntity, properties, relatedProperties); } rels.Add(rel as T); entity = relatedEntity; properties = remain; } return(rels); }
public DirectRelationship Reverse() { DirectRelationship relationship = this; if (relationship is ManyToOneDirectRelationship) { return(new OneToManyDirectRelationship(relationship as ManyToOneDirectRelationship)); } else if (relationship is OneToManyDirectRelationship) { return(new ManyToOneDirectRelationship(relationship as OneToManyDirectRelationship)); } else if (relationship is OneToOneDirectRelationship) { return(new OneToOneDirectRelationship(relationship.RelatedEntity, relationship.Entity, relationship.RelatedProperties.ToArray(), relationship.Properties.ToArray())); } else { throw new NotSupportedException(relationship.GetType().ToString()); // never } }
internal static IEnumerable <DirectRelationship> GetDirectRelationships(this XElement schema, string entity) { Dictionary <string, DirectRelationship> directRelationships = new Dictionary <string, DirectRelationship>(); XElement entitySchema = schema.GetEntitySchema(entity); IEnumerable <XElement> collProps = entitySchema.Elements(SchemaVocab.Property).Where(p => p.Attribute(SchemaVocab.Collection) != null); foreach (XElement collProp in collProps) { string collection = collProp.Attribute(SchemaVocab.Collection).Value; string relatedEntity = schema.GetEntitySchemaByCollection(collection).Attribute(SchemaVocab.Name).Value; string relationshipString = collProp.Attribute(SchemaVocab.Relationship).Value; Relationship oRelationship = new Relationship(relationshipString, entity, relatedEntity, schema); DirectRelationship first = oRelationship.DirectRelationships[0]; string key = first.ToString(); if (!directRelationships.ContainsKey(key)) { directRelationships.Add(key, first); } } return(directRelationships.Values); }
private static PlainRelationship CreatePlainRelationship(XElement relationshipSchema) { PlainRelationship relationship; if (relationshipSchema.Elements(SchemaVocab.Relationship).Any()) { string type = relationshipSchema.Attribute(SchemaVocab.Type).Value; string entity = relationshipSchema.Attribute(SchemaVocab.Entity).Value; string relatedEntity = relationshipSchema.Attribute(SchemaVocab.RelatedEntity).Value; List <DirectRelationship> relList = new List <DirectRelationship>(); foreach (XElement xDirectRelationship in relationshipSchema.Elements(SchemaVocab.Relationship)) { DirectRelationship rel = DirectRelationship.Create(xDirectRelationship, type); relList.Add(rel); } IEnumerable <DirectRelationship> rels = DirectRelationship.Connect(relList); switch (type) { case SchemaVocab.ManyToOne: relationship = new ManyToOneRelationship(entity, relatedEntity, rels); break; case SchemaVocab.OneToMany: relationship = new OneToManyRelationship(entity, relatedEntity, rels); break; case SchemaVocab.OneToOne: relationship = new OneToOneRelationship(entity, relatedEntity, rels); break; default: throw new NotSupportedException(type); } } else { DirectRelationship rel = DirectRelationship.Create(relationshipSchema); List <DirectRelationship> relList = new List <DirectRelationship>() { rel }; if (rel is ManyToOneDirectRelationship) { relationship = new ManyToOneRelationship(rel.Entity, rel.RelatedEntity, relList); } else if (rel is OneToManyDirectRelationship) { relationship = new OneToManyRelationship(rel.Entity, rel.RelatedEntity, relList); } else if (rel is OneToOneDirectRelationship) { relationship = new OneToOneRelationship(rel.Entity, rel.RelatedEntity, relList); } else { throw new NotSupportedException(rel.GetType().ToString()); // never } } XAttribute attr = relationshipSchema.Attribute(SchemaVocab.Name); if (attr != null) { relationship.Name = attr.Value; } return(relationship); }
private static XElement PlainRelationshipToXml(PlainRelationship relationship) { XElement relationshipSchema = new XElement(SchemaVocab.Relationship); relationshipSchema.SetAttributeValue(SchemaVocab.Name, relationship.Name); string type; if (relationship is ManyToOneRelationship) { type = SchemaVocab.ManyToOne; } else if (relationship is OneToManyRelationship) { type = SchemaVocab.OneToMany; } else if (relationship is OneToOneRelationship) { type = SchemaVocab.OneToOne; } else { throw new NotSupportedException(relationship.GetType().ToString()); // never } relationshipSchema.SetAttributeValue(SchemaVocab.Type, type); relationshipSchema.SetAttributeValue(SchemaVocab.Entity, relationship.Entity); relationshipSchema.SetAttributeValue(SchemaVocab.RelatedEntity, relationship.RelatedEntity); if (relationship.DirectRelationships.Length == 1) { DirectRelationship rel = relationship.DirectRelationships[0]; for (int i = 0; i < rel.Properties.Length; i++) { XElement xProperty = new XElement(SchemaVocab.Property); xProperty.SetAttributeValue(SchemaVocab.Name, rel.Properties[i]); xProperty.SetAttributeValue(SchemaVocab.RelatedProperty, rel.RelatedProperties[i]); relationshipSchema.Add(xProperty); } } else { foreach (DirectRelationship rel in relationship.DirectRelationships) { XElement relSchema = new XElement(SchemaVocab.Relationship); string relType; if (rel is ManyToOneDirectRelationship) { relType = SchemaVocab.ManyToOne; } else if (rel is OneToManyDirectRelationship) { relType = SchemaVocab.OneToMany; } else if (rel is OneToOneDirectRelationship) { relType = SchemaVocab.OneToOne; } else { throw new NotSupportedException(rel.GetType().ToString()); // never } relSchema.SetAttributeValue(SchemaVocab.Type, relType); relSchema.SetAttributeValue(SchemaVocab.Entity, rel.Entity); relSchema.SetAttributeValue(SchemaVocab.RelatedEntity, rel.RelatedEntity); for (int i = 0; i < rel.Properties.Length; i++) { XElement xProperty = new XElement(SchemaVocab.Property); xProperty.SetAttributeValue(SchemaVocab.Name, rel.Properties[i]); xProperty.SetAttributeValue(SchemaVocab.RelatedProperty, rel.RelatedProperties[i]); relSchema.Add(xProperty); } relationshipSchema.Add(relSchema); } } return(relationshipSchema); }