Exemple #1
0
        public static TableOperation Retrieve <TElement>(string partitionKey, string rowkey)
            where TElement : ITableEntity
        {
            CommonUtility.AssertNotNull("partitionKey", partitionKey);
            CommonUtility.AssertNotNull("rowkey", rowkey);

            // Create and return the table operation.
            return(new TableOperation(null /* entity */, TableOperationType.Retrieve)
            {
                RetrievePartitionKey = partitionKey,
                RetrieveRowKey = rowkey,
                RetrieveResolver =
                    (pk, rk, ts, prop, etag) => EntityUtilities.ResolveEntityByType <TElement>(
                        pk,
                        rk,
                        ts,
                        prop,
                        etag)
            });
        }
        internal ExecutionInfo Bind()
        {
            ExecutionInfo retVal = new ExecutionInfo();

            // IQueryable impl
            if (this.Expression != null)
            {
                Dictionary <Expression, Expression> normalizerRewrites = new Dictionary <Expression, Expression>(ReferenceEqualityComparer <Expression> .Instance);

                // Step 1. Evaluate any local evaluatable expressions ( lambdas etc)
                Expression partialEvaluatedExpression = Evaluator.PartialEval(this.Expression);

                // Step 2. Normalize expression, replace String Comparisons etc.
                Expression normalizedExpression = ExpressionNormalizer.Normalize(partialEvaluatedExpression, normalizerRewrites);

                // Step 3. Bind Expression, Analyze predicates and create query option expressions. End result is a single ResourceSetExpression
                Expression boundExpression = ResourceBinder.Bind(normalizedExpression);

                // Step 4. Parse the Bound expression into sub components, i.e. take count, filter, select columns, request options, opcontext, etc.
                ExpressionParser parser = new ExpressionParser();
                parser.Translate(boundExpression);

                // Step 5. Store query components & params
                this.TakeCount          = parser.TakeCount;
                this.FilterString       = parser.FilterString;
                this.SelectColumns      = parser.SelectColumns;
                retVal.RequestOptions   = parser.RequestOptions;
                retVal.OperationContext = parser.OperationContext;

                // Step 6. If projection & no resolver then generate a resolver to perform the projection
                if (parser.Resolver == null)
                {
                    if (parser.Projection != null && parser.Projection.Selector != ProjectionQueryOptionExpression.DefaultLambda)
                    {
                        Type intermediateType = parser.Projection.Selector.Parameters[0].Type;

                        // Convert Expression to take type object as input to allow for direct invocation.
                        ParameterExpression paramExpr = Expression.Parameter(typeof(object));

                        Func <object, TElement> projectorFunc = Expression.Lambda <Func <object, TElement> >(
                            Expression.Invoke(parser.Projection.Selector, Expression.Convert(paramExpr, intermediateType)), paramExpr).Compile();

                        // Generate a resolver to do the projection.
                        retVal.Resolver = (pk, rk, ts, props, etag) =>
                        {
                            // Parse to intermediate type
                            ITableEntity intermediateObject = (ITableEntity)EntityUtilities.InstantiateEntityFromType(intermediateType);
                            intermediateObject.PartitionKey = pk;
                            intermediateObject.RowKey       = rk;
                            intermediateObject.Timestamp    = ts;
                            intermediateObject.ReadEntity(props, parser.OperationContext);
                            intermediateObject.ETag = etag;

                            // Invoke lambda expression
                            return(projectorFunc(intermediateObject));
                        };
                    }
                    else
                    {
                        // No op - No resolver or projection specified.
                    }
                }
                else
                {
                    retVal.Resolver = (EntityResolver <TElement>)parser.Resolver.Value;
                }
            }

            retVal.RequestOptions   = TableRequestOptions.ApplyDefaults(retVal.RequestOptions, this.queryProvider.Table.ServiceClient);
            retVal.OperationContext = retVal.OperationContext ?? new OperationContext();
            return(retVal);
        }
Exemple #3
0
        /// <summary>
        /// Adds a table operation that retrieves an entity with the specified partition key and row key to the batch operation.  The entity will be deserialized into the specified class type which extends <see cref="ITableEntity"/>.
        /// </summary>
        /// <typeparam name="TElement">The class of type for the entity to retrieve.</typeparam>
        /// <param name="batch">The input <see cref="TableBatchOperation"/>, which acts as the <c>this</c> instance for the extension method.</param>
        /// <param name="partitionKey">A string containing the partition key of the entity to be retrieved.</param>
        /// <param name="rowkey">A string containing the row key of the entity to be retrieved.</param>
        /// <param name="selectedColumns">List of column names for projection.</param>
        public void Retrieve <TElement>(string partitionKey, string rowkey, List <string> selectedColumns = null) where TElement : ITableEntity
        {
            CommonUtility.AssertNotNull("partitionKey", partitionKey);
            CommonUtility.AssertNotNull("rowkey", rowkey);

            // Add the table operation.
            this.Add(new TableOperation(null /* entity */, TableOperationType.Retrieve)
            {
                RetrievePartitionKey = partitionKey, RetrieveRowKey = rowkey, SelectColumns = selectedColumns, RetrieveResolver = (pk, rk, ts, prop, etag) => EntityUtilities.ResolveEntityByType <TElement>(pk, rk, ts, prop, etag)
            });
        }
Exemple #4
0
        /// <summary>
        /// Adds a table operation that retrieves an entity with the specified partition key and row key to the batch operation.  The entity will be de-serialized into the specified class type which extends <see cref="ITableEntity"/>.
        /// </summary>
        /// <typeparam name="TElement">The class of type for the entity to retrieve.</typeparam>
        /// <param name="batch">The input <see cref="TableBatchOperation"/>, which acts as the <c>this</c> instance for the extension method.</param>
        /// <param name="partitionKey">A string containing the partition key of the entity to be retrieved.</param>
        /// <param name="rowkey">A string containing the row key of the entity to be retrieved.</param>
        public static void Retrieve <TElement>(this TableBatchOperation batch, string partitionKey, string rowkey) where TElement : ITableEntity
        {
            CommonUtils.AssertNotNull("partitionKey", partitionKey);
            CommonUtils.AssertNotNull("rowkey", rowkey);

            // Add the table operation.
            batch.Add(new TableOperation(null /* entity */, TableOperationType.Retrieve)
            {
                RetrievePartitionKey = partitionKey, RetrieveRowKey = rowkey, RetrieveResolver = (pk, rk, ts, prop, etag) => EntityUtilities.ResolveEntityByType <TElement>(pk, rk, ts, prop, etag)
            });
        }