()
| 11 | |
| 12 | #[cfg(feature = "bindings")] |
| 13 | fn compile_protos() { |
| 14 | use std::path::{Path, PathBuf}; |
| 15 | let root = PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("protos"); |
| 16 | let descriptor_path = root.join("proto_descriptor.bin"); |
| 17 | println!("cargo:rerun-if-changed={}", descriptor_path.display()); |
| 18 | let descriptor_mtime = std::fs::metadata(&descriptor_path) |
| 19 | .map(|m| m.modified().unwrap()) |
| 20 | .unwrap_or(std::time::SystemTime::UNIX_EPOCH); |
| 21 | let mut run_protoc = false; |
| 22 | let proto_files = root |
| 23 | .read_dir() |
| 24 | .unwrap() |
| 25 | .filter_map(|e| { |
| 26 | let e = e.unwrap(); |
| 27 | let path = e.path(); |
| 28 | (path.extension() == Some(std::ffi::OsStr::new("proto"))).then_some(path) |
| 29 | }) |
| 30 | .collect::<Vec<_>>(); |
| 31 | for proto_file in &proto_files { |
| 32 | println!("cargo:rerun-if-changed={}", proto_file.display()); |
| 33 | let mtime = match std::fs::metadata(proto_file) { |
| 34 | Ok(m) => m.modified().unwrap(), |
| 35 | Err(e) => panic!("Failed to stat proto file {}: {:?}", proto_file.display(), e), |
| 36 | }; |
| 37 | if mtime > descriptor_mtime { |
| 38 | run_protoc = true; |
| 39 | } |
| 40 | } |
| 41 | |
| 42 | fn prost_config(descriptor_path: &Path, run_protoc: bool) -> prost_build::Config { |
| 43 | let mut config = prost_build::Config::new(); |
| 44 | config.file_descriptor_set_path(descriptor_path); |
| 45 | // If our cached descriptor is up-to-date, we don't need to run protoc. |
| 46 | // This is helpful so that users don't need to have protoc installed |
| 47 | // unless they're updating the protos. |
| 48 | if !run_protoc { |
| 49 | config.skip_protoc_run(); |
| 50 | } |
| 51 | config |
| 52 | } |
| 53 | if let Err(e) = |
| 54 | prost_config(&descriptor_path, run_protoc).compile_protos(&proto_files, &[root.as_path()]) |
| 55 | { |
| 56 | if e.kind() == std::io::ErrorKind::NotFound && e.to_string().contains("protoc") { |
| 57 | eprintln!("protoc not found, skipping protobuf compilation"); |
| 58 | prost_config(&descriptor_path, false) |
| 59 | .compile_protos(&proto_files, &[root.as_path()]) |
| 60 | .expect("Failed to compile protos"); |
| 61 | } else { |
| 62 | panic!("Failed to compile protos: {e:?}"); |
| 63 | } |
| 64 | } |
| 65 | |
| 66 | #[cfg(feature = "serde")] |
| 67 | { |
| 68 | let descriptor_set = std::fs::read(descriptor_path).expect("Failed to read descriptor set"); |
| 69 | pbjson_build::Builder::new() |
| 70 | .register_descriptors(&descriptor_set) |
no test coverage detected