示例#1
0
        public void SampleBasedOnTraceId()
        {
            Sampler defaultProbability = new TraceIdRatioBasedSampler(0.0001);

            // This traceId will not be sampled by the TraceIdRatioBasedSampler because the first 8 bytes as long
            // is not less than probability * Long.MAX_VALUE;
            var notSampledtraceId =
                ActivityTraceId.CreateFromBytes(
                    new byte[]
            {
                0x8F,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
            });

            Assert.Equal(
                SamplingDecision.Drop,
                defaultProbability.ShouldSample(new SamplingParameters(default, notSampledtraceId, ActivityDisplayName, ActivityKindServer, null, null)).Decision);
示例#2
0
        public void ProbabilitySampler_SampleBasedOnTraceId()
        {
            Sampler defaultProbability = new ProbabilitySampler(0.0001);
            // This traceId will not be sampled by the ProbabilitySampler because the first 8 bytes as long
            // is not less than probability * Long.MAX_VALUE;
            var notSampledtraceId =
                ActivityTraceId.CreateFromBytes(
                    new byte[]
            {
                0x8F,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
            });

            Assert.False(
                defaultProbability.ShouldSample(
        public void CheckToOtlpLogRecordSpanIdTraceIdAndFlag()
        {
            var logRecords = new List <LogRecord>();

            using var loggerFactory = LoggerFactory.Create(builder =>
            {
                builder.AddOpenTelemetry(options =>
                {
                    options.AddInMemoryExporter(logRecords);
                });
            });

            var logger = loggerFactory.CreateLogger("OtlpLogExporterTests");

            ActivityTraceId expectedTraceId = default;
            ActivitySpanId  expectedSpanId  = default;

            using (var activity = new Activity(Utils.GetCurrentMethodName()).Start())
            {
                logger.LogInformation("Log within an activity.");

                expectedTraceId = activity.TraceId;
                expectedSpanId  = activity.SpanId;
            }

            var logRecord     = logRecords[0];
            var otlpLogRecord = logRecord.ToOtlpLog();

            Assert.Equal(expectedTraceId.ToString(), ActivityTraceId.CreateFromBytes(otlpLogRecord.TraceId.ToByteArray()).ToString());
            Assert.Equal(expectedSpanId.ToString(), ActivitySpanId.CreateFromBytes(otlpLogRecord.SpanId.ToByteArray()).ToString());
            Assert.Equal((uint)logRecord.TraceFlags, otlpLogRecord.Flags);
        }
示例#4
0
        public void Int128ConversionWorksAsExpected()
        {
            var id     = ActivityTraceId.CreateFromBytes(new byte[] { 0x1a, 0x0f, 0x54, 0x63, 0x25, 0xa8, 0x56, 0x43, 0x1a, 0x4c, 0x24, 0xea, 0xa8, 0x60, 0xb0, 0xe8 });
            var int128 = new Int128(id);

            Assert.Equal <long>(unchecked ((long)0x1a0f546325a85643), int128.High);
            Assert.Equal <long>(unchecked ((long)0x1a4c24eaa860b0e8), int128.Low);
        }
        /// <inheritdoc />
        public SpanContext FromByteArray(byte[] bytes)
        {
            if (bytes == null)
            {
                OpenTelemetryApiEventSource.Log.FailedToExtractSpanContext("null bytes");
                return(SpanContext.BlankRemote);
            }

            if (bytes.Length != 29 || bytes[0] != VersionId)
            {
                OpenTelemetryApiEventSource.Log.FailedToExtractSpanContext("unexpected bytes length or version");
                return(SpanContext.BlankRemote);
            }

            ActivityTraceId traceId      = default;
            ActivitySpanId  spanId       = default;
            var             traceOptions = ActivityTraceFlags.None;

            var traceparentBytes = new ReadOnlySpan <byte>(bytes);
            var pos = 1;

            try
            {
                if (bytes.Length > pos && bytes[pos] == TraceIdFieldId)
                {
                    traceId = ActivityTraceId.CreateFromBytes(traceparentBytes.Slice(pos + IdSize, 16));
                    pos    += IdSize + TraceIdSize;
                }

                if (bytes.Length > pos && bytes[pos] == SpanIdFieldId)
                {
                    spanId = ActivitySpanId.CreateFromBytes(traceparentBytes.Slice(pos + IdSize, 8));
                    pos   += IdSize + SpanIdSize;
                }

                if (bytes.Length > pos && bytes[pos] == TraceOptionsFieldId)
                {
                    traceOptions = (ActivityTraceFlags)traceparentBytes[pos + IdSize];
                }

                return(new SpanContext(traceId, spanId, traceOptions));
            }
            catch (Exception ex)
            {
                OpenTelemetryApiEventSource.Log.SpanContextExtractException(ex);
                return(SpanContext.BlankRemote);
            }
        }
        public void StartRemoteChildSpan_WithProbabilitySamplerDefaultSampler()
        {
            var configMock = Mock.Get <ITraceConfig>(traceConfig);

            configMock.Setup((c) => c.ActiveTraceParams).Returns(TraceParams.Default);
            // This traceId will not be sampled by the ProbabilitySampler because the first 8 bytes as long
            // is not less than probability * Long.MAX_VALUE;
            var traceId =
                ActivityTraceId.CreateFromBytes(
                    new byte[] { 0x8F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0, 0, 0, 0, 0, 0, 0, 0, });

            // If parent is sampled then the remote child must be sampled.
            var childSpan =
                new SpanBuilder(SpanName, spanBuilderOptions)
                .SetSpanKind(SpanKind.Internal)
                .SetParent(SpanContext.Create(
                               traceId,
                               ActivitySpanId.CreateRandom(),
                               ActivityTraceFlags.Recorded,
                               Tracestate.Empty))
                .StartSpan();

            Assert.True(childSpan.Context.IsValid);
            Assert.Equal(traceId, childSpan.Context.TraceId);
            Assert.True((childSpan.Context.TraceOptions & ActivityTraceFlags.Recorded) != 0);
            childSpan.End();

            Assert.Equal(TraceParams.Default, traceConfig.ActiveTraceParams);

            // If parent is not sampled then the remote child must be not sampled.
            childSpan =
                new SpanBuilder(SpanName, spanBuilderOptions)
                .SetSpanKind(SpanKind.Internal)
                .SetParent(SpanContext.Create(
                               traceId,
                               ActivitySpanId.CreateRandom(),
                               ActivityTraceFlags.None,
                               Tracestate.Empty))
                .StartSpan();

            Assert.True(childSpan.Context.IsValid);
            Assert.Equal(traceId, childSpan.Context.TraceId);
            Assert.True((childSpan.Context.TraceOptions & ActivityTraceFlags.Recorded) == 0);
            childSpan.End();
        }
        public SpanContext FromByteArray(byte[] bytes)
        {
            if (bytes == null)
            {
                throw new ArgumentNullException(nameof(bytes));
            }

            if (bytes.Length == 0 || bytes[0] != VersionId)
            {
                throw new SpanContextParseException("Unsupported version.");
            }

            ActivityTraceId traceId      = default;
            ActivitySpanId  spanId       = default;
            var             traceOptions = ActivityTraceFlags.None;

            var traceparentBytes = new ReadOnlySpan <byte>(bytes);
            var pos = 1;

            try
            {
                if (bytes.Length > pos && bytes[pos] == TraceIdFieldId)
                {
                    traceId = ActivityTraceId.CreateFromBytes(traceparentBytes.Slice(pos + IdSize, 16));
                    pos    += IdSize + TraceIdSize;
                }

                if (bytes.Length > pos && bytes[pos] == SpanIdFieldId)
                {
                    spanId = ActivitySpanId.CreateFromBytes(traceparentBytes.Slice(pos + IdSize, 8));
                    pos   += IdSize + SpanIdSize;
                }

                if (bytes.Length > pos && bytes[pos] == TraceOptionsFieldId)
                {
                    traceOptions = (ActivityTraceFlags)traceparentBytes[pos + IdSize];
                }

                return(SpanContext.Create(traceId, spanId, traceOptions, Tracestate.Empty));
            }
            catch (Exception e)
            {
                throw new SpanContextParseException("Invalid input.", e);
            }
        }
        public void VerifyHashAlgorithmCorrectness()
        {
            byte[] testBytes = new byte[]
            {
                0x8F, 0xFF, 0xFF, 0xFF,
                0xFF, 0xFF, 0xFF, 0xFF,
                0, 0, 0, 0, 0, 0, 0, 0,
            };
            byte[] testBytes2 = new byte[]
            {
                0x0F, 0x1F, 0x2F, 0x3F,
                0x4F, 0x5F, 0x6F, 0x7F,
                0x8F, 0x9F, 0xAF, 0xBF,
                0xCF, 0xDF, 0xEF, 0xFF,
            };
            ActivityTraceId testId  = ActivityTraceId.CreateFromBytes(testBytes);
            ActivityTraceId testId2 = ActivityTraceId.CreateFromBytes(testBytes2);

            ActivityContext    parentContext = default(ActivityContext);
            SamplingParameters testParams    = new SamplingParameters(parentContext, testId, "TestActivity", ActivityKind.Internal);
            SamplingParameters testParams2   = new SamplingParameters(parentContext, testId2, "TestActivity", ActivityKind.Internal);

            var zeroSampler = new ApplicationInsightsSampler(0);
            ApplicationInsightsSampler oneSampler = new ApplicationInsightsSampler(1);

            // 0.86 is below the sample score for testId1, but strict enough to drop testId2
            ApplicationInsightsSampler ratioSampler = new ApplicationInsightsSampler(0.86f);

            Assert.Equal(SamplingDecision.Drop, zeroSampler.ShouldSample(testParams).Decision);
            Assert.Equal(SamplingDecision.Drop, zeroSampler.ShouldSample(testParams2).Decision);

            Assert.Equal(SamplingDecision.RecordAndSample, oneSampler.ShouldSample(testParams).Decision);
            Assert.Equal(SamplingDecision.RecordAndSample, oneSampler.ShouldSample(testParams2).Decision);

            Assert.Equal(SamplingDecision.Drop, ratioSampler.ShouldSample(testParams).Decision);
            Assert.Equal(SamplingDecision.RecordAndSample, ratioSampler.ShouldSample(testParams2).Decision);
        }
示例#9
0
        public void ActivityTraceIdTests()
        {
            Span <byte> idBytes1 = stackalloc byte[16];
            Span <byte> idBytes2 = stackalloc byte[16];

            // Empty Constructor
            string          zeros   = "00000000000000000000000000000000";
            ActivityTraceId emptyId = new ActivityTraceId();

            Assert.Equal(zeros, emptyId.ToHexString());
            emptyId.CopyTo(idBytes1);
            Assert.Equal(new byte[16], idBytes1.ToArray());

            Assert.True(emptyId == new ActivityTraceId());
            Assert.True(!(emptyId != new ActivityTraceId()));
            Assert.True(emptyId.Equals(new ActivityTraceId()));
            Assert.True(emptyId.Equals((object)new ActivityTraceId()));
            Assert.Equal(new ActivityTraceId().GetHashCode(), emptyId.GetHashCode());

            // NewActivityTraceId
            ActivityTraceId newId1 = ActivityTraceId.CreateRandom();

            Assert.True(IsLowerCaseHex(newId1.ToHexString()));
            Assert.Equal(32, newId1.ToHexString().Length);

            ActivityTraceId newId2 = ActivityTraceId.CreateRandom();

            Assert.Equal(32, newId1.ToHexString().Length);
            Assert.NotEqual(newId1.ToHexString(), newId2.ToHexString());

            // Test equality
            Assert.True(newId1 != newId2);
            Assert.True(!(newId1 == newId2));
            Assert.True(!(newId1.Equals(newId2)));
            Assert.True(!(newId1.Equals((object)newId2)));
            Assert.NotEqual(newId1.GetHashCode(), newId2.GetHashCode());

            ActivityTraceId newId3 = ActivityTraceId.CreateFromString("00000000000000000000000000000001".AsSpan());

            Assert.True(newId3 != emptyId);
            Assert.True(!(newId3 == emptyId));
            Assert.True(!(newId3.Equals(emptyId)));
            Assert.True(!(newId3.Equals((object)emptyId)));
            Assert.NotEqual(newId3.GetHashCode(), emptyId.GetHashCode());

            // Use in Dictionary (this does assume we have no collisions in IDs over 100 tries (very good).
            var dict = new Dictionary <ActivityTraceId, string>();

            for (int i = 0; i < 100; i++)
            {
                var newId7 = ActivityTraceId.CreateRandom();
                dict[newId7] = newId7.ToHexString();
            }
            int ctr = 0;

            foreach (string value in dict.Values)
            {
                string valueInDict;
                Assert.True(dict.TryGetValue(ActivityTraceId.CreateFromString(value.AsSpan()), out valueInDict));
                Assert.Equal(value, valueInDict);
                ctr++;
            }
            Assert.Equal(100, ctr);     // We got out what we put in.

            // AsBytes and Byte constructor.
            newId2.CopyTo(idBytes2);
            ActivityTraceId newId2Clone = ActivityTraceId.CreateFromBytes(idBytes2);

            Assert.Equal(newId2.ToHexString(), newId2Clone.ToHexString());
            newId2Clone.CopyTo(idBytes1);
            Assert.Equal(idBytes2.ToArray(), idBytes1.ToArray());

            Assert.True(newId2 == newId2Clone);
            Assert.True(newId2.Equals(newId2Clone));
            Assert.True(newId2.Equals((object)newId2Clone));
            Assert.Equal(newId2.GetHashCode(), newId2Clone.GetHashCode());

            // String constructor and ToHexString().
            string          idStr = "0123456789abcdef0123456789abcdef";
            ActivityTraceId id    = ActivityTraceId.CreateFromString(idStr.AsSpan());

            Assert.Equal(idStr, id.ToHexString());

            // Utf8 Constructor.
            byte[]          idUtf8 = Encoding.UTF8.GetBytes(idStr);
            ActivityTraceId id1    = ActivityTraceId.CreateFromUtf8String(idUtf8);

            Assert.Equal(idStr, id1.ToHexString());

            // ToString
            Assert.Equal(idStr, id.ToString());
        }
        public void ProbabilitySampler_SampleBasedOnTraceId()
        {
            ISampler defaultProbability = ProbabilitySampler.Create(0.0001);
            // This traceId will not be sampled by the ProbabilitySampler because the first 8 bytes as long
            // is not less than probability * Long.MAX_VALUE;
            var notSampledtraceId =
                ActivityTraceId.CreateFromBytes(
                    new byte[]
            {
                0x8F,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
            });

            Assert.False(
                defaultProbability.ShouldSample(
                    null,
                    notSampledtraceId,
                    ActivitySpanId.CreateRandom(),
                    SPAN_NAME,
                    null).IsSampled);
            // This traceId will be sampled by the ProbabilitySampler because the first 8 bytes as long
            // is less than probability * Long.MAX_VALUE;
            var sampledtraceId =
                ActivityTraceId.CreateFromBytes(
                    new byte[]
            {
                0x00,
                0x00,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0xFF,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
                0,
            });

            Assert.True(
                defaultProbability.ShouldSample(
                    null,
                    sampledtraceId,
                    ActivitySpanId.CreateRandom(),
                    SPAN_NAME,
                    null).IsSampled);
        }