Skip to content

Commit 6628b5b

Browse files
committed
add zipkin baggage propagator
1 parent 05616aa commit 6628b5b

File tree

2 files changed

+98
-0
lines changed

2 files changed

+98
-0
lines changed
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
/*
2+
* Copyright The OpenTelemetry Authors
3+
* SPDX-License-Identifier: Apache-2.0
4+
*/
5+
6+
import Foundation
7+
8+
/**
9+
* Implementation of the Zipkin propagation protocol and by default it uses `baggage-` prefix. See
10+
* https://github.com/openzipkin/brave/blob/master/brave/README.md#remote-baggage
11+
*/
12+
13+
public class ZipkinBaggagePropagator: TextMapBaggagePropagator {
14+
public static let baggagePrefix = "baggage-"
15+
16+
public let fields: Set<String> = []
17+
18+
public init() {}
19+
20+
public func inject<S>(baggage: Baggage, carrier: inout [String: String], setter: S) where S: Setter {
21+
baggage.getEntries().forEach {
22+
setter.set(carrier: &carrier, key: ZipkinBaggagePropagator.baggagePrefix + $0.key.name, value: $0.value.string)
23+
}
24+
}
25+
26+
public func extract<G>(carrier: [String: String], getter: G) -> Baggage? where G: Getter {
27+
let builder = OpenTelemetry.instance.baggageManager.baggageBuilder()
28+
29+
carrier.forEach {
30+
if $0.key.hasPrefix(ZipkinBaggagePropagator.baggagePrefix) {
31+
if $0.key.count == ZipkinBaggagePropagator.baggagePrefix.count {
32+
return
33+
}
34+
35+
if let key = EntryKey(name: String($0.key.dropFirst(ZipkinBaggagePropagator.baggagePrefix.count))),
36+
let value = EntryValue(string: $0.value)
37+
{
38+
builder.put(key: key, value: value, metadata: nil)
39+
}
40+
}
41+
}
42+
43+
return builder.build()
44+
}
45+
}
Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
/*
2+
* Copyright The OpenTelemetry Authors
3+
* SPDX-License-Identifier: Apache-2.0
4+
*/
5+
6+
@testable import OpenTelemetryApi
7+
import XCTest
8+
9+
class ZipkinBaggagePropagatorTests: XCTestCase {
10+
let builder = DefaultBaggageBuilder()
11+
let zipkinPropagator = ZipkinBaggagePropagator()
12+
let setter = TestSetter()
13+
let getter = TestGetter()
14+
15+
func testInjectBaggage() {
16+
// Metadata won't be propagated, but it MUST NOT cause ay problem.
17+
let baggage = builder.put(key: "nometa", value: "nometa-value")
18+
.put(key: "nometa", value: "nometa-value")
19+
.put(key: "meta", value: "meta-value", metadata: "somemetadata; someother=foo")
20+
.build()
21+
22+
var carrier = [String: String]()
23+
zipkinPropagator.inject(baggage: baggage, carrier: &carrier, setter: setter)
24+
25+
let expected1 = [ZipkinBaggagePropagator.baggagePrefix + "nometa": "nometa-value",
26+
ZipkinBaggagePropagator.baggagePrefix + "meta": "meta-value"]
27+
let expected2 = [ZipkinBaggagePropagator.baggagePrefix + "meta": "meta-value",
28+
ZipkinBaggagePropagator.baggagePrefix + "nometa": "nometa-value"]
29+
XCTAssert(carrier == expected1 || carrier == expected2)
30+
}
31+
32+
func testExtractBaggageWithPrefix() {
33+
var carrier = [String: String]()
34+
carrier[ZipkinBaggagePropagator.baggagePrefix + "nometa"] = "nometa-value"
35+
carrier[ZipkinBaggagePropagator.baggagePrefix + "meta"] = "meta-value"
36+
carrier["another"] = "value"
37+
38+
let expectedBaggage = builder.put(key: "nometa", value: "nometa-value")
39+
.put(key: "meta", value: "meta-value")
40+
.build()
41+
42+
let result = zipkinPropagator.extract(carrier: carrier, getter: getter)
43+
XCTAssertEqual(result?.getEntries().sorted(), expectedBaggage.getEntries().sorted())
44+
}
45+
46+
func testExtractBaggageWithPrefixEmptyKey() {
47+
var carrier = [String: String]()
48+
carrier[ZipkinBaggagePropagator.baggagePrefix] = "value"
49+
50+
let result = zipkinPropagator.extract(carrier: carrier, getter: getter)!
51+
XCTAssertTrue(result.getEntries().isEmpty)
52+
}
53+
}

0 commit comments

Comments
 (0)