| Crates.io | actr-version |
| lib.rs | actr-version |
| version | 0.1.5 |
| created_at | 2025-11-09 08:33:24.012647+00 |
| updated_at | 2026-01-19 09:29:38.717954+00 |
| description | Protocol compatibility analysis library using semantic proto analysis |
| homepage | |
| repository | https://github.com/actor-rtc/actr-version |
| max_upload_size | |
| id | 1923810 |
| size | 117,361 |
๐ Semantic Protocol Compatibility Analysis Library
actr-version provides professional-grade protobuf compatibility analysis through proto-sign semantic breaking change detection and actr-protocol service structures, enabling comprehensive service version management.
This library solves the real problem of protocol compatibility analysis - not just comparing hashes, but understanding the semantic meaning of protobuf schema changes.
// Use proto-sign for true semantic analysis
let result = ServiceCompatibility::analyze_compatibility(&base_service, &candidate_service)?;
// Detects: field removal, type changes, backward compatibility, etc.
proto-signServiceSpec structures from actr-protocolServiceSpec built-in semantic fingerprintsAdd to your Cargo.toml:
[dependencies]
actr-version = { git = "https://github.com/actor-rtc/actr-version" }
actr-protocol = { git = "https://github.com/actor-rtc/actr-protocol" }
use actr_version::{ServiceCompatibility, CompatibilityLevel, Fingerprint, ProtoFile};
use actr_protocol::ServiceSpec;
// Create base service with proto content
let proto_files = vec![ProtoFile {
name: "user.proto".to_string(),
content: r#"
syntax = "proto3";
message User {
string name = 1;
string email = 2;
}
"#.to_string(),
path: None,
}];
let base_fingerprint = Fingerprint::calculate_service_semantic_fingerprint(&proto_files)?;
let base_service = ServiceSpec {
version: "1.0.0".to_string(),
description: Some("User management service".to_string()),
fingerprint: base_fingerprint,
protobufs: proto_files.into_iter().map(|pf| {
actr_protocol::service_spec::Protobuf {
uri: format!("actr://user-service/{}", pf.name),
content: pf.content,
fingerprint: "file_fp".to_string(),
}
}).collect(),
};
// Create candidate service with breaking change
let candidate_proto = vec![ProtoFile {
name: "user.proto".to_string(),
content: r#"
syntax = "proto3";
message User {
string name = 1;
// email field removed - this is a breaking change!
int32 age = 3; // new field added
}
"#.to_string(),
path: None,
}];
let candidate_fingerprint = Fingerprint::calculate_service_semantic_fingerprint(&candidate_proto)?;
let candidate_service = ServiceSpec {
version: "1.1.0".to_string(),
description: Some("User management service".to_string()),
fingerprint: candidate_fingerprint,
protobufs: candidate_proto.into_iter().map(|pf| {
actr_protocol::service_spec::Protobuf {
uri: format!("actr://user-service/{}", pf.name),
content: pf.content,
fingerprint: "file_fp".to_string(),
}
}).collect(),
};
// Execute semantic compatibility analysis
let result = ServiceCompatibility::analyze_compatibility(&base_service, &candidate_service)?;
match result.level {
CompatibilityLevel::FullyCompatible => {
println!("โ
No changes detected - safe to deploy");
},
CompatibilityLevel::BackwardCompatible => {
println!("โ ๏ธ Backward compatible changes - safe to upgrade");
for change in &result.changes {
println!(" - {}: {}", change.change_type, change.description);
}
},
CompatibilityLevel::BreakingChanges => {
println!("โ Breaking changes detected - coordinated upgrade required!");
for breaking_change in &result.breaking_changes {
println!(" - {}: {}", breaking_change.rule, breaking_change.message);
}
}
}
// Fingerprint calculation
Fingerprint::calculate_proto_semantic_fingerprint(content: &str) -> Result<String>
Fingerprint::calculate_service_semantic_fingerprint(files: &[ProtoFile]) -> Result<String>
// Compatibility analysis
ServiceCompatibility::analyze_compatibility(base: &ServiceSpec, candidate: &ServiceSpec)
-> Result<CompatibilityAnalysisResult>
ServiceCompatibility::has_breaking_changes(base: &ServiceSpec, candidate: &ServiceSpec)
-> Result<bool>
ServiceCompatibility::get_breaking_changes(base: &ServiceSpec, candidate: &ServiceSpec)
-> Result<Vec<BreakingChange>>
ServiceCompatibility::are_semantically_identical(base: &ServiceSpec, candidate: &ServiceSpec)
-> Result<bool>
The library has 95%+ test coverage with comprehensive tests for:
cargo test
Apache-2.0 License - see LICENSE file