rkik-nts

Crates.iorkik-nts
lib.rsrkik-nts
version0.4.0
created_at2025-11-05 13:12:00.137234+00
updated_at2026-01-23 11:01:17.613317+00
descriptionHigh-level NTS (Network Time Security) Client library based on ntpd-rs
homepage
repositoryhttps://github.com/aguacero7/rkik-nts
max_upload_size
id1917973
size186,241
Aguacero 🌧️ (aguacero7)

documentation

README

rkik-nts

Crates.io Documentation

A high-level NTS (Network Time Security) Client library for Rust, based on ntpd-rs from the Pendulum Project.

This library provides a simple, safe, and ergonomic API for querying time from NTS-secured NTP servers. It handles the complexity of NTS key exchange and authenticated time synchronization, making it easy to integrate secure time synchronization into your applications.

Features

  • Secure: Full NTS (Network Time Security) support for authenticated time queries
  • Certificate Diagnostics: TLS certificate information capture for security auditing and diagnostics
  • TLS Debugging: SSLKEYLOGFILE support for Wireshark traffic analysis
  • Simple API: Easy-to-use client interface with sensible defaults
  • Async: Built on Tokio for efficient async I/O
  • Configurable: Flexible configuration options for advanced use cases
  • Battle-tested: Based on ntpd-rs from Project Pendulum
  • Integration-ready: Designed for seamless integration with rkik

Quick Start

Add to your Cargo.toml:

[dependencies]
rkik-nts = "0.4"
tokio = { version = "1", features = ["full"] }

Basic usage:

use rkik_nts::{NtsClient, NtsClientConfig};

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    // Create a client configuration
    let config = NtsClientConfig::new("time.cloudflare.com");

    // Create and connect the client
    let mut client = NtsClient::new(config);
    client.connect().await?;

    // Query the current time
    let time = client.get_time().await?;

    println!("Network time: {:?}", time.network_time);
    println!("Offset (ms): {} ms", time.offset_signed());
    println!("Authenticated: {}", time.authenticated);

    Ok(())
}

Examples

Simple Client

cargo run --example simple_client --features tracing-subscriber

End-to-End NTS Validation

cargo run --example nts_end_to_end --features tracing-subscriber

Certificate Information (New in v0.3.0)

Access TLS certificate information from the NTS-KE handshake:

use rkik_nts::{NtsClient, NtsClientConfig};

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    let config = NtsClientConfig::new("time.cloudflare.com");
    let mut client = NtsClient::new(config);
    client.connect().await?;

    // Access certificate information
    if let Some(ke_result) = client.nts_ke_info() {
        if let Some(cert) = &ke_result.certificate {
            println!("Certificate Subject: {}", cert.subject);
            println!("Certificate Issuer: {}", cert.issuer);
            println!("Valid from: {} to {}", cert.valid_from, cert.valid_until);
            println!("SHA-256 Fingerprint: {}", cert.fingerprint_sha256);
            println!("Self-signed: {}", cert.is_self_signed);
        }
    }

    Ok(())
}

Run the certificate example:

cargo run --example test_certificate --features tracing-subscriber

Custom Configuration

use rkik_nts::{NtsClient, NtsClientConfig};
use std::time::Duration;

let config = NtsClientConfig::new("time.cloudflare.com")
    .with_port(4460)
    .with_timeout(Duration::from_secs(5))
    .with_max_retries(3);

let mut client = NtsClient::new(config);
client.connect().await?;
let time = client.get_time().await?;

See the examples/ directory for more detailed examples.

Advanced Features

TLS Traffic Analysis with SSLKEYLOGFILE

For debugging and network analysis, you can capture TLS session keys for Wireshark decryption:

# Set environment variable to enable keylog
export SSLKEYLOGFILE=/tmp/sslkeylog.txt

# Run your application or example
cargo run --example test_certificate --features tracing-subscriber

# Use the keylog file in Wireshark:
# Edit → Preferences → Protocols → TLS → (Pre)-Master-Secret log filename

This allows you to decrypt and analyze the NTS-KE TLS traffic in Wireshark for troubleshooting.

Public NTS Servers

Here are some public NTS servers you can use for testing:

  • time.cloudflare.com - Cloudflare
  • nts.ntp.se - Netnod (Sweden)
  • ntppool1.time.nl - NLnet Labs (Netherlands)
  • time.txryan.com - Ryan Sleevi
  • nts.ntp.org.au - Australian NTP Pool

Integration with rkik

This library is designed for seamless integration with rkik, but can also be used as a standalone NTS client library. The API is intentionally kept simple and focused on the core functionality of NTS time synchronization.

Architecture

The library is structured into several modules:

  • client: High-level NTS client implementation
  • config: Configuration types and builders
  • error: Error types and result aliases
  • nts_ke: NTS Key Exchange protocol implementation
  • types: Common types (TimeSnapshot, NtsKeResult, etc.)

How NTS Works

Network Time Security (NTS) is a security extension for NTP that provides:

  1. Authentication: Cryptographic verification that time data comes from the expected server
  2. Encryption: Protection of time synchronization traffic
  3. Resistance to replay attacks: Each query uses unique authentication cookies

The protocol works in two phases:

  1. NTS-KE (Key Exchange): TLS connection to exchange keys and cookies
  2. NTP with NTS: UDP-based time queries using the negotiated keys

This library handles both phases transparently.

Requirements

  • Rust 1.70 or later
  • Tokio runtime

Development

# Build the library
cargo build

# Run tests
cargo test

# Run examples
cargo run --example simple_client --features tracing-subscriber

# Build documentation
cargo doc --open

See CONTRIBUTING.md for development guidelines.

Based on ntpd-rs

This library is built on top of ntpd-rs, a memory-safe NTP implementation developed by the Pendulum Project. The ntpd-rs project is maintained by Tweede golf and was originally funded by ISRG's Prossimo project.

Contributing

Contributions are welcome! Please see CONTRIBUTING.md for details.

Acknowledgments

Resources

Commit count: 31

cargo fmt