public async Task TestReducePageSizeScenario()
        {
            int partitionKey = 0;
            // Create some docs to make sure that one separate response is returned for 1st execute of query before retries.
            // These are to make sure continuation token is passed along during retries.
            string sprocId   = "createTwoDocs";
            string sprocBody = @"function(startIndex) { for (var i = 0; i < 2; ++i) __.createDocument(
                            __.getSelfLink(),
                            { id: 'doc' + (i + startIndex).toString(), value: 'y'.repeat(1500000), pk:0 },
                            err => { if (err) throw err;}
                        );}";

            Scripts scripts = this.Container.Scripts;

            StoredProcedureResponse storedProcedureResponse =
                await scripts.CreateStoredProcedureAsync(new StoredProcedureProperties(sprocId, sprocBody));

            ManualResetEvent allDocsProcessed = new ManualResetEvent(false);

            int    processedDocCount      = 0;
            string accumulator            = string.Empty;
            ChangeFeedProcessor processor = this.Container
                                            .GetChangeFeedProcessorBuilder("test", (IReadOnlyCollection <dynamic> docs, CancellationToken token) =>
            {
                processedDocCount += docs.Count();
                foreach (var doc in docs)
                {
                    accumulator += doc.id.ToString() + ".";
                }
                if (processedDocCount == 5)
                {
                    allDocsProcessed.Set();
                }

                return(Task.CompletedTask);
            })
                                            .WithStartFromBeginning()
                                            .WithInstanceName("random")
                                            .WithMaxItems(6)
                                            .WithLeaseContainer(this.LeaseContainer).Build();

            // Generate the payload
            await scripts.ExecuteStoredProcedureAsync <int, object>(sprocId, 0, new PartitionKey(partitionKey));

            // Create 3 docs each 1.5MB. All 3 do not fit into MAX_RESPONSE_SIZE (4 MB). 2nd and 3rd are in same transaction.
            var content = string.Format("{{\"id\": \"doc2\", \"value\": \"{0}\", \"pk\": 0}}", new string('x', 1500000));

            await this.Container.CreateItemAsync(JsonConvert.DeserializeObject <dynamic>(content), new PartitionKey(partitionKey));

            await scripts.ExecuteStoredProcedureAsync <int, object>(sprocId, 3, new PartitionKey(partitionKey));

            await processor.StartAsync();

            // Letting processor initialize and pickup changes
            var isStartOk = allDocsProcessed.WaitOne(10 * BaseChangeFeedClientHelper.ChangeFeedSetupTime);
            await processor.StopAsync();

            Assert.IsTrue(isStartOk, "Timed out waiting for docs to process");
            Assert.AreEqual("doc0.doc1.doc2.doc3.doc4.", accumulator);
        }
        public async Task<HttpStatusCode> BulkUpdateAsync<T>(IEnumerable<T> entities, string storedProcedureName) where T : IIdentifiable
        {
            Guard.ArgumentNotNull(entities, nameof(entities));

            string documentType = GetDocumentType<T>();

            IList<DocumentEntity<T>> documents = new List<DocumentEntity<T>>();

            foreach (T entity in entities)
            {
                DocumentEntity<T> doc = new DocumentEntity<T>(entity);
                if (doc.DocumentType != null && doc.DocumentType != documentType)
                {
                    throw new ArgumentException($"Cannot change {entity.Id} from {doc.DocumentType} to {typeof(T).Name}");
                }

                doc.DocumentType = documentType;
                doc.UpdatedAt = DateTimeOffset.Now;
                documents.Add(doc);
            }

            string documentsAsJson = JsonConvert.SerializeObject(documents);

            dynamic[] args = new dynamic[] { JsonConvert.DeserializeObject<dynamic>(documentsAsJson) };

            Scripts cosmosScripts = RepositoryContainer.Scripts;

            StoredProcedureExecuteResponse<string> response = await cosmosScripts.ExecuteStoredProcedureAsync<string>(
                storedProcedureId: storedProcedureName,
                partitionKey: PartitionKey.Null,
                requestOptions: null,
                parameters: args);

            return response.StatusCode;
        }
Example #3
0
        // </RunBulkImport>

        /// <summary>
        /// Get documents ordered by some doc property. This is done using OrderBy stored procedure.
        /// </summary>
        // <RunOrderBy>
        private static async Task RunOrderBy(Container container)
        {
            // 1. Create or get the stored procedure.
            string body     = File.ReadAllText(@"js\OrderBy.js");
            string scriptId = "OrderBy";

            await TryDeleteStoredProcedure(container, scriptId);

            Scripts cosmosScripts         = container.Scripts;
            StoredProcedureResponse sproc = await cosmosScripts.CreateStoredProcedureAsync(new StoredProcedureProperties(scriptId, body));

            // 2. Prepare to run stored procedure.
            string orderByFieldName = "FamilyId";
            string filterQuery      = string.Format(CultureInfo.InvariantCulture, "SELECT r.FamilyId FROM root r WHERE r.{0} > 10", orderByFieldName);
            // Note: in order to do a range query (> 10) on this field, the collection must have a range index set for this path (see ReadOrCreateCollection).

            int?continuationToken = null;
            int batchCount        = 0;

            do
            {
                // 3. Run the stored procedure.
                StoredProcedureExecuteResponse <OrderByResult> response = await cosmosScripts.ExecuteStoredProcedureAsync <OrderByResult>(
                    scriptId,
                    new PartitionKey("Andersen"),
                    new dynamic[] { filterQuery, orderByFieldName, continuationToken });

                // 4. Process stored procedure response.
                continuationToken = response.Resource.Continuation;

                Console.WriteLine($"Printing documents filtered/ordered by '{filterQuery}' and ordered by '{orderByFieldName}', batch #{batchCount++}, count #{response.Resource.Result.Length}");
            } while (continuationToken != null);
            // 5. To take care of big response, loop until Response.continuation token is null (see OrderBy.js for details).
        }
Example #4
0
        public async Task ExecuteSPGreeting(string name)
        {
            string message = "Execute SPGreeting";

            Printer.PrintLine(message: message);
            Scripts scripts = _container.Scripts;
            StoredProcedureExecuteResponse <string> sprocResponse = await scripts.ExecuteStoredProcedureAsync <string>("Greetings", new PartitionKey("/pizzaType"), new dynamic[] { name });

            WriteLine($"SP Greeting Result: {sprocResponse.Resource}");
            Printer.PrintLine(noOfTimes: (101 + message.Length));
        }
Example #5
0
        public async Task ExecuteSPDeletePizza(string pizzaType, string pizzaId)
        {
            string message = "Execute SPDeletePizza";

            Printer.PrintLine(message: message);
            Scripts scripts = _container.Scripts;
            StoredProcedureExecuteResponse <string> sprocResponse = await scripts.ExecuteStoredProcedureAsync <string>("DeletePizza", new PartitionKey(pizzaType), new dynamic[] { pizzaId });

            WriteLine($"SP DeletePizza Result: \n{JsonConvert.DeserializeObject(sprocResponse.Resource)}");
            Printer.PrintLine(noOfTimes: (101 + message.Length));
        }
Example #6
0
        public async Task ExecuteGetPizzaCount(string partitionKey)
        {
            string message = "Execute GetPizzaCount";

            Printer.PrintLine(message: message);
            Scripts scripts = _container.Scripts;
            StoredProcedureExecuteResponse <string> sprocResponse = await scripts.ExecuteStoredProcedureAsync <string>("GetPizzaCount", new PartitionKey($"{partitionKey}"), new dynamic[] { });

            WriteLine($"SP GetPizzaCount Result: {JsonConvert.DeserializeObject(sprocResponse.Resource)}");
            Printer.PrintLine(noOfTimes: (101 + message.Length));
        }
        public async Task ExecuteNonePkTest()
        {
            // Create a container in v2 without a partition key
            string            containerId     = "SprocPkNone" + Guid.NewGuid().ToString();
            ContainerInternal containerNonePk = await NonPartitionedContainerHelper.CreateNonPartitionedContainer(this.database, containerId);

            Scripts scriptsNonePk = containerNonePk.Scripts;

            string sprocId   = Guid.NewGuid().ToString();
            string sprocBody = @"function() {
                var context = getContext();
                var response = context.getResponse();
                var collection = context.getCollection();
                var collectionLink = collection.getSelfLink();

                var filterQuery = 'SELECT * FROM c';

                collection.queryDocuments(collectionLink, filterQuery, { },
                    function(err, documents) {
                        response.setBody(documents);
                    }
                );
            }";

            StoredProcedureResponse storedProcedureResponse =
                await scriptsNonePk.CreateStoredProcedureAsync(new StoredProcedureProperties(sprocId, sprocBody));

            Assert.AreEqual(HttpStatusCode.Created, storedProcedureResponse.StatusCode);
            StoredProcedureTests.ValidateStoredProcedureSettings(sprocId, sprocBody, storedProcedureResponse);

            // Insert document and then query
            string testPartitionId = Guid.NewGuid().ToString();
            var    payload         = new { id = testPartitionId, user = testPartitionId };
            ItemResponse <dynamic> createItemResponse = await containerNonePk.CreateItemAsync <dynamic>(payload);

            Assert.AreEqual(HttpStatusCode.Created, createItemResponse.StatusCode);

            StoredProcedureProperties storedProcedure             = storedProcedureResponse;
            StoredProcedureExecuteResponse <JArray> sprocResponse = await scriptsNonePk.ExecuteStoredProcedureAsync <JArray>(
                sprocId,
                Cosmos.PartitionKey.None,
                parameters : null);

            Assert.AreEqual(HttpStatusCode.OK, sprocResponse.StatusCode);

            JArray jArray = sprocResponse;

            Assert.AreEqual(1, jArray.Count);
            Assert.AreEqual(testPartitionId, jArray[0]["id"]);

            StoredProcedureResponse deleteResponse = await scriptsNonePk.DeleteStoredProcedureAsync(sprocId);

            Assert.AreEqual(HttpStatusCode.NoContent, deleteResponse.StatusCode);
        }
Example #8
0
        public async Task ExecuteSPCreateNewPizza(string pizzaType, string pizzaFileName)
        {
            string newPizza = File.ReadAllText($"Models/PizzaData/{pizzaFileName}.json");
            string message  = "Execute SPCreateNewPizza";

            Printer.PrintLine(message: message);
            Scripts scripts = _container.Scripts;
            StoredProcedureExecuteResponse <string> sprocResponse = await scripts.ExecuteStoredProcedureAsync <string>("CreateNewPizza", new PartitionKey(pizzaType), new dynamic[] { newPizza });

            WriteLine($"SP Create New Pizza Result: \n{JsonConvert.DeserializeObject(sprocResponse.Resource)}");
            Printer.PrintLine(noOfTimes: (100 + message.Length));
        }
Example #9
0
        public async Task ExecuteSPBulkPizzaCreate(string pizzaFile, string partitionKey)
        {
            var    jsonArray = JArray.Parse(File.ReadAllText($@"Models/PizzaData/PizzaCollection/{pizzaFile}PizzaCollection.json"));
            string message   = "Execute SPBulkPizzaCreate";

            Printer.PrintLine(message: message);
            Scripts scripts = _container.Scripts;
            StoredProcedureExecuteResponse <string> sprocResponse = await scripts.ExecuteStoredProcedureAsync <string>("BulkPizzaCreate", new PartitionKey($"{partitionKey}"), new dynamic[] { jsonArray });

            WriteLine($"SP Bulk Pizza Create Result: \n{JsonConvert.DeserializeObject(sprocResponse.Resource)}");
            Printer.PrintLine(noOfTimes: (100 + message.Length));
        }
        private static async Task Execute_spHelloWorld()
        {
            Console.WriteLine("\nExecute spHelloWorld stored procedure");

            Scripts      scripts      = Shared.Client.GetContainer("mydb", "mystore").Scripts;
            PartitionKey partitionKey = new PartitionKey(string.Empty);
            StoredProcedureExecuteResponse <string> result = await scripts.ExecuteStoredProcedureAsync <string>("spHelloWorld", partitionKey, null);

            string message = result.Resource;

            Console.WriteLine($"Result: {message}");
        }
        protected async Task <StoredProcedureExecuteResponse <T> > ExecuteStoredProc <T>(Scripts client, string partitionId, CancellationToken cancellationToken, params object[] parameters)
        {
            EnsureArg.IsNotNull(client, nameof(client));
            EnsureArg.IsNotNull(partitionId, nameof(partitionId));

            StoredProcedureExecuteResponse <T> results = await client.ExecuteStoredProcedureAsync <T>(
                FullName,
                new PartitionKey(partitionId),
                parameters,
                cancellationToken : cancellationToken);

            return(results);
        }
Example #12
0
        public async Task ExecuteSPGetPizzas(string pizzaType = "Veg", decimal price = 300)
        {
            string message = "Execute SPGetPizzas";

            Printer.PrintLine(message: message);
            Scripts scripts = _container.Scripts;
            StoredProcedureExecuteResponse <string> sprocResponse = await scripts.ExecuteStoredProcedureAsync <string>("GetPizzas", new PartitionKey(pizzaType), new dynamic[] { pizzaType, price });

            // StoredProcedureExecuteResponse<string> sprocResponse = await scripts.ExecuteStoredProcedureAsync<string>("GetPizzas", new PartitionKey(pizzaType), new dynamic[] { pizzaType });
            // StoredProcedureExecuteResponse<string> sprocResponse = await scripts.ExecuteStoredProcedureAsync<string>("GetPizzas", new PartitionKey(pizzaType), new dynamic[] { });

            WriteLine($"SP Get VegPizza Result: \n{JsonConvert.DeserializeObject(sprocResponse.Resource)}");
            Printer.PrintLine(noOfTimes: (101 + message.Length));
        }
Example #13
0
        public async Task GetRequestChargeFromResource()
        {
            // <GetRequestCharge>
            Container container         = this.cosmosClient.GetContainer("database", "container");
            string    itemId            = "myItem";
            string    partitionKey      = "partitionKey";
            string    storedProcedureId = "storedProcedureId";
            string    queryText         = "SELECT * FROM c";

            ItemResponse <dynamic> itemResponse = await container.CreateItemAsync <dynamic>(
                item : new { id = itemId, pk = partitionKey },
                partitionKey : new PartitionKey(partitionKey));

            double requestCharge = itemResponse.RequestCharge;

            Scripts scripts = container.Scripts;
            StoredProcedureExecuteResponse <object> sprocResponse = await scripts.ExecuteStoredProcedureAsync <object>(
                storedProcedureId : storedProcedureId,
                partitionKey : new PartitionKey(partitionKey),
                parameters : new dynamic[] { new object() });

            requestCharge = sprocResponse.RequestCharge;

            FeedIterator <dynamic> feedIterator = container.GetItemQueryIterator <dynamic>(
                queryText: queryText,
                requestOptions: new QueryRequestOptions()
            {
                PartitionKey = new PartitionKey(partitionKey)
            });

            while (feedIterator.HasMoreResults)
            {
                FeedResponse <dynamic> feedResponse = await feedIterator.ReadNextAsync();

                requestCharge = feedResponse.RequestCharge;
            }
            // </GetRequestCharge>
        }
Example #14
0
        // </RunSimpleScript>

        /// <summary>
        /// Import many documents using stored procedure.
        /// </summary>
        // <RunBulkImport>
        private static async Task RunBulkImport(Container container)
        {
            string inputDirectory = @".\Data\";
            string inputFileMask  = "*.json";
            int    maxFiles       = 2000;
            int    maxScriptSize  = 50000;

            // 1. Get the files.
            string[]      fileNames = Directory.GetFiles(inputDirectory, inputFileMask);
            DirectoryInfo di        = new DirectoryInfo(inputDirectory);

            FileInfo[] fileInfos = di.GetFiles(inputFileMask);

            // 2. Prepare for import.
            int currentCount = 0;
            int fileCount    = maxFiles != 0 ? Math.Min(maxFiles, fileNames.Length) : fileNames.Length;

            // 3. Create stored procedure for this script.
            string scriptId = "BulkImport";
            string body     = File.ReadAllText(@".\JS\BulkImport.js");

            await TryDeleteStoredProcedure(container, scriptId);

            Scripts cosmosScripts         = container.Scripts;
            StoredProcedureResponse sproc = await cosmosScripts.CreateStoredProcedureAsync(new StoredProcedureProperties(scriptId, body));

            // 4. Create a batch of docs (MAX is limited by request size (2M) and to script for execution.
            // We send batches of documents to create to script.
            // Each batch size is determined by MaxScriptSize.
            // MaxScriptSize should be so that:
            // -- it fits into one request (MAX request size is 16Kb).
            // -- it doesn't cause the script to time out.
            // -- it is possible to experiment with MaxScriptSize to get best performance given number of throttles, etc.
            while (currentCount < fileCount)
            {
                // 5. Create args for current batch.
                //    Note that we could send a string with serialized JSON and JSON.parse it on the script side,
                //    but that would cause script to run longer. Since script has timeout, unload the script as much
                //    as we can and do the parsing by client and framework. The script will get JavaScript objects.
                string    argsJson = CreateBulkInsertScriptArguments(fileNames, currentCount, fileCount, maxScriptSize);
                dynamic[] args     = new dynamic[] { JsonConvert.DeserializeObject <dynamic>(argsJson) };

                // 6. execute the batch.
                StoredProcedureExecuteResponse <int> scriptResult = await cosmosScripts.ExecuteStoredProcedureAsync <int>(
                    scriptId,
                    new PartitionKey("Andersen"),
                    args);

                // 7. Prepare for next batch.
                int currentlyInserted = scriptResult.Resource;
                currentCount += currentlyInserted;
            }

            // 8. Validate
            int numDocs = 0;

            using (FeedIterator <dynamic> setIterator = container.GetItemQueryIterator <dynamic>())
            {
                while (setIterator.HasMoreResults)
                {
                    FeedResponse <dynamic> response = await setIterator.ReadNextAsync();

                    numDocs += response.Count();
                }
            }

            Console.WriteLine("Found {0} documents in the collection. There were originally {1} files in the Data directory\r\n", numDocs, fileCount);
        }