Skip to content

Commit 6d2edf0

Browse files
authored
Merge branch 'main' into refactor-span-processor
2 parents 5fce0a5 + 78db32c commit 6d2edf0

File tree

3 files changed

+104
-64
lines changed

3 files changed

+104
-64
lines changed

opentelemetry-otlp/tests/integration_test/src/test_utils.rs

+12-2
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,7 @@
2020

2121
use anyhow::Result;
2222
use opentelemetry::{otel_debug, otel_info};
23-
use std::fs;
24-
use std::fs::File;
23+
use std::fs::{self, File, OpenOptions};
2524
use std::os::unix::fs::PermissionsExt;
2625
use std::sync::{Arc, Mutex, Once, OnceLock};
2726
use testcontainers::core::wait::HttpWaitStrategy;
@@ -125,6 +124,17 @@ fn upsert_empty_file(path: &str) -> File {
125124
file
126125
}
127126

127+
/// Cleans up file specificed as argument by truncating its content.
128+
///
129+
/// This function is meant to cleanup the generated json file before a test starts,
130+
/// preventing entries from previous tests from interfering with the current test's results.
131+
pub fn cleanup_file(file_path: &str) {
132+
let _ = OpenOptions::new()
133+
.write(true)
134+
.truncate(true)
135+
.open(file_path); // ignore result, as file may not exist
136+
}
137+
128138
///
129139
/// Shuts down our collector container. This should be run as part of each test
130140
/// suite shutting down!

opentelemetry-otlp/tests/integration_test/tests/logs.rs

+28-62
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,14 @@
22

33
use anyhow::Result;
44
use ctor::dtor;
5+
use integration_test_runner::logs_asserter::{read_logs_from_json, LogsAsserter};
56
use integration_test_runner::test_utils;
67
use opentelemetry_otlp::LogExporter;
78
use opentelemetry_sdk::logs::LoggerProvider;
89
use opentelemetry_sdk::{logs as sdklogs, Resource};
910
use std::fs::File;
1011
use std::io::Read;
12+
use std::os::unix::fs::MetadataExt;
1113

1214
fn init_logs(is_simple: bool) -> Result<sdklogs::LoggerProvider> {
1315
let exporter_builder = LogExporter::builder();
@@ -88,26 +90,26 @@ mod logtests {
8890
#[tokio::test(flavor = "multi_thread", worker_threads = 4)]
8991
#[cfg(any(feature = "tonic-client", feature = "reqwest-blocking-client"))]
9092
pub async fn logs_batch_tokio_multi_thread() -> Result<()> {
91-
logs_batch_tokio_helper().await
93+
logs_tokio_helper(false).await
9294
}
9395

9496
#[tokio::test(flavor = "multi_thread", worker_threads = 1)]
9597
#[cfg(any(feature = "tonic-client", feature = "reqwest-blocking-client"))]
9698
pub async fn logs_batch_tokio_multi_with_one_worker() -> Result<()> {
97-
logs_batch_tokio_helper().await
99+
logs_tokio_helper(false).await
98100
}
99101

100102
#[tokio::test(flavor = "current_thread")]
101103
#[cfg(any(feature = "tonic-client", feature = "reqwest-blocking-client"))]
102104
pub async fn logs_batch_tokio_current() -> Result<()> {
103-
logs_batch_tokio_helper().await
105+
logs_tokio_helper(false).await
104106
}
105107

106-
async fn logs_batch_tokio_helper() -> Result<()> {
107-
use crate::{assert_logs_results, init_logs};
108+
async fn logs_tokio_helper(is_simple: bool) -> Result<()> {
109+
use crate::{assert_logs_results_contains, init_logs};
108110
test_utils::start_collector_container().await?;
109111

110-
let logger_provider = init_logs(false).unwrap();
112+
let logger_provider = init_logs(is_simple).unwrap();
111113
let layer = OpenTelemetryTracingBridge::new(&logger_provider);
112114
let subscriber = tracing_subscriber::registry().with(layer);
113115
// generate a random uuid and store it to expected guid
@@ -119,58 +121,37 @@ mod logtests {
119121

120122
let _ = logger_provider.shutdown();
121123
tokio::time::sleep(Duration::from_secs(5)).await;
122-
assert_logs_results(test_utils::LOGS_FILE, expected_uuid.as_str())?;
124+
assert_logs_results_contains(test_utils::LOGS_FILE, expected_uuid.as_str())?;
123125
Ok(())
124126
}
125127

126128
#[tokio::test(flavor = "multi_thread", worker_threads = 4)]
127129
#[cfg(any(feature = "tonic-client", feature = "reqwest-client"))]
128130
pub async fn logs_simple_tokio_multi_thread() -> Result<()> {
129-
logs_simple_tokio_helper().await
131+
logs_tokio_helper(true).await
130132
}
131133

132134
#[tokio::test(flavor = "multi_thread", worker_threads = 1)]
133135
#[cfg(any(feature = "tonic-client", feature = "reqwest-client"))]
134136
pub async fn logs_simple_tokio_multi_with_one_worker() -> Result<()> {
135-
logs_simple_tokio_helper().await
137+
logs_tokio_helper(true).await
136138
}
137139

138140
// Ignored, to be investigated
139141
#[ignore]
140142
#[tokio::test(flavor = "current_thread")]
141143
#[cfg(any(feature = "tonic-client", feature = "reqwest-client"))]
142144
pub async fn logs_simple_tokio_current() -> Result<()> {
143-
logs_simple_tokio_helper().await
144-
}
145-
146-
async fn logs_simple_tokio_helper() -> Result<()> {
147-
use crate::{assert_logs_results, init_logs};
148-
test_utils::start_collector_container().await?;
149-
150-
let logger_provider = init_logs(true).unwrap();
151-
let layer = OpenTelemetryTracingBridge::new(&logger_provider);
152-
let subscriber = tracing_subscriber::registry().with(layer);
153-
info!("Tracing initialized");
154-
// generate a random uuid and store it to expected guid
155-
let expected_uuid = Uuid::new_v4().to_string();
156-
{
157-
let _guard = tracing::subscriber::set_default(subscriber);
158-
info!(target: "my-target", uuid = expected_uuid, "hello from {}. My price is {}.", "banana", 2.99);
159-
}
160-
161-
let _ = logger_provider.shutdown();
162-
tokio::time::sleep(Duration::from_secs(5)).await;
163-
assert_logs_results(test_utils::LOGS_FILE, expected_uuid.as_str())?;
164-
Ok(())
145+
logs_tokio_helper(true).await
165146
}
166147

167148
#[test]
168149
#[cfg(any(feature = "tonic-client", feature = "reqwest-blocking-client"))]
169150
pub fn logs_batch_non_tokio_main() -> Result<()> {
170-
logs_batch_non_tokio_helper()
151+
logs_non_tokio_helper(false)
171152
}
172153

173-
fn logs_batch_non_tokio_helper() -> Result<()> {
154+
fn logs_non_tokio_helper(is_simple: bool) -> Result<()> {
174155
// Initialize the logger provider inside a tokio runtime
175156
// as this allows tonic client to capture the runtime,
176157
// but actual export occurs from the dedicated std::thread
@@ -179,7 +160,7 @@ mod logtests {
179160
let logger_provider = rt.block_on(async {
180161
// While we're here setup our collector container too, as this needs tokio to run
181162
test_utils::start_collector_container().await?;
182-
init_logs(false)
163+
init_logs(is_simple)
183164
})?;
184165
let layer = layer::OpenTelemetryTracingBridge::new(&logger_provider);
185166
let subscriber = tracing_subscriber::registry().with(layer);
@@ -192,43 +173,18 @@ mod logtests {
192173

193174
let _ = logger_provider.shutdown();
194175
std::thread::sleep(Duration::from_secs(5));
195-
assert_logs_results(test_utils::LOGS_FILE, expected_uuid.as_str())?;
176+
assert_logs_results_contains(test_utils::LOGS_FILE, expected_uuid.as_str())?;
196177
Ok(())
197178
}
198179

199180
#[test]
200181
#[cfg(any(feature = "tonic-client", feature = "reqwest-blocking-client"))]
201182
pub fn logs_simple_non_tokio_main() -> Result<()> {
202-
logs_simple_non_tokio_helper()
203-
}
204-
205-
fn logs_simple_non_tokio_helper() -> Result<()> {
206-
// Initialize the logger provider inside a tokio runtime
207-
// as this allows tonic client to capture the runtime,
208-
// but actual export occurs from the main non-tokio thread.
209-
let rt = tokio::runtime::Runtime::new()?;
210-
let logger_provider = rt.block_on(async {
211-
// While we're here setup our collector container too, as this needs tokio to run
212-
test_utils::start_collector_container().await?;
213-
init_logs(true)
214-
})?;
215-
let layer = layer::OpenTelemetryTracingBridge::new(&logger_provider);
216-
let subscriber = tracing_subscriber::registry().with(layer);
217-
// generate a random uuid and store it to expected guid
218-
let expected_uuid = Uuid::new_v4().to_string();
219-
{
220-
let _guard = tracing::subscriber::set_default(subscriber);
221-
info!(target: "my-target", uuid = expected_uuid, "hello from {}. My price is {}.", "banana", 2.99);
222-
}
223-
224-
let _ = logger_provider.shutdown();
225-
std::thread::sleep(Duration::from_secs(5));
226-
assert_logs_results(test_utils::LOGS_FILE, expected_uuid.as_str())?;
227-
Ok(())
183+
logs_non_tokio_helper(true)
228184
}
229185
}
230186

231-
pub fn assert_logs_results(result: &str, expected_content: &str) -> Result<()> {
187+
pub fn assert_logs_results_contains(result: &str, expected_content: &str) -> Result<()> {
232188
let file = File::open(result)?;
233189
let mut contents = String::new();
234190
let mut reader = std::io::BufReader::new(&file);
@@ -237,6 +193,16 @@ pub fn assert_logs_results(result: &str, expected_content: &str) -> Result<()> {
237193
Ok(())
238194
}
239195

196+
pub fn assert_logs_results(result: &str, expected: &str) -> Result<()> {
197+
let left = read_logs_from_json(File::open(expected)?)?;
198+
let right = read_logs_from_json(File::open(result)?)?;
199+
200+
LogsAsserter::new(left, right).assert();
201+
202+
assert!(File::open(result).unwrap().metadata().unwrap().size() > 0);
203+
Ok(())
204+
}
205+
240206
///
241207
/// Make sure we stop the collector container, otherwise it will sit around hogging our
242208
/// ports and subsequent test runs will fail.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
#![cfg(unix)]
2+
3+
use anyhow::Result;
4+
use ctor::dtor;
5+
use integration_test_runner::logs_asserter::{read_logs_from_json, LogsAsserter};
6+
use integration_test_runner::test_utils;
7+
use opentelemetry_appender_tracing::layer;
8+
use opentelemetry_otlp::LogExporter;
9+
use opentelemetry_sdk::logs::LoggerProvider;
10+
use opentelemetry_sdk::Resource;
11+
use std::fs::File;
12+
use std::os::unix::fs::MetadataExt;
13+
use tracing::info;
14+
use tracing_subscriber::layer::SubscriberExt;
15+
16+
#[tokio::test(flavor = "multi_thread", worker_threads = 4)]
17+
#[cfg(feature = "tonic-client")]
18+
pub async fn test_logs() -> Result<()> {
19+
test_utils::start_collector_container().await?;
20+
test_utils::cleanup_file("./actual/logs.json"); // Ensure logs.json is empty before the test
21+
let exporter_builder = LogExporter::builder().with_tonic();
22+
let exporter = exporter_builder.build()?;
23+
let mut logger_provider_builder = LoggerProvider::builder();
24+
logger_provider_builder = logger_provider_builder.with_batch_exporter(exporter);
25+
let logger_provider = logger_provider_builder
26+
.with_resource(
27+
Resource::builder_empty()
28+
.with_service_name("logs-integration-test")
29+
.build(),
30+
)
31+
.build();
32+
let layer = layer::OpenTelemetryTracingBridge::new(&logger_provider);
33+
let subscriber = tracing_subscriber::registry().with(layer);
34+
35+
{
36+
let _guard = tracing::subscriber::set_default(subscriber);
37+
info!(target: "my-target", "hello from {}. My price is {}.", "banana", 2.99);
38+
}
39+
40+
let _ = logger_provider.shutdown();
41+
tokio::time::sleep(std::time::Duration::from_secs(5)).await;
42+
assert_logs_results(test_utils::LOGS_FILE, "expected/logs.json")?;
43+
Ok(())
44+
}
45+
46+
fn assert_logs_results(result: &str, expected: &str) -> Result<()> {
47+
let left = read_logs_from_json(File::open(expected)?)?;
48+
let right = read_logs_from_json(File::open(result)?)?;
49+
50+
LogsAsserter::new(left, right).assert();
51+
52+
assert!(File::open(result).unwrap().metadata().unwrap().size() > 0);
53+
Ok(())
54+
}
55+
56+
///
57+
/// Make sure we stop the collector container, otherwise it will sit around hogging our
58+
/// ports and subsequent test runs will fail.
59+
///
60+
#[dtor]
61+
fn shutdown() {
62+
println!("metrics::shutdown");
63+
test_utils::stop_collector_container();
64+
}

0 commit comments

Comments
 (0)