/// <summary>
        /// Appends the current parameter name and value, e.g. <c>@P0</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Par(this IProjectionAttribute attribute)
        {
            if (!attribute.Context.Domain.Dialect.Support.HasFlag(DialectSupport.InputParameters))
            {
                throw ProjectionException.FromProjection(attribute, $"Dialect '{attribute.Context.Domain.Dialect.GetType().Name}' does not support input parameters.");
            }

            IField value = attribute.Field?.Invoke();

            if (value != null)
            {
                string paramName   = attribute.Context.Lookup.Parameter(attribute.Identity, value);
                string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

                Parameter param = new Parameter(paramName, value);

                IProjectionAttribute result = attribute.Append(dialectName).Append(param);

                if (attribute.Metadata.HasFlag(ProjectionMetadataFlags.Output) && attribute.Context.Domain.Dialect.Support.HasFlag(DialectSupport.OutputParameters))
                {
                    ParameterBinding binding = new ParameterBinding(param);

                    result = result.Append(binding);
                }

                return(result);
            }
            else
            {
                string paramName   = attribute.Context.Lookup.Parameter(attribute.Identity, attribute.Metadata.Identity);
                string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

                return(attribute.Append(dialectName));
            }
        }
        /// <summary>
        /// Appends the current property name, e.g. <c>"Item.MyValue"</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute</param>
        /// <param name="tblAlias">An alias to qualify the property name with.</param>
        /// <param name="propName">A name to suffix the property name with.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Prop(this IProjectionAttribute attribute, string tblAlias = null, string propName = null)
        {
            if ((propName == null || attribute.Field != null) && attribute.Metadata.HasFlag(RelationMetadataFlags.Model))
            {
                throw ProjectionException.FromProjection(attribute, "Cannot reference model directly.");
            }

            if (attribute.Field != null)
            {
                IField field = attribute.Field();

                ColumnBinding binding = new ColumnBinding(field.Identity.Name, field);

                propName = attribute.Context.Domain.Dialect.Identifier(binding.ColumnName);

                return(attribute.Append(propName).Append(binding));
            }
            else
            {
                string fullName = attribute.Metadata.Identity.Name;

                if (propName != null)
                {
                    fullName = attribute.Identity.Schema.Notation.Combine(fullName, propName);
                }

                if (tblAlias != null)
                {
                    attribute = attribute.Append(attribute.Context.Domain.Dialect.Identifier(tblAlias));
                    attribute = attribute.Append(attribute.Context.Domain.Dialect.Qualifier);
                }

                return(attribute.Append(attribute.Context.Domain.Dialect.Identifier(fullName)));
            }
        }
        /// <summary>
        /// Appends the current parameter name and value, e.g. <c>@P0</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Par(this IProjectionAttribute attribute)
        {
            IField value = attribute.Field?.Invoke();

            if (value != null)
            {
                string paramName   = attribute.Context.Lookup.Parameter(attribute.Identity, value);
                string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

                Parameter param = new Parameter(paramName, value);

                IProjectionAttribute result = attribute.Append(dialectName).Append(param);

                if (attribute.Metadata.HasFlag(ProjectionMetadataFlags.Output))
                {
                    ParameterBinding binding = new ParameterBinding(param.Name, value);

                    result = result.Append(binding);
                }

                return(result);
            }
            else
            {
                string paramName   = attribute.Context.Lookup.Parameter(attribute.Identity, attribute.Metadata.Identity);
                string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

                return(attribute.Append(dialectName));
            }
        }
        /// <summary>
        /// Appends the current property name, e.g. <c>"Item.MyValue"</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute</param>
        /// <param name="tblAlias">An alias to qualify the property name with.</param>
        /// <param name="propName">A name to suffix the property name with.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Prop(this IProjectionAttribute attribute, string tblAlias = null, string propName = null)
        {
            if (attribute.Metadata.HasFlag(RelationMetadataFlags.Model) && (propName == null || attribute.Data != null))
            {
                throw ProjectionException.PropertyNotFound(attribute.Metadata);
            }

            if (attribute.Data != null)
            {
                ColumnBinding binding = new ColumnBinding(attribute.Data.Output);

                propName = attribute.Context.Domain.Dialect.Identifier(binding.ColumnName);

                return(attribute.Append(propName).Append(binding));
            }
            else
            {
                string fullName = attribute.Metadata.Identity.Name;

                if (propName != null)
                {
                    fullName = attribute.Identity.Schema.Notation.Combine(fullName, propName);
                }

                if (tblAlias != null)
                {
                    attribute = attribute.Append(attribute.Context.Domain.Dialect.Identifier(tblAlias));
                    attribute = attribute.Append(attribute.Context.Domain.Dialect.Qualifier);
                }

                return(attribute.Append(attribute.Context.Domain.Dialect.Identifier(fullName)));
            }
        }
Example #5
0
        /// <summary>
        /// Appends the current column name in unqualified form, e.g. <c>"MyColumn"</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute ColName(this IProjectionAttribute attribute)
        {
            ITableMetadata column = ProjectionHelper.GetPreferredColumnMetadata(attribute);

            string identifier = attribute.Context.Domain.Dialect.Identifier(column.ColumnName);

            return(attribute.Append(identifier));
        }
Example #6
0
        /// <summary>
        /// Appends the current table alias, e.g. <c>T0</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Ali(this IProjectionAttribute attribute)
        {
            ITableMetadata table = ProjectionHelper.GetTableMetadata(attribute);

            string alias = attribute.Context.Lookup.Table(attribute.Identity, table.Identity);

            return(attribute.Append(alias));
        }
Example #7
0
        /// <summary>
        /// Appends the current JSON path literal, e.g. <c>'$.my.value'</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute JsonPath(this IProjectionAttribute attribute)
        {
            IJsonMetadata metadata = ProjectionHelper.GetJsonMetadata(attribute.Metadata);

            string literal = attribute.Context.Domain.Dialect.String(metadata.Path);

            return(attribute.Append(literal));
        }
Example #8
0
        public static IProjectionAttribute Refcursor(this IProjectionAttribute attribute)
        {
            string paramName   = attribute.Context.Lookup.Custom("R", attribute.Identity, attribute.Metadata.Identity, attribute.Field?.Invoke());
            string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

            Parameter param = new Parameter(paramName, contract: new RefcursorContract());

            return(attribute.Append(dialectName).Append(param));
        }
Example #9
0
        public static IField GetFieldValue(IProjectionAttribute attribute)
        {
            if (attribute.Field == null)
            {
                throw ProjectionException.ValueNotFound(attribute);
            }

            return(attribute.Field());
        }
Example #10
0
        /// <summary>
        /// Appends the current variable name, e.g. <c>@V0</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Var(this IProjectionAttribute attribute)
        {
            IField field = ProjectionHelper.GetFieldValue(attribute);

            string variableName = attribute.Context.Lookup.Variable(attribute.Identity, field);
            string dialectName  = attribute.Context.Domain.Dialect.Variable(variableName);

            return(attribute.Append(dialectName));
        }
Example #11
0
        /// <summary>
        /// Appends the current table name, e.g. <c>"MyTable"</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute TblName(this IProjectionAttribute attribute)
        {
            ITableMetadata table = ProjectionHelper.GetTableMetadata(attribute);

            string qualifier = attribute.Context.Domain.Dialect.Qualifier;
            string tableName = string.Join(qualifier, table.TableName.Select(attribute.Context.Domain.Dialect.Identifier));

            return(attribute.Append(tableName));
        }
Example #12
0
        public static IProjectionAttribute Refcursor(this IProjectionAttribute attribute)
        {
            string paramName   = attribute.Context.Lookup.Custom("R");
            string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

            Refcursor param = new Refcursor(paramName);

            return(attribute.Append(dialectName).Append(param));
        }
Example #13
0
        /// <summary>
        /// Appends the current variable name, e.g. <c>@V0</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Var(this IProjectionAttribute attribute)
        {
            if (attribute.Data == null)
            {
                throw ProjectionException.ValueNotFound(attribute.Metadata);
            }

            string variableName = attribute.Context.Lookup.Variable(attribute.Identity, attribute.Data.Input);
            string dialectName  = attribute.Context.Domain.Dialect.Variable(variableName);

            return(attribute.Append(dialectName));
        }
        protected ProjectionAttribute(IProjectionAttribute attribute, IProjectionMetadata metadata, IProjectionData data, ISqlContent content)
        {
            if (attribute == null)
            {
                throw ProjectionException.ArgumentNull(nameof(attribute), metadata);
            }

            this.Context  = attribute.Context;
            this.Identity = attribute.Identity;
            this.Metadata = metadata ?? throw ProjectionException.ArgumentNull(nameof(metadata), metadata);
            this.Data     = data;
            this.Content  = content ?? throw ProjectionException.ArgumentNull(nameof(content), metadata);
        }
        /// <summary>
        /// Appends the current value in safe literal form, e.g. <c>1</c>, to the attribute buffer. Parameters are used for unsafe literals.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Lit(this IProjectionAttribute attribute)
        {
            string literal = attribute.Context.Domain.Dialect.Literal(attribute.Data?.Source.Snapshot);

            if (literal == null)
            {
                return(attribute.Par());
            }
            else
            {
                return(attribute.Append(literal));
            }
        }
Example #16
0
        public static ITableMetadata GetPreferredColumnMetadata(IProjectionAttribute attribute)
        {
            if (attribute.Metadata.HasFlag(TableMetadataFlags.Column))
            {
                return(attribute.Metadata.Table);
            }
            else if (attribute.Metadata.Item != null && attribute.Metadata.Item.HasFlag(TableMetadataFlags.Column))
            {
                return(attribute.Metadata.Item.Table);
            }

            throw ProjectionException.FromProjection(attribute, "No column information found.");
        }
Example #17
0
        /// <summary>
        /// Appends the current JSON path literal, e.g. <c>'$.my.value'</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute JsonPath(this IProjectionAttribute attribute)
        {
            IJsonMetadata metadata = attribute.Metadata.Identity.GetMetadata <IJsonMetadata>();

            if (metadata == null)
            {
                throw ProjectionException.FromProjection(attribute, "JSON metadata not found.");
            }

            string literal = attribute.Context.Domain.Dialect.String(metadata.Path);

            return(attribute.Append(literal));
        }
Example #18
0
        /// <summary>
        /// Appends the current correlated table name, e.g. <c>"MyTable" T0</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <param name="tblAlias">An alternative alias to use for the current table.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Tbl(this IProjectionAttribute attribute, string tblAlias = null)
        {
            attribute = attribute.TblName().Append(" ");

            if (tblAlias != null)
            {
                return(attribute.Append(attribute.Context.Domain.Dialect.Identifier(tblAlias)));
            }
            else
            {
                return(attribute.Ali());
            }
        }
Example #19
0
        protected ProjectionAttribute(IProjectionAttribute attribute, IProjectionMetadata metadata, ISqlContent content, Func <IField> field)
        {
            if (attribute == null)
            {
                throw ProjectionException.ArgumentNull(nameof(attribute), this);
            }

            this.Context  = attribute.Context;
            this.Identity = attribute.Identity;
            this.Metadata = metadata ?? throw ProjectionException.ArgumentNull(nameof(attribute), this);
            this.Content  = content ?? throw ProjectionException.ArgumentNull(nameof(content), this);
            this.Field    = field;
        }
Example #20
0
        /// <summary>
        /// Appends the current column name in qualified form, e.g. <c>T0."MyColumn"</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <param name="tblAlias">The table alias to qualify the column name with.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Col(this IProjectionAttribute attribute, string tblAlias = null)
        {
            if (tblAlias != null)
            {
                attribute = attribute.Append(attribute.Context.Domain.Dialect.Identifier(tblAlias));
            }
            else
            {
                attribute = attribute.Ali();
            }

            return(attribute.Append(attribute.Context.Domain.Dialect.Qualifier).ColName());
        }
Example #21
0
        /// <summary>
        /// Appends a call to <c>JSON_EXTRACT</c> from the current column and JSON path, e.g. <c>JSON_EXTRACT(T0."MyJson", '$.my.value')</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Json(this IProjectionAttribute attribute)
        {
            IJsonMetadata json = attribute.Metadata.Identity.Require <IJsonMetadata>();

            IProjectionMetadata valueMetadata = attribute.Metadata;
            IProjectionMetadata rootMetadata  = json.MemberOf.Identity.Lookup <IProjectionMetadata>();

            attribute = attribute.Append("JSON_EXTRACT(");
            attribute = attribute.With(metadata: rootMetadata).Col();
            attribute = attribute.Append(",");
            attribute = attribute.With(metadata: valueMetadata).JsonPath();
            attribute = attribute.Append(")");

            return(attribute);
        }
Example #22
0
        /// <summary>
        /// Appends the current value in safe literal form, e.g. <c>1</c>, to the attribute buffer. Parameters are used for unsafe literals.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Lit(this IProjectionAttribute attribute)
        {
            IField field = ProjectionHelper.GetFieldValue(attribute);

            string literal = attribute.Context.Domain.Dialect.Literal(field?.Value);

            if (literal == null)
            {
                return(attribute.Par());
            }
            else
            {
                return(attribute.Append(literal));
            }
        }
        public static IProjection IsEq(this IProjection projection, IProjection other)
        {
            List <IProjectionAttribute> newAttrs = new List <IProjectionAttribute>();

            foreach (var(l, r) in projection.Attrs().Zip(other.Attrs()))
            {
                IProjectionAttribute newAttr = l;

                newAttr = newAttr.Eq();
                newAttr = newAttr.With(metadata: r.Metadata, field: r.Field).Par();
                newAttr = newAttr.With(metadata: l.Metadata, field: l.Field);

                newAttrs.Add(newAttr);
            }

            return(projection.With(attributes: newAttrs));
        }
Example #24
0
        /// <summary>
        /// Appends the current parameter name and value, e.g. <c>@P0</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Par(this IProjectionAttribute attribute)
        {
            if (!attribute.Context.Domain.Dialect.Support.HasFlag(DialectSupport.InputParameters))
            {
                throw ProjectionException.ParametersNotSupported(attribute);
            }

            if (attribute.Data?.Input != null)
            {
                string paramName   = attribute.Context.Lookup.Parameter(attribute.Identity, attribute.Data.Input);
                string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

                Parameter param = new Parameter(paramName, attribute.Data.Input);

                IProjectionAttribute result = attribute.Append(dialectName).Append(param);

                if (attribute.Metadata.HasFlag(ProjectionMetadataFlags.Output))
                {
                    if (attribute.Context.Domain.Dialect.Support.HasFlag(DialectSupport.OutputParameters))
                    {
                        ParameterBinding binding = new ParameterBinding(attribute.Data.Output, param.Name);

                        result = result.Append(binding);
                    }

                    if (attribute.Metadata.HasAnyFlag(ProjectionMetadataFlags.Cascade))
                    {
                        CascadeBinding binding = new CascadeBinding(attribute.Data.Output, attribute.Data.Input);

                        result = result.Append(binding);
                    }
                }

                return(result);
            }
            else
            {
                string paramName   = attribute.Context.Lookup.Parameter(attribute.Identity, attribute.Metadata.Identity);
                string dialectName = attribute.Context.Domain.Dialect.Parameter(paramName);

                return(attribute.Append(dialectName));
            }
        }
Example #25
0
        /// <summary>
        /// Appends a call to <c>JSON_VALUE</c> from the current column and JSON path, e.g. <c>JSON_VALUE(T0."MyJson", '$.my.value')</c>, to the attribute buffer.
        /// </summary>
        /// <param name="attribute">The current attribute.</param>
        /// <returns>A new attribute containing the appended buffer.</returns>
        public static IProjectionAttribute Json(this IProjectionAttribute attribute)
        {
            IJsonMetadata json = ProjectionHelper.GetJsonMetadata(attribute);

            IProjectionMetadata metadata     = attribute.Metadata;
            IProjectionMetadata rootMetadata = json.MemberOf.Identity.GetMetadata <IProjectionMetadata>();

            attribute = attribute.Append("JSON_VALUE(");
            try
            {
                attribute = attribute.With(metadata: rootMetadata).Col();
            }
            catch (ProjectionException ex)
            {
                throw ProjectionException.FromProjection(attribute, "JSON value requires a column to read from.", innerException: ex);
            }
            attribute = attribute.Append(",");
            attribute = attribute.With(metadata: metadata).JsonPath();
            attribute = attribute.Append(")");

            return(attribute);
        }
Example #26
0
        public static IProjection IsEq(this IProjection projection, IProjection other)
        {
            List <IProjectionAttribute> newHeader = new List <IProjectionAttribute>();

            foreach (var(l, r) in projection.Attrs().Zip(other.Attrs()))
            {
                IProjectionAttribute newAttr = l;

                newAttr = newAttr.Eq();
                newAttr = newAttr.With(data: r.Data).Par();
                newAttr = newAttr.With(data: l.Data);

                newHeader.Add(newAttr);
            }

            ProjectionOptions newOptions = new ProjectionOptions(projection.Options)
            {
                Separator = Environment.NewLine + "AND" + Environment.NewLine,
            };

            return(projection.With(header: newHeader, options: newOptions));
        }
        public static IProjection IsEq(this IProjection projection, IProjection other)
        {
            List <IProjectionAttribute> newAttrs = new List <IProjectionAttribute>();

            foreach (var(l, r) in projection.Attrs().Zip(other.Attrs()))
            {
                IProjectionAttribute newAttr = l;

                newAttr = newAttr.Eq();
                newAttr = newAttr.With(metadata: r.Metadata, field: r.Field).Par();
                newAttr = newAttr.With(metadata: l.Metadata, field: l.Field);

                newAttrs.Add(newAttr);
            }

            ProjectionOptions newOptions = new ProjectionOptions(projection.Options)
            {
                Separator = Environment.NewLine + "AND" + Environment.NewLine,
            };

            return(projection.With(attributes: newAttrs, options: newOptions));
        }
Example #28
0
        public static IProjectionAttribute ValList(this IProjection projection, Func <IProjectionAttribute, IProjectionAttribute> itemFactory)
        {
            if (projection.Source == null)
            {
                throw ProjectionException.ValueNotFound(projection);
            }

            IField[]             items     = new Relation(projection.Source, projection.Metadata.Identity.Name).Column().ToArray();
            IProjectionAttribute attribute = projection.Attr();

            if (items.Length == 0)
            {
                return(attribute);
            }

            attribute = itemFactory(attribute.With(metadata: attribute.Metadata, field: () => items[0]));

            foreach (IField item in items.Skip(1))
            {
                attribute = itemFactory(attribute.With(field: () => item).Append(", "));
            }

            return(attribute);
        }
 public static bool HasVal(this IProjectionAttribute attribute) => (attribute.Data.Source.Snapshot != null);
Example #30
0
 public static IJsonMetadata GetJsonMetadata(IProjectionAttribute attribute) => attribute.Metadata.Identity.GetMetadata <IJsonMetadata>() ??
 throw ProjectionException.FromProjection(attribute, "JSON metadata not found.");