164 lines
5.9 KiB
Rust
164 lines
5.9 KiB
Rust
//! Tracing coverage tests
|
|
//!
|
|
//! These tests ensure tracing statements are executed during coverage runs.
|
|
//! They set up a tracing subscriber and exercise all code paths that contain
|
|
//! tracing statements.
|
|
|
|
#[cfg(feature = "tracing")]
|
|
#[cfg(test)]
|
|
mod tracing_tests {
|
|
use announcement::Announcement;
|
|
use std::sync::Arc;
|
|
use std::thread;
|
|
use std::time::Duration;
|
|
use tracing::Level;
|
|
use tracing_subscriber::fmt::format::FmtSpan;
|
|
|
|
/// Test: Tracing test: all tracing paths
|
|
///
|
|
/// Verifies: Verifies all tracing paths
|
|
/// Category: tracing
|
|
/// Test that exercises all tracing statements in src/lib.rs
|
|
#[test]
|
|
fn test_all_tracing_paths() {
|
|
// Set up tracing subscriber to capture all trace/debug messages
|
|
let subscriber = tracing_subscriber::fmt()
|
|
.with_max_level(Level::TRACE)
|
|
.with_span_events(FmtSpan::FULL)
|
|
.with_test_writer()
|
|
.finish();
|
|
|
|
tracing::subscriber::with_default(subscriber, || {
|
|
// Test 1: Announcement::new() - covers line 286-287
|
|
let (announcer, announcement) = Announcement::<i32>::new();
|
|
|
|
// Test 2: announce() - covers lines 422-423, 440, 444
|
|
let listener = announcement.listener();
|
|
announcer.announce(42).unwrap();
|
|
assert_eq!(listener.try_listen(), Some(42));
|
|
|
|
// Test 3: close() - covers lines 486, 492-493
|
|
let (announcer2, announcement2) = Announcement::<String>::new();
|
|
let _listener2 = announcement2.listener();
|
|
announcer2.close();
|
|
assert!(announcement2.is_closed());
|
|
|
|
// Test 4: Drop (auto-close) - covers lines 531-532, 538-539
|
|
let (announcer3, announcement3) = Announcement::<Vec<u8>>::new();
|
|
let _listener3 = announcement3.listener();
|
|
drop(announcer3); // Triggers Drop impl
|
|
assert!(announcement3.is_closed());
|
|
|
|
// Test 5: listen() async fast path - covers lines 653-654
|
|
let (announcer4, announcement4) = Announcement::<String>::new();
|
|
announcer4.announce("fast".to_string()).unwrap();
|
|
let listener4 = announcement4.listener();
|
|
let rt = tokio::runtime::Runtime::new().unwrap();
|
|
let result = rt.block_on(async { listener4.listen().await });
|
|
assert_eq!(result, Ok("fast".to_string()));
|
|
|
|
// Test 6: listen() async slow path - covers lines 660-661, 666-667, 675-677, 682-683, 691
|
|
let (announcer5, announcement5) = Announcement::<i32>::new();
|
|
let listener5 = announcement5.listener();
|
|
|
|
let rt2 = tokio::runtime::Runtime::new().unwrap();
|
|
rt2.block_on(async {
|
|
let listen_future = listener5.listen();
|
|
|
|
// Spawn a task to announce after a delay
|
|
let ann5_clone = announcer5;
|
|
tokio::spawn(async move {
|
|
tokio::time::sleep(Duration::from_millis(10)).await;
|
|
ann5_clone.announce(99).unwrap();
|
|
});
|
|
|
|
let result = listen_future.await;
|
|
assert_eq!(result, Ok(99));
|
|
});
|
|
|
|
// Test 7: listen() async with closed announcer - covers lines 660-661, 666-667, 682-683
|
|
let (announcer6, announcement6) = Announcement::<String>::new();
|
|
let listener6 = announcement6.listener();
|
|
|
|
let rt3 = tokio::runtime::Runtime::new().unwrap();
|
|
rt3.block_on(async {
|
|
let listen_future = listener6.listen();
|
|
|
|
// Close the announcer
|
|
let ann6_clone = announcer6;
|
|
tokio::spawn(async move {
|
|
tokio::time::sleep(Duration::from_millis(10)).await;
|
|
ann6_clone.close();
|
|
});
|
|
|
|
let result = listen_future.await;
|
|
assert!(result.is_err());
|
|
});
|
|
});
|
|
}
|
|
|
|
/// Test: Tracing test: blocking with tracing
|
|
///
|
|
/// Verifies: Verifies blocking with tracing
|
|
/// Category: tracing
|
|
/// Test blocking operations with tracing
|
|
#[cfg(feature = "std")]
|
|
#[test]
|
|
fn test_blocking_with_tracing() {
|
|
let subscriber = tracing_subscriber::fmt()
|
|
.with_max_level(Level::TRACE)
|
|
.with_test_writer()
|
|
.finish();
|
|
|
|
tracing::subscriber::with_default(subscriber, || {
|
|
// listen_blocking() - exercises tracing in blocking wait
|
|
let (announcer, announcement) = Announcement::<i32>::new();
|
|
let listener = announcement.listener();
|
|
|
|
thread::spawn(move || {
|
|
thread::sleep(Duration::from_millis(10));
|
|
announcer.announce(123).unwrap();
|
|
});
|
|
|
|
let result = listener.listen_blocking();
|
|
assert_eq!(result, Ok(123));
|
|
});
|
|
}
|
|
|
|
/// Test: Tracing test: concurrent tracing
|
|
///
|
|
/// Verifies: Verifies concurrent tracing
|
|
/// Category: tracing
|
|
/// Test concurrent tracing paths
|
|
#[test]
|
|
fn test_concurrent_tracing() {
|
|
let subscriber = tracing_subscriber::fmt()
|
|
.with_max_level(Level::TRACE)
|
|
.with_test_writer()
|
|
.finish();
|
|
|
|
tracing::subscriber::with_default(subscriber, || {
|
|
let (announcer, announcement) = Announcement::<Arc<String>>::new();
|
|
|
|
// Announce first
|
|
announcer
|
|
.announce(Arc::new("concurrent".to_string()))
|
|
.unwrap();
|
|
|
|
let mut handles = vec![];
|
|
|
|
// Create multiple listeners concurrently after announce
|
|
for _ in 0..10 {
|
|
let listener = announcement.listener();
|
|
handles.push(thread::spawn(move || listener.try_listen()));
|
|
}
|
|
|
|
// Verify all threads received the value
|
|
for handle in handles {
|
|
let result = handle.join().unwrap();
|
|
assert_eq!(result, Some(Arc::new("concurrent".to_string())));
|
|
}
|
|
});
|
|
}
|
|
}
|