protected void Create(T aggreg, XElement entitySchema, DirectRelationship parentRelationship, Dictionary <string, object> parentPropertyValues, string path, string entity, XElement schema)
        {
            CreateAggregation <T> createAggregation = CreateCreateAggregation(default(T), entity, schema);

            createAggregation.Split(aggreg, entitySchema, parentRelationship, parentPropertyValues, path);
            Commands.AddRange(createAggregation.ExecuteCommands);
        }
Example #2
0
        // ManyToMany
        protected Dictionary <string, object> TransPropertyValues(ManyToManyRelationship relationship,
                                                                  Dictionary <string, object> parent, Dictionary <string, object> child)
        {
            Dictionary <string, object> propertyValues = new Dictionary <string, object>();

            DirectRelationship firstDirectRelationship  = relationship.DirectRelationships[0];
            DirectRelationship secondDirectRelationship = relationship.DirectRelationships[1];

            for (int i = 0; i < firstDirectRelationship.Properties.Length; i++)
            {
                string propertyName        = firstDirectRelationship.Properties[i];
                string relatedPropertyName = firstDirectRelationship.RelatedProperties[i];
                propertyValues.Add(relatedPropertyName, parent[propertyName]);
            }

            for (int i = 0; i < secondDirectRelationship.RelatedProperties.Length; i++)
            {
                string relatedPropertyName = secondDirectRelationship.RelatedProperties[i];
                string propertyName        = secondDirectRelationship.Properties[i];

                propertyValues.Add(propertyName, child[relatedPropertyName]);
            }

            return(propertyValues);
        }
Example #3
0
        internal protected void Split(T obj, XElement entitySchema, DirectRelationship parentRelationship, Dictionary <string, object> parentPropertyValues, string path)
        {
            string entity = entitySchema.Attribute(SchemaVocab.Name).Value;

            InsertCommand <T> executeCommand = CreateInsertCommand(obj, entity);

            executeCommand.EntitySchema         = entitySchema;
            executeCommand.UniqueKeySchema      = GetKeySchema(entitySchema);
            executeCommand.ParentPropertyValues = parentPropertyValues;
            executeCommand.ParentRelationship   = parentRelationship;
            executeCommand.Path = path;

            //executeCommand.PropertyValues = GetPropertyValues(executeCommand, out Dictionary<XElement, T> childrenDict);

            executeCommand.PropertyValues = GetPropertyValues(executeCommand.AggregNode, executeCommand.EntitySchema);

            SetDefaultValues(executeCommand);

            Commands.Add(executeCommand);

            //
            IEnumerable <KeyValuePair <XElement, T> > propertySchemaChildrens = GetPropertySchemaChildrens(executeCommand.AggregNode, executeCommand.EntitySchema);

            foreach (KeyValuePair <XElement, T> childrenPair in propertySchemaChildrens)
            {
                XElement        propertySchema = childrenPair.Key;
                IEnumerable <T> children       = GetChildren(childrenPair.Value);

                //
                string childrenPath = path + propertySchema.Attribute(SchemaVocab.Name).Value;

                //
                XElement childEntitySchema = GetEntitySchemaByCollection(propertySchema.Attribute(SchemaVocab.Collection).Value);
                string   childEntity       = childEntitySchema.Attribute(SchemaVocab.Name).Value;

                //
                string       relationshipString = propertySchema.Attribute(SchemaVocab.Relationship).Value;
                Relationship childRelationship  = GetParentChildrenRelationship(relationshipString, entity, childEntity);
                if (childRelationship == null)
                {
                    continue;
                }

                if (childRelationship is ManyToManyRelationship)
                {
                    Split(children, childEntitySchema, childRelationship as ManyToManyRelationship, executeCommand.PropertyValues, childrenPath);
                    return;
                }

                int index = 0;
                foreach (T child in children)
                {
                    Split(child, childEntitySchema, childRelationship.DirectRelationships[0], executeCommand.PropertyValues,
                          string.Format("{0}[{1}]", childrenPath, index));
                    index++;
                }
            }
        }
Example #4
0
        // ManyToMany
        protected bool IsDeleteTransSetNull(ManyToManyRelationship relationship)
        {
            DirectRelationship firstDirectRelationship = relationship.DirectRelationships[0];

            // pure relationship-table
            if (relationship.DirectRelationships.Length == 2)
            {
                DirectRelationship secondDirectRelationship = relationship.DirectRelationships[1];
                string             relationshipEntity       = firstDirectRelationship.RelatedEntity;

                if (relationshipEntity == secondDirectRelationship.Entity) // assert
                {
                    List <string> relationshipProperties = new List <string>(firstDirectRelationship.RelatedProperties);
                    relationshipProperties.AddRange(secondDirectRelationship.Properties);

                    XElement entitySchema = Schema.GetEntitySchema(relationshipEntity);

                    List <string> PropertyNames = entitySchema.Elements(SchemaVocab.Property)
                                                  .Where(x => x.Attribute(SchemaVocab.Column) != null)
                                                  .Select(x => x.Attribute(SchemaVocab.Name).Value).ToList();

                    if (PropertyNames.Count == relationshipProperties.Count)
                    {
                        bool pure = true;
                        relationshipProperties.Sort();
                        PropertyNames.Sort();
                        for (int i = 0; i < PropertyNames.Count; i++)
                        {
                            if (relationshipProperties[i] == PropertyNames[i])
                            {
                                continue;
                            }
                            pure = false;
                        }
                        if (pure)
                        {
                            return(false);
                        }
                    }
                }
            }

            //
            string   mmEntity       = firstDirectRelationship.RelatedEntity;
            XElement mmEntitySchema = GetEntitySchema(mmEntity);

            for (int i = 0; i < firstDirectRelationship.RelatedProperties.Length; i++)
            {
                string   relatedPropertyName = firstDirectRelationship.RelatedProperties[i];
                XElement mmPropertySchema    = GetPropertySchema(mmEntitySchema, relatedPropertyName);
                if (mmPropertySchema.Attribute(SchemaVocab.AllowDBNull).Value == SchemaVocab.True)
                {
                    return(true);
                }
            }

            return(false);
        }
        protected void Delete(T aggreg, XElement entitySchema, DirectRelationship parentRelationship, Dictionary <string, object> parentPropertyValues, string path, string entity, XElement schema)
        {
            DeleteAggregation <T> deleteAggregation = CreateDeleteAggregation(default(T), entity, schema);

            deleteAggregation.Split(aggreg, entitySchema, parentRelationship, parentPropertyValues, path);

            // reverse back
            IEnumerable <ExecuteCommand <T> > executeCommands = deleteAggregation.ExecuteCommands.Reverse();

            DeleteCommands.AddRange(executeCommands);
        }
        protected Dictionary <ExpandNode, TempTableNode> CreateChildren(IEnumerable <ExpandNode> qChildren, TempTableNode node,
                                                                        out IEnumerable <string> relatedPropertiesForSelect)
        {
            Dictionary <ExpandNode, TempTableNode> childDict = new Dictionary <ExpandNode, TempTableNode>();

            List <string> childrenForSelect = new List <string>();

            foreach (ExpandNode qChild in qChildren)
            {
                TempTableNode child;
                string[]      select = new string[qChild.Query.Select.Properties.Length];
                qChild.Query.Select.Properties.CopyTo(select, 0);
                if (qChild is EntityExpandNode)
                {
                    child = new EntityTempNode(qChild.Property, select, qChild.Entity);
                }
                else if (qChild is CollectionExpandNode)
                {
                    Order[] orderby = GetOrders(qChild.Query);
                    child = new CollectionTempNode(qChild.Property, select, orderby, qChild.Entity);
                }
                else
                {
                    throw new NotSupportedException(qChild.GetType().ToString()); // never
                }
                child.Path = node.Path + "/" + qChild.Property;

                //
                DirectRelationship          firstDirectRelationship = qChild.Relationship.DirectRelationships[0];
                Dictionary <string, string> relatedKey = new Dictionary <string, string>();
                for (int i = 0; i < firstDirectRelationship.Properties.Length; i++)
                {
                    relatedKey.Add(firstDirectRelationship.Properties[i], firstDirectRelationship.RelatedProperties[i]);
                }
                child.RelatedKey = relatedKey;

                node.Children.Add(child);

                // NativeProperties
                childrenForSelect.AddRange(firstDirectRelationship.Properties);

                childDict.Add(qChild, child);
            }

            relatedPropertiesForSelect = childrenForSelect.Distinct();

            return(childDict);
        }
Example #7
0
        // ManyToMany
        protected XElement TransKeySchema(ManyToManyRelationship relationship, out XElement mmEntitySchema)
        {
            DirectRelationship oneToManyRelationship = relationship.DirectRelationships[0];
            DirectRelationship manyToOneRelationship = relationship.DirectRelationships[1];

            string mmEntity = oneToManyRelationship.RelatedEntity;

            mmEntitySchema = GetEntitySchema(mmEntity);

            XElement             mmKeySchema        = new XElement(mmEntitySchema.Name);
            IEnumerable <string> mmKeyPropertyNames = oneToManyRelationship.RelatedProperties.Union(manyToOneRelationship.Properties);

            foreach (string mmPropertyName in mmKeyPropertyNames)
            {
                mmKeySchema.Add(mmEntitySchema.Elements(SchemaVocab.Property).First(p => p.Attribute(SchemaVocab.Name).Value == mmPropertyName));
            }

            return(mmKeySchema);
        }
Example #8
0
        internal static ForeignKey CreateUndirectedForeignKey(this DirectRelationship relationship, XElement schema)
        {
            XElement      entitySchema = schema.GetEntitySchema(relationship.Entity);
            string        table        = entitySchema.Attribute(SchemaVocab.Table).Value;
            List <string> columns      = new List <string>();

            foreach (string property in relationship.Properties)
            {
                XElement propertySchema = entitySchema.Elements(SchemaVocab.Property).First(x => x.Attribute(SchemaVocab.Name).Value == property);
                columns.Add(propertySchema.Attribute(SchemaVocab.Column).Value);
            }

            XElement      relatedEntitySchema = schema.GetEntitySchema(relationship.RelatedEntity);
            string        relatedTable        = relatedEntitySchema.Attribute(SchemaVocab.Table).Value;
            List <string> relatedColumns      = new List <string>();

            foreach (string property in relationship.RelatedProperties)
            {
                XElement relatedPropertySchema = relatedEntitySchema.Elements(SchemaVocab.Property).First(x => x.Attribute(SchemaVocab.Name).Value == property);
                relatedColumns.Add(relatedPropertySchema.Attribute(SchemaVocab.Column).Value);
            }

            return(new ForeignKey(table, relatedTable, columns, relatedColumns));
        }
        protected int Execute_Original(UpdateCommandNode <T> node, Modifier <T> modifier)
        {
            int affected = Execute(node as UpdateCommand <T>, modifier);

            if (node.ChildrenCollection.Count == 0)
            {
                return(affected);
            }

            //
            foreach (UpdateCommandNodeChildren <T> nodeChildren in node.ChildrenCollection)
            {
                string childrenPath = nodeChildren.Path;

                DirectRelationship relationship      = nodeChildren.ParentRelationship;
                string             childEntity       = relationship.RelatedEntity;
                XElement           childEntitySchema = node.Schema.GetEntitySchema(childEntity);
                XElement           childKeySchema    = SchemaHelper.GetKeySchema(childEntitySchema);

                Dictionary <string, object> relatedPropertyValues = GetRelatedPropertyValues(relationship, node, out Dictionary <string, object> dbPropertyValues);

                //
                IEnumerable <IReadOnlyDictionary <string, object> > refetchedChildPVs = FetchRelatedFromDb(relatedPropertyValues, relationship.RelatedEntity, node.Schema);
                IEnumerable <IReadOnlyDictionary <string, object> > origChildPVs      = nodeChildren.UpdateCommandNodes.Select(n => n.OrigPropertyValues);
                foreach (IReadOnlyDictionary <string, object> refetchedChildPV in refetchedChildPVs)
                {
                    Dictionary <string, object> refetchedKeyChildPV = new Dictionary <string, object>();
                    foreach (string property in childKeySchema.Elements(SchemaVocab.Property).Select(x => x.Attribute(SchemaVocab.Name).Value))
                    {
                        refetchedKeyChildPV.Add(property, refetchedChildPV[property]);
                    }

                    IReadOnlyDictionary <string, object> found = Find(origChildPVs, refetchedKeyChildPV);
                    if (found == null)
                    {
                        throw new ConstraintException(ErrorMessages.InsertedByAnotherUser);
                    }
                }

                //
                foreach (UpdateCommandNode <T> childNode in nodeChildren.UpdateCommandNodes)
                {
                    if (childNode.AggregNode == null)
                    {
                        continue;
                    }

                    // establishing relationship
                    foreach (KeyValuePair <string, object> propertyValue in relatedPropertyValues)
                    {
                        if (!childNode.FixedUpdatePropertyValues.ContainsKey(propertyValue.Key))
                        {
                            childNode.FixedUpdatePropertyValues.Add(propertyValue.Key, propertyValue.Value);
                        }
                    }

                    //
                    Execute_Original(childNode, modifier);
                }
            }

            return(affected);
        }
Example #10
0
 public UpdateCommandNodeChildren(DirectRelationship oneToManyRelationship, string path)
 {
     ParentRelationship = oneToManyRelationship;
     Path = path;
 }
Example #11
0
        protected UpdateCommandNode <T> Split(T aggregNode, string entity, XElement entitySchema, XElement uniqueKeySchema, XElement concurrencySchema,
                                              DirectRelationship parentRelationship, Dictionary <string, object> parentPropertyValues, string path)
        {
            UpdateCommandNode <T> executeCommand = CreateUpdateCommandNode(aggregNode, entity);

            executeCommand.EntitySchema         = entitySchema;
            executeCommand.UniqueKeySchema      = uniqueKeySchema;
            executeCommand.ConcurrencySchema    = concurrencySchema;
            executeCommand.ParentPropertyValues = parentPropertyValues;
            executeCommand.ParentRelationship   = parentRelationship;
            executeCommand.Path = path;

            executeCommand.PropertyValues = GetPropertyValues(aggregNode, entitySchema);

            //executeCommand.FixedUpdatePropertyValues = new Dictionary<string, object>();

            //
            IEnumerable <KeyValuePair <XElement, T> > propertySchemaChildrens = GetPropertySchemaChildrens(aggregNode, entitySchema);

            foreach (KeyValuePair <XElement, T> childrenPair in propertySchemaChildrens)
            {
                XElement        propertySchema = childrenPair.Key;
                IEnumerable <T> children       = GetChildren(childrenPair.Value);

                //
                string childPath = path + propertySchema.Attribute(SchemaVocab.Name).Value;

                //
                XElement childEntitySchema = GetEntitySchemaByCollection(propertySchema.Attribute(SchemaVocab.Collection).Value);
                string   childEntity       = childEntitySchema.Attribute(SchemaVocab.Name).Value;

                //
                string       relationshipString = propertySchema.Attribute(SchemaVocab.Relationship).Value;
                Relationship childRelationship  = GetParentChildrenRelationship(relationshipString, entity, childEntity);
                if (childRelationship == null)
                {
                    continue;
                }

                //
                UpdateCommandNodeChildren <T> nodeChildren = new UpdateCommandNodeChildren <T>(childRelationship.DirectRelationships[0], path);
                executeCommand.ChildrenCollection.Add(nodeChildren);

                if (childRelationship is ManyToManyRelationship)
                {
                    Split(children, childEntitySchema, childRelationship as ManyToManyRelationship, executeCommand.PropertyValues, childPath, nodeChildren.UpdateCommandNodes);
                }
                else
                {
                    XElement childKeySchema         = GetKeySchema(childEntitySchema);
                    XElement childConcurrencySchema = GetConcurrencySchema(childEntitySchema);

                    int index = 0;
                    foreach (T child in children)
                    {
                        UpdateCommandNode <T> childNode = Split(child, childEntity, childEntitySchema, childKeySchema, childConcurrencySchema,
                                                                childRelationship.DirectRelationships[0], executeCommand.PropertyValues,
                                                                string.Format("{0}[{1}]", childPath, index));
                        nodeChildren.UpdateCommandNodes.Add(childNode);
                        index++;
                    }
                }
            }

            return(executeCommand);
        }
Example #12
0
        internal static ForeignKey CreateForeignKey(this DirectRelationship directRelationship, XElement schema)
        {
            DirectRelationship relationship = (directRelationship is OneToManyDirectRelationship) ? directRelationship.Reverse() : directRelationship;

            return(CreateUndirectedForeignKey(relationship, schema));
        }
Example #13
0
        internal protected void Split(IEnumerable <T> children, XElement childEntitySchema, ManyToManyRelationship manyToManyRelationship, Dictionary <string, object> parentPropertyValues, string childrenPath)
        {
            string childEntity = childEntitySchema.Attribute(SchemaVocab.Name).Value;

            XElement mmKeySchema         = TransKeySchema(manyToManyRelationship, out XElement mmEntitySchema);
            string   mmEntity            = mmEntitySchema.Attribute(SchemaVocab.Name).Value;
            XElement mmConcurrencySchema = GetConcurrencySchema(mmEntitySchema);

            //
            bool mmDeleteTransSetNull = IsDeleteTransSetNull(manyToManyRelationship);

            Dictionary <string, object>      mmUpdatePropertyValues = null;
            IEnumerable <DirectRelationship> mmRelationships        = null;

            if (mmDeleteTransSetNull)
            {
                mmUpdatePropertyValues = new Dictionary <string, object>();
                DirectRelationship oneToManyRelationship = manyToManyRelationship.DirectRelationships[0];
                for (int i = 0; i < oneToManyRelationship.RelatedProperties.Length; i++)
                {
                    string relatedPropertyName = oneToManyRelationship.RelatedProperties[i];
                    mmUpdatePropertyValues.Add(relatedPropertyName, null);
                }
            }
            else
            {
                mmRelationships = GetDirectRelationships(mmEntity);
            }

            int index = 0;

            foreach (T child in children)
            {
                Dictionary <string, object> childPropertyValues = GetPropertyValues(child, childEntitySchema);
                Dictionary <string, object> mmPropertyValues    = TransPropertyValues(manyToManyRelationship, parentPropertyValues, childPropertyValues);

                ExecuteCommand <T> mmExecuteCommand;
                if (mmDeleteTransSetNull)
                {
                    UpdateCommand <T> mmUpdateCommand = CreateUpdateCommand(child, childEntity);
                    mmUpdateCommand.FixedUpdatePropertyValues = mmUpdatePropertyValues;
                    mmUpdateCommand.ConcurrencySchema         = mmConcurrencySchema;

                    mmExecuteCommand = mmUpdateCommand;
                }
                else
                {
                    DeleteCommand <T> mmDeleteCommand = CreateDeleteCommand(child, childEntity);
                    mmDeleteCommand.ConcurrencySchema  = mmConcurrencySchema;
                    mmDeleteCommand.ChildRelationships = mmRelationships;

                    mmExecuteCommand = mmDeleteCommand;
                }

                mmExecuteCommand.EntitySchema         = mmEntitySchema;
                mmExecuteCommand.UniqueKeySchema      = mmKeySchema;
                mmExecuteCommand.PropertyValues       = mmPropertyValues;
                mmExecuteCommand.ParentPropertyValues = parentPropertyValues;
                mmExecuteCommand.ParentRelationship   = manyToManyRelationship.DirectRelationships[0];
                mmExecuteCommand.Path = string.Format("{0}[{1}]", childrenPath, index);

                Commands.Add(mmExecuteCommand);

                index++;
            }
        }