Skip to main content

Common Errors

Network Transport Unavailable

Symptom: Network publishing doesn’t work, but local publishing works fine. Cause: Network transport failed to initialize or is disabled. Solution:
use cerulion_core::prelude::*;

// Check if network is enabled
let publisher = Publisher::create("topic", true)?;
if publisher.is_network_enabled() {
    println!("Network publishing is active");
} else {
    println!("Network publishing is disabled");
    publisher.enable_network();
}

// Check logs for network errors
// Network failures are logged but don't propagate to the caller
Network failures are logged but don’t propagate to the caller. This ensures local communication continues even if the network is down. Check logs if network communication isn’t working.
Prevention:
  • Check network connectivity before enabling network transport
  • Monitor logs for network errors
  • Use is_network_enabled() to verify network status

Deserialization Errors

Symptom: from_bytes() fails when receiving messages. Cause: Message format doesn’t match your struct, message is corrupted, or version mismatch. Solution:
use cerulion_core::prelude::*;

match subscriber.receive() {
    Ok(Some(bytes)) => {
        match SensorData::from_bytes(&bytes) {
            Ok(data) => {
                // Process message
                process(data);
            }
            Err(e) => {
                // Log error with context
                eprintln!("Deserialization error: {}", e);
                eprintln!("Message length: {} bytes", bytes.len());
                // Optionally: log first few bytes for debugging
                if bytes.len() > 0 {
                    eprintln!("First bytes: {:?}", &bytes[..std::cmp::min(16, bytes.len())]);
                }
            }
        }
    }
    _ => {}
}
Prevention:
  • Validate message length before deserialization
  • Use versioned message formats
  • Handle deserialization errors gracefully
  • Log raw bytes for debugging when errors occur

Publisher Dropped Too Early

Symptom: Subscriber receives None even though messages are being sent. Cause: Publisher was dropped before subscriber could receive messages. Solution:
use cerulion_core::prelude::*;

// ✅ Good: Publisher stays alive
let publisher = Publisher::create("topic", true)?;
let subscriber = Subscriber::create("topic", None)?;

// Keep publisher in scope
// ... use publisher and subscriber ...

// ❌ Bad: Publisher dropped too early
{
    let publisher = Publisher::create("topic", true)?;
} // Publisher dropped here
let subscriber = Subscriber::create("topic", None)?;
// Subscriber won't receive messages
Prevention:
  • Keep publisher handles alive for the lifetime you need them
  • Use shared ownership (Arc) if publishers need to be shared across threads
  • Don’t drop publishers before subscribers finish receiving

Subscriber Handle Dropped

Symptom: Subscription stops working unexpectedly. Cause: Subscriber handle was dropped, closing the subscription. Solution:
use cerulion_core::prelude::*;

// ✅ Good: Keep subscriber handle alive
let subscriber = Subscriber::create("topic", None)?;
// Keep subscriber in scope
// ... use subscriber ...

// ❌ Bad: Subscriber handle dropped
{
    let subscriber = Subscriber::create("topic", None)?;
} // Subscriber handle dropped here
// Subscription is automatically closed
Prevention:
  • Keep subscriber handles alive for the lifetime you need the subscription
  • Use shared ownership (Arc) if subscribers need to be shared across threads
  • Don’t drop subscriber handles while you still need to receive messages

Force Local Transport with No Local Publisher

Symptom: receive() always returns None when forcing local transport. Cause: No local publisher exists for the topic. Solution:
use cerulion_core::prelude::*;

// ❌ Bad: Force local when no publisher exists
let subscriber = Subscriber::create("topic", Some(false))?;
// receive() will always return None

// ✅ Good: Use auto-detection or ensure publisher exists first
let publisher = Publisher::create("topic", true)?;
let subscriber = Subscriber::create("topic", Some(false))?;
// Now local transport works

// ✅ Alternative: Use auto-detection
let subscriber = Subscriber::create("topic", None)?;
// Automatically uses local if available, network otherwise
Prevention:
  • Use auto-detection (None) unless you’re certain a local publisher exists
  • Create the publisher before creating a local-only subscriber
  • Check if local transport is available before forcing it

Type Mismatch

Symptom: Deserialization fails because message format doesn’t match expected type. Cause: Multiple publishers sending different message types to the same topic, or version mismatch. Solution:
use cerulion_core::prelude::*;

// Publishers work with raw bytes, so multiple publishers can exist
let pub1 = Publisher::create("topic", true)?;
let pub2 = Publisher::create("topic", true)?;

// Type mismatch will be detected at deserialization time by subscribers
// Subscribers must handle deserialization errors appropriately
match subscriber.receive() {
    Ok(Some(bytes)) => {
        match SensorData::from_bytes(&bytes) {
            Ok(data) => process(data),
            Err(e) => {
                // Handle type mismatch
                eprintln!("Type mismatch: {}", e);
                // Optionally: try deserializing as different type
            }
        }
    }
    _ => {}
}
Prevention:
  • Use consistent message types for each topic
  • Version your message formats
  • Handle deserialization errors gracefully
  • Consider using TopicManager for built-in type safety

Troubleshooting Tips

Check Network Status

use cerulion_core::prelude::*;

let publisher = Publisher::create("topic", true)?;

// Verify network is enabled
if !publisher.is_network_enabled() {
    println!("Network is disabled, enabling...");
    publisher.enable_network();
}

// Check if network thread is running
// (Network thread starts automatically when network is enabled)

Verify Publisher/Subscriber Are Alive

use cerulion_core::prelude::*;

// Ensure publisher stays alive
let publisher = Publisher::create("topic", true)?;

// Ensure subscriber stays alive
let subscriber = Subscriber::create("topic", None)?;

// Both must remain in scope
// ... use them ...

Log Raw Bytes for Debugging

use cerulion_core::prelude::*;

match subscriber.receive() {
    Ok(Some(bytes)) => {
        // Log message details for debugging
        eprintln!("Received {} bytes", bytes.len());
        if bytes.len() > 0 {
            eprintln!("First 16 bytes: {:?}", &bytes[..std::cmp::min(16, bytes.len())]);
        }
        
        match SensorData::from_bytes(&bytes) {
            Ok(data) => process(data),
            Err(e) => {
                eprintln!("Deserialization failed: {}", e);
                // Raw bytes logged above for debugging
            }
        }
    }
    _ => {}
}

Check Transport Mode

use cerulion_core::prelude::*;

// For subscribers, check if local transport is available
let mut subscriber = Subscriber::create("topic", Some(true))?; // Network only

// Try to enable local transport
match subscriber.enable_local_subscriber(None) {
    Ok(()) => println!("Local transport enabled"),
    Err(e) => println!("Local transport not available: {}", e),
}

When to Check Logs

Check logs when:
  • Network communication isn’t working
  • Messages aren’t being received
  • Deserialization errors occur frequently
  • Performance issues are suspected
Network errors are logged but don’t propagate to the caller. Always check logs if network communication isn’t working as expected.

Next Steps