private bool ConstraintPredicate(
            IMetadataConstraints otherConstraints,
            RelationConstraint c,
            RelationConstraintType relationConstraintType,
            Func <RelationConstraint, bool> predicate)
        {
            if (c.RelationConstraintType != relationConstraintType)
            {
                return(false);
            }
            if (!FilterSystemFlagUserPredicate(c.Relation))
            {
                return(false);
            }
            if (relationConstraintType != RelationConstraintType.FOREIGN_KEY && !Metadata.MetadataRelations.Relations.ContainsKey(c.RelationName))
            {
                return(false);
            }

            var otherConstraint = otherConstraints.RelationConstraintsByName.Values.FirstOrDefault(x => x == c);

            if (otherConstraint != null)
            {
                return(predicate == null
                           ? otherConstraint != c
                           : otherConstraint != c || predicate(otherConstraint));
            }

            return(true);
        }
Esempio n. 2
0
    protected override IEnumerable <Command> OnCreate(IMetadata sourceMetadata, IMetadata targetMetadata, IComparerContext context)
    {
        var command = new Command();

        command.Append($"ALTER TABLE {RelationName.AsSqlIndentifier()}");
        if (!SqlHelper.IsImplicitIntegrityConstraintName(ConstraintName))
        {
            command.Append($" ADD CONSTRAINT {ConstraintName.AsSqlIndentifier()}");
        }
        else
        {
            command.Append(" ADD");
        }

        switch (RelationConstraintType)
        {
        case RelationConstraintType.Check:
            command.Append($" {Triggers[0].TriggerSource}");
            break;

        case RelationConstraintType.NotNull:
            break;

        case RelationConstraintType.ForeignKey:
        case RelationConstraintType.PrimaryKey:
        case RelationConstraintType.Unique:
        {
            var fields =
                Index
                .Segments
                .OrderBy(s => s.FieldPosition)
                .Select(s => s.FieldName);

            command.Append($" {RelationConstraintType.ToDescription()} ({string.Join(", ", fields)})");

            if (RelationConstraintType == RelationConstraintType.ForeignKey)
            {
                var referenceConstraint         = sourceMetadata.MetadataConstraints.ReferenceConstraintsByName[ConstraintName];
                var referenceRelationConstraint = referenceConstraint.RelationConstraintUq;
                var primaryKeyFields            =
                    referenceRelationConstraint
                    .Index
                    .Segments
                    .OrderBy(s => s.FieldPosition)
                    .Select(s => s.FieldName);

                command
                .AppendLine()
                .Append($"  REFERENCES {referenceRelationConstraint.RelationName} ({string.Join(", ", primaryKeyFields)})");
                if (referenceConstraint.UpdateRule != ConstraintRule.Restrict)
                {
                    command
                    .AppendLine()
                    .Append($"  ON UPDATE {referenceConstraint.UpdateRule.ToDescription()}");
                }
                if (referenceConstraint.DeleteRule != ConstraintRule.Restrict)
                {
                    command
                    .AppendLine()
                    .Append($"  ON DELETE {referenceConstraint.DeleteRule.ToDescription()}");
                }
                if (referenceConstraint.UpdateRule != ConstraintRule.Restrict || referenceConstraint.DeleteRule != ConstraintRule.Restrict)
                {
                    command.AppendLine();
                }
            }

            command.Append(AddConstraintUsingIndex(sourceMetadata, targetMetadata, context));
            break;
        }

        default:
            throw new ArgumentOutOfRangeException($"Unknown relation constraint type: {RelationConstraintType}.");
        }

        yield return(command);
    }