File tree Expand file tree Collapse file tree 12 files changed +125
-19
lines changed
Exporters/OpenTelemetryProtocol
Tests/ExportersTests/OpenTelemetryProtocol Expand file tree Collapse file tree 12 files changed +125
-19
lines changed Original file line number Diff line number Diff line change 1+ //
2+ // Copyright The OpenTelemetry Authors
3+ // SPDX-License-Identifier: Apache-2.0
4+ //
5+
6+ import Foundation
7+
8+ public enum Constants {
9+ enum HTTP {
10+ static let userAgent = " User-Agent "
11+ }
12+ }
Original file line number Diff line number Diff line change 1+ //
2+ // Copyright The OpenTelemetry Authors
3+ // SPDX-License-Identifier: Apache-2.0
4+ //
5+
6+ import Foundation
7+ import OpenTelemetryApi
8+
9+ public struct Headers {
10+ // GetUserAgentHeader returns an OTLP header value of the form "OTel OTLP Exporter Swift/{{ .Version }}"
11+ // https://github.com/open-telemetry/opentelemetry-specification/blob/main/specification/protocol/exporter.md#user-agent
12+ public static func getUserAgentHeader( ) -> String {
13+ var version = OpenTelemetry . version
14+ if !version. isEmpty && version. hasPrefix ( " v " ) {
15+ version = String ( version. dropFirst ( 1 ) )
16+ }
17+ let userAgent = " OTel-OTLP-Exporter-Swift/ \( version) "
18+
19+ return userAgent
20+ }
21+ }
Original file line number Diff line number Diff line change @@ -25,6 +25,7 @@ public class OtlpHttpExporterBase {
2525 do {
2626 request. httpMethod = " POST "
2727 request. httpBody = try body. serializedData ( )
28+ request. setValue ( Headers . getUserAgentHeader ( ) , forHTTPHeaderField: Constants . HTTP. userAgent)
2829 request. setValue ( " application/x-protobuf " , forHTTPHeaderField: " Content-Type " )
2930 } catch {
3031 print ( " Error serializing body: \( error) " )
Original file line number Diff line number Diff line change @@ -24,13 +24,20 @@ public class OtlpLogExporter : LogRecordExporter {
2424 self . channel = channel
2525 logClient = Opentelemetry_Proto_Collector_Logs_V1_LogsServiceNIOClient ( channel: channel)
2626 self . config = config
27+ let userAgentHeader = ( Constants . HTTP. userAgent, Headers . getUserAgentHeader ( ) )
2728 if let headers = envVarHeaders {
28- callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
29+ var updatedHeaders = headers
30+ updatedHeaders. append ( userAgentHeader)
31+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( updatedHeaders) , logger: logger)
2932 } else if let headers = config. headers {
30- callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
33+ var updatedHeaders = headers
34+ updatedHeaders. append ( userAgentHeader)
35+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( updatedHeaders) , logger: logger)
3136 }
3237 else {
33- callOptions = CallOptions ( logger: logger)
38+ var headers = [ ( String, String) ] ( )
39+ headers. append ( userAgentHeader)
40+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
3441 }
3542 }
3643
Original file line number Diff line number Diff line change @@ -23,13 +23,20 @@ public class OtlpMetricExporter: MetricExporter {
2323 self . channel = channel
2424 self . config = config
2525 self . metricClient = Opentelemetry_Proto_Collector_Metrics_V1_MetricsServiceNIOClient ( channel: self . channel)
26+ let userAgentHeader = ( Constants . HTTP. userAgent, Headers . getUserAgentHeader ( ) )
2627 if let headers = envVarHeaders {
27- callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
28+ var updatedHeaders = headers
29+ updatedHeaders. append ( userAgentHeader)
30+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( updatedHeaders) , logger: logger)
2831 } else if let headers = config. headers {
29- callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
32+ var updatedHeaders = headers
33+ updatedHeaders. append ( userAgentHeader)
34+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( updatedHeaders) , logger: logger)
3035 }
3136 else {
32- callOptions = CallOptions ( logger: logger)
37+ var headers = [ ( String, String) ] ( )
38+ headers. append ( userAgentHeader)
39+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
3340 }
3441 }
3542
Original file line number Diff line number Diff line change @@ -21,14 +21,20 @@ public class OtlpTraceExporter: SpanExporter {
2121 self . channel = channel
2222 traceClient = Opentelemetry_Proto_Collector_Trace_V1_TraceServiceNIOClient ( channel: channel)
2323 self . config = config
24+ let userAgentHeader = ( Constants . HTTP. userAgent, Headers . getUserAgentHeader ( ) )
2425 if let headers = envVarHeaders {
25- callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
26+ var updatedHeaders = headers
27+ updatedHeaders. append ( userAgentHeader)
28+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( updatedHeaders) , logger: logger)
2629 } else if let headers = config. headers {
30+ var updatedHeaders = headers
31+ updatedHeaders. append ( userAgentHeader)
32+ callOptions = CallOptions ( customMetadata: HPACKHeaders ( updatedHeaders) , logger: logger)
33+ } else {
34+ var headers = [ ( String, String) ] ( )
35+ headers. append ( userAgentHeader)
2736 callOptions = CallOptions ( customMetadata: HPACKHeaders ( headers) , logger: logger)
2837 }
29- else {
30- callOptions = CallOptions ( logger: logger)
31- }
3238 }
3339
3440 public func export( spans: [ SpanData ] ) -> SpanExporterResultCode {
Original file line number Diff line number Diff line change @@ -290,14 +290,19 @@ public class RecordEventsReadableSpan: ReadableSpan {
290290 }
291291
292292 public func end( time: Date ) {
293- internalStatusQueue. sync ( flags: . barrier) {
293+ let alreadyEnded = internalStatusQueue. sync ( flags: . barrier) {
294294 if internalEnd {
295- return
296-
297- } else {
298- internalEnd = true
295+ return true
299296 }
297+
298+ internalEnd = true
299+ return false
300300 }
301+
302+ if alreadyEnded {
303+ return
304+ }
305+
301306 eventsSyncLock. withLockVoid {
302307 attributesSyncLock. withLockVoid {
303308 isRecording = false
Original file line number Diff line number Diff line change @@ -45,11 +45,14 @@ class OtlpHttpLogRecordExporterTests: XCTestCase {
4545
4646 let endpoint = URL ( string: " http://localhost: \( testServer. serverPort) " ) !
4747 let exporter = OtlpHttpLogExporter ( endpoint: endpoint)
48-
4948 let _ = exporter. export ( logRecords: [ logRecord] )
5049
5150 // TODO: Use protobuf to verify that we have received the correct Log records
52- XCTAssertNoThrow ( try testServer. receiveHead ( ) )
51+ XCTAssertNoThrow ( try testServer. receiveHeadAndVerify { head in
52+ let otelVersion = Headers . getUserAgentHeader ( )
53+ XCTAssertTrue ( head. headers. contains ( name: Constants . HTTP. userAgent) )
54+ XCTAssertEqual ( otelVersion, head. headers. first ( name: Constants . HTTP. userAgent) )
55+ } )
5356 XCTAssertNoThrow ( try testServer. receiveBodyAndVerify ( ) { body in
5457 var contentsBuffer = ByteBuffer ( buffer: body)
5558 let contents = contentsBuffer. readString ( length: contentsBuffer. readableBytes) !
Original file line number Diff line number Diff line change @@ -55,7 +55,11 @@ class OtlpHttpMetricsExporterTest: XCTestCase {
5555 }
5656 XCTAssertEqual ( result, MetricExporterResultCode . success)
5757
58- XCTAssertNoThrow ( try testServer. receiveHead ( ) )
58+ XCTAssertNoThrow ( try testServer. receiveHeadAndVerify { head in
59+ let otelVersion = Headers . getUserAgentHeader ( )
60+ XCTAssertTrue ( head. headers. contains ( name: Constants . HTTP. userAgent) )
61+ XCTAssertEqual ( otelVersion, head. headers. first ( name: Constants . HTTP. userAgent) )
62+ } )
5963 XCTAssertNoThrow ( try testServer. receiveBodyAndVerify ( ) { body in
6064 var contentsBuffer = ByteBuffer ( buffer: body)
6165 let contents = contentsBuffer. readString ( length: contentsBuffer. readableBytes) !
Original file line number Diff line number Diff line change @@ -25,6 +25,7 @@ class OtlpHttpTraceExporterTests: XCTestCase {
2525 override func tearDown( ) {
2626 XCTAssertNoThrow ( try testServer. stop ( ) )
2727 XCTAssertNoThrow ( try group. syncShutdownGracefully ( ) )
28+
2829 }
2930
3031 // This is a somewhat hacky solution to verifying that the spans got across correctly. It simply looks for the metric
@@ -41,7 +42,11 @@ class OtlpHttpTraceExporterTests: XCTestCase {
4142 spans. append ( generateFakeSpan ( endpointName: endpointName2) )
4243 let _ = exporter. export ( spans: spans)
4344
44- XCTAssertNoThrow ( try testServer. receiveHead ( ) )
45+ XCTAssertNoThrow ( try testServer. receiveHeadAndVerify { head in
46+ let otelVersion = Headers . getUserAgentHeader ( )
47+ XCTAssertTrue ( head. headers. contains ( name: Constants . HTTP. userAgent) )
48+ XCTAssertEqual ( otelVersion, head. headers. first ( name: Constants . HTTP. userAgent) )
49+ } )
4550 XCTAssertNoThrow ( try testServer. receiveBodyAndVerify ( ) { body in
4651 var contentsBuffer = ByteBuffer ( buffer: body)
4752 let contents = contentsBuffer. readString ( length: contentsBuffer. readableBytes) !
You can’t perform that action at this time.
0 commit comments