From ba47e733eed355d2961e5f253d08e4ea1721b6d5 Mon Sep 17 00:00:00 2001 From: Sourabh Jain Date: Fri, 13 May 2022 21:49:15 +0530 Subject: [PATCH] Diagnostics : Adds Continuation Token from PkRange cache (#3180) Diagnostics : Adds Continuation Token from PkRange cache. Right now, NoOpTrace has been passed in most of the cases for PartitionKeyRangeCache call. In future PRs, we will be removing NoOpTrace from these calls to get the proper diagnostics. --- .../src/Routing/PartitionKeyRangeCache.cs | 4 ++++ .../src/Tracing/ITraceDatumVisitor.cs | 1 + .../PartitionKeyRangeCacheTraceDatum.cs | 23 +++++++++++++++++++ .../Tracing/TraceWriter.TraceJsonWriter.cs | 14 +++++++++++ .../Tracing/TraceWriter.TraceTextWriter.cs | 9 ++++++++ .../CosmosItemSessionTokenTests.cs | 13 +++++++++++ 6 files changed, 64 insertions(+) create mode 100644 Microsoft.Azure.Cosmos/src/Tracing/TraceData/PartitionKeyRangeCacheTraceDatum.cs diff --git a/Microsoft.Azure.Cosmos/src/Routing/PartitionKeyRangeCache.cs b/Microsoft.Azure.Cosmos/src/Routing/PartitionKeyRangeCache.cs index a7d9b92bcc..6715692218 100644 --- a/Microsoft.Azure.Cosmos/src/Routing/PartitionKeyRangeCache.cs +++ b/Microsoft.Azure.Cosmos/src/Routing/PartitionKeyRangeCache.cs @@ -264,6 +264,10 @@ private async Task GetRoutingMapForCollectionAsync( throw new NotFoundException($"{DateTime.UtcNow.ToString("o", CultureInfo.InvariantCulture)}: GetRoutingMapForCollectionAsync(collectionRid: {collectionRid}), Range information either doesn't exist or is not complete."); } + trace.AddDatum($"PKRangeCache Info({DateTime.UtcNow.ToString("o", CultureInfo.InvariantCulture)})", + new PartitionKeyRangeCacheTraceDatum( + previousContinuationToken: previousRoutingMap?.ChangeFeedNextIfNoneMatch, + continuationToken: routingMap.ChangeFeedNextIfNoneMatch)); return routingMap; } diff --git a/Microsoft.Azure.Cosmos/src/Tracing/ITraceDatumVisitor.cs b/Microsoft.Azure.Cosmos/src/Tracing/ITraceDatumVisitor.cs index 85db42440d..dda5c20673 100644 --- a/Microsoft.Azure.Cosmos/src/Tracing/ITraceDatumVisitor.cs +++ b/Microsoft.Azure.Cosmos/src/Tracing/ITraceDatumVisitor.cs @@ -16,5 +16,6 @@ internal interface ITraceDatumVisitor void Visit(ClientSideRequestStatisticsTraceDatum clientSideRequestStatisticsTraceDatum); void Visit(CpuHistoryTraceDatum cpuHistoryTraceDatum); void Visit(ClientConfigurationTraceDatum clientConfigurationTraceDatum); + void Visit(PartitionKeyRangeCacheTraceDatum partitionKeyRangeCacheTraceDatum); } } diff --git a/Microsoft.Azure.Cosmos/src/Tracing/TraceData/PartitionKeyRangeCacheTraceDatum.cs b/Microsoft.Azure.Cosmos/src/Tracing/TraceData/PartitionKeyRangeCacheTraceDatum.cs new file mode 100644 index 0000000000..5fc9cb87dc --- /dev/null +++ b/Microsoft.Azure.Cosmos/src/Tracing/TraceData/PartitionKeyRangeCacheTraceDatum.cs @@ -0,0 +1,23 @@ +// ------------------------------------------------------------ +// Copyright (c) Microsoft Corporation. All rights reserved. +// ------------------------------------------------------------ + +namespace Microsoft.Azure.Cosmos.Tracing.TraceData +{ + internal class PartitionKeyRangeCacheTraceDatum : TraceDatum + { + public string PreviousContinuationToken { get; } + public string ContinuationToken { get; } + + public PartitionKeyRangeCacheTraceDatum(string previousContinuationToken, string continuationToken) + { + this.PreviousContinuationToken = previousContinuationToken; + this.ContinuationToken = continuationToken; + } + + internal override void Accept(ITraceDatumVisitor traceDatumVisitor) + { + traceDatumVisitor.Visit(this); + } + } +} diff --git a/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceJsonWriter.cs b/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceJsonWriter.cs index 29c5589180..b38c5a948a 100644 --- a/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceJsonWriter.cs +++ b/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceJsonWriter.cs @@ -441,6 +441,19 @@ public void Visit(StoreResult storeResult) this.jsonWriter.WriteObjectEnd(); } + public void Visit(PartitionKeyRangeCacheTraceDatum partitionKeyRangeCacheTraceDatum) + { + this.jsonWriter.WriteObjectStart(); + + this.jsonWriter.WriteFieldName("Previous Continuation Token"); + this.WriteStringValueOrNull(partitionKeyRangeCacheTraceDatum.PreviousContinuationToken); + + this.jsonWriter.WriteFieldName("Continuation Token"); + this.WriteStringValueOrNull(partitionKeyRangeCacheTraceDatum.ContinuationToken); + + this.jsonWriter.WriteObjectEnd(); + } + private void WriteJsonUriArray(string propertyName, IEnumerable uris) { this.jsonWriter.WriteFieldName(propertyName); @@ -560,6 +573,7 @@ private void WriteDateTimeStringValue(DateTime value) this.jsonWriter.WriteStringValue(value.ToString("o", CultureInfo.InvariantCulture)); } } + } } } diff --git a/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceTextWriter.cs b/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceTextWriter.cs index a9b6fe3245..7bc28aec80 100644 --- a/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceTextWriter.cs +++ b/Microsoft.Azure.Cosmos/src/Tracing/TraceWriter.TraceTextWriter.cs @@ -496,6 +496,15 @@ public override string ToString() { return this.toStringValue; } + + public void Visit(PartitionKeyRangeCacheTraceDatum partitionKeyRangeCacheTraceDatum) + { + StringBuilder stringBuilder = new StringBuilder(); + stringBuilder.AppendLine($"Previous Continuation Token: {partitionKeyRangeCacheTraceDatum.PreviousContinuationToken ?? ""}"); + stringBuilder.AppendLine($"Continuation Token: {partitionKeyRangeCacheTraceDatum.ContinuationToken ?? ""}"); + + this.toStringValue = stringBuilder.ToString(); + } } /// diff --git a/Microsoft.Azure.Cosmos/tests/Microsoft.Azure.Cosmos.EmulatorTests/CosmosItemSessionTokenTests.cs b/Microsoft.Azure.Cosmos/tests/Microsoft.Azure.Cosmos.EmulatorTests/CosmosItemSessionTokenTests.cs index 6e31490c45..652cb01441 100644 --- a/Microsoft.Azure.Cosmos/tests/Microsoft.Azure.Cosmos.EmulatorTests/CosmosItemSessionTokenTests.cs +++ b/Microsoft.Azure.Cosmos/tests/Microsoft.Azure.Cosmos.EmulatorTests/CosmosItemSessionTokenTests.cs @@ -16,6 +16,7 @@ namespace Microsoft.Azure.Cosmos.SDK.EmulatorTests using System.Threading; using Microsoft.Azure.Cosmos.Routing; using Newtonsoft.Json.Linq; + using System.Linq; [TestClass] public class CosmosItemSessionTokenTests : BaseCosmosClientHelper @@ -371,6 +372,18 @@ public async Task InvalidSessionTokenAfterContainerRecreationAndCollectionCacheR while (queryIteratorOldContainer.HasMoreResults) { FeedResponse response = await queryIteratorOldContainer.ReadNextAsync(); + if(i == 0) + { + string diagnosticString = response.Diagnostics.ToString(); + Assert.IsTrue(diagnosticString.Contains("PKRangeCache Info(")); + JObject diagnosticJobject = JObject.Parse(diagnosticString); + JToken actualToken = diagnosticJobject.SelectToken("$.children[0].children[?(@.name=='Get Partition Key Ranges')].children[?(@.name=='Try Get Overlapping Ranges')].data"); + JToken actualNode = actualToken.Children().First().First(); + + Assert.IsTrue(actualNode["Previous Continuation Token"].ToString().Length == 0); + Assert.IsTrue(actualNode["Continuation Token"].ToString().Length > 0); + } + itemCountOldContainer += response.Count; }