Example #1
0
        public DocumentDesign(Configuration configuration, DocumentTable table, Type documentType, string discriminator)
        {
            Root          = this;
            DocumentType  = documentType;
            Table         = table;
            Discriminator = discriminator;

            if (DocumentTable.DiscriminatorColumn.Length > -1 && discriminator.Length > DocumentTable.DiscriminatorColumn.Length)
            {
                throw new InvalidOperationException($"Discriminator '{discriminator}' is too long for column. Maximum length is {DocumentTable.DiscriminatorColumn.Length}.");
            }

            decendentsAndSelf = new Dictionary <string, DocumentDesign> {
                { Discriminator, this }
            };

            GetKey = configuration.DefaultKeyResolver;

            Projections = new Dictionary <string, Projection>
            {
                [DocumentTable.DiscriminatorColumn] = Projection.From <string>(_ => Discriminator),
                [DocumentTable.DocumentColumn]      = Projection.From <byte[]>(document => configuration.Serializer.Serialize(document)),
                [DocumentTable.MetadataColumn]      = Projection.From <byte[]>((document, metadata) =>
                                                                               metadata != null
                        ? configuration.Serializer.Serialize(metadata)
                        : null),
                [DocumentTable.VersionColumn]            = Projection.From <int>(_ => configuration.ConfiguredVersion),
                [DocumentTable.AwaitsReprojectionColumn] = Projection.From <bool>(_ => false)
            };
        }
Example #2
0
        public DocumentDesign(Configuration configuration, DocumentDesign parent, Type documentType, string discriminator)
            : this(configuration, parent.Table, documentType, discriminator)
        {
            Parent      = parent;
            Projections = parent.Projections.ToDictionary();
            Projections[Table.DiscriminatorColumn] = Projection.From <string>(managedEntity => Discriminator);

            Parent.AddChild(this);
        }
Example #3
0
        public DocumentDesigner <TEntity> With <TMember>(string name, Expression <Func <TEntity, TMember> > projector, params Option[] options)
        {
            if (typeof(TMember) == typeof(string))
            {
                options = options.Concat(new MaxLength(1024)).ToArray();
            }

            var column = design.Table[name];

            if (design.Table.IdColumn.Equals(column))
            {
                throw new ArgumentException("You can not make a projection for IdColumn. Use Document.Key() method instead.");
            }

            if (column == null)
            {
                var lengthOption = options
                                   .OfType <MaxLength>()
                                   .FirstOrDefault();

                column = new Column(name, typeof(TMember), lengthOption?.Length);
                design.Table.Register(column);
            }

            Func <object, object> compiledProjector;

            if (!options.OfType <DisableNullCheckInjection>().Any())
            {
                var nullCheckInjector    = new NullCheckInjector();
                var nullCheckedProjector = (Expression <Func <TEntity, object> >)nullCheckInjector.Visit(projector);

                if (!nullCheckInjector.CanBeTrustedToNeverReturnNull && !column.IsPrimaryKey)
                {
                    column.Nullable = true;
                }

                compiledProjector = Compile(name, nullCheckedProjector);
            }
            else
            {
                compiledProjector = Compile(name, projector);
            }

            var newProjection = Projection.From <TMember>(managedEntity => compiledProjector(managedEntity.Entity));

            if (!newProjection.ReturnType.IsCastableTo(column.Type))
            {
                throw new InvalidOperationException(
                          $"Can not override projection for {name} of type {column.Type} " +
                          $"with a projection that returns {newProjection.ReturnType} (on {typeof (TEntity)}).");
            }

            Projection existingProjection;

            if (!design.Projections.TryGetValue(name, out existingProjection))
            {
                if (design.Parent != null && !column.IsPrimaryKey)
                {
                    column.Nullable = true;
                }

                design.Projections.Add(column, newProjection);
            }
            else
            {
                design.Projections[name] = newProjection;
            }

            return(this);
        }