Add display - #569
Conversation
nbuffon
left a comment
There was a problem hiding this comment.
I really wonder why theses "examples" are barely using libits, and mostly rewriting parsing and data manipulation functions.
What's the rational behind not using the messages' structures through Message to access the values they carry for example ?
| let po_qk2 = quadtree::lat_lon_to_quadkey(po_lat2, po_lon2, 26); | ||
| eprintln!("PO2 zoom 26: {} ({}, {})", po_qk2, po_lat2, po_lon2); | ||
| } | ||
| } |
There was a problem hiding this comment.
There is no mod.rs anywhere in the project, as recommended by the Rust doc
Prior to rustc 1.30, using mod.rs files was the way to load a module with nested children. It is encouraged to use the new naming convention as it is more consistent, and avoids having many files named mod.rs within a project.
Please stick to quadtree.rs
| if number_of_slash > 0 && ((number_of_slash * 2) + 1 == s.len()) { | ||
| if number_of_slash > 0 { | ||
| if (number_of_slash * 2) + 1 != s.len() { | ||
| return Err(ParseError::InvalidTileChar('/')); |
There was a problem hiding this comment.
Shouldn't we use a dedicated error for this ?
If I understand it correctly it just checks that you don't have two consecutive / or that it does not start or end with a / and not that an invalid char was found (valid characters being [0,1,2,3,/]).
Something like ParseError::MalformedSequence or MalformedQuadKey might be more relevant.
Note that just comparing the number of / might consider typo as valid (0//01 or /01/1)
| } | ||
| } | ||
| } | ||
|
|
There was a problem hiding this comment.
Why not
impl TryFrom<char> for Tile {
type Error = ParseError;
fn try_from(tile: char) -> Result<Self, Self::Error> {
...
}
}| _ => panic!("Unable to convert the char {tile} as a Tile"), | ||
| } | ||
| Tile::try_from_char(tile) | ||
| .unwrap_or_else(|_| panic!("Unable to convert the char {tile} as a Tile")) |
There was a problem hiding this comment.
You can .expect("message"), it will panic with the provided message in case of error
| struct LogEntry { | ||
| #[serde(rename = "type", alias = "message_type")] | ||
| message_type: String, | ||
| message: Option<Value>, |
There was a problem hiding this comment.
What is the reason of not using the SDK's types and functions but re-parsing the JSON and checking types and all ?
Using Message/Content/Mobile and even by "casting" to the correct type you should be able to achieve the same thing (without having to redefine everything).
match log_entry.message {
Message::CAM(cam) => {
...| // (e.g. [mobility]) that a display-only config does not provide. | ||
| let mqtt_properties = ini | ||
| .section(Some(MQTT_SECTION)) | ||
| .unwrap_or_else(|| panic!("Missing [{}] section in {}", MQTT_SECTION, config_path)); |
There was a problem hiding this comment.
Use expect(...), it will panic for you
| /// Extracts the message type from an MQTT topic. | ||
| /// Topic format: {context}/outQueue/v2x/{msgtype}/+/{quadkey_path} | ||
| /// or simpler: just look for known message types in the topic segments. | ||
| fn extract_message_type_from_topic(topic: &str) -> String { |
| }; | ||
| let year = if month <= 2 { year + 1 } else { year }; | ||
| format!("{:04}-{:02}-{:02}", year, month, day) | ||
| } |
|
|
||
| if !Path::new(&db_path).exists() { | ||
| eprintln!("❌ Database not found: {}", db_path); | ||
| eprintln!(" Run 'display_log_reader' or 'display_mqtt_reader' first."); |
There was a problem hiding this comment.
I use an ensure! instead...
| * Authors: see CONTRIBUTORS.md | ||
| */ | ||
|
|
||
| #![allow(dead_code)] |
There was a problem hiding this comment.
database.rs contains elements used by the server and not by the log reader, so it throws warnings. It's ugly, I try to dispath database functions not used by the 23 example bins (server, file, mqtt) differently...
991eb17 to
908396d
Compare
Signed-off-by: Frédéric Gardes <frederic.gardes@orange.com>
Precise the minor versions of dependencies. Remove useless dev dependency. Signed-off-by: Frédéric Gardes <frederic.gardes@orange.com>
Signed-off-by: Frédéric Gardes <frederic.gardes@orange.com>
Add comments on Rust elements. Provide a coordinate / tile converter Factorize caracter conversion. Use a Result to manage the slashes. Use "quadkey" everywhere (no "quad_key"). Add position_confidence() to Mobile trait with default implementation. Implement position_confidence() in CAM, DENM, CPM, CAM113. Add confidence_mean() to PositionConfidenceEllipse (v2.x and v1.1.3). Declare the 3 examples. Signed-off-by: Frédéric Gardes <frederic.gardes@orange.com>
Add a log parser, a mqtt client and a web server. Describe the database. Provide the configuration file. Signed-off-by: Frédéric Gardes <frederic.gardes@orange.com>
Changes
Close #568
Close #369
Test
How to test
Select the date (DAY) 2026-07-22. You should see 1 CAM and 1 CPM with 1 PO (3 messages).
docker run -it --rm eclipse-mosquitto mosquitto_pub -h test.mosquitto.org -p 8886 -t default/outQueue/v2x/cam/car_002/1/2/0/2/2/2/0/3/0/2/2/2/2/1/3/1/3/3/3/3/1/1/3/3/2/2 --tls-version tlsv1.2 --capath /etc/ssl/certs/ -m '{"message_type":"cam","origin":"self","version":"2.4.0","source_uuid":"car_002","timestamp":1784727122142,"message":{"protocol_version":1,"station_id":666,"generation_delta_time":64291,"basic_container":{"station_type":5,"reference_position":{"latitude":436005000,"longitude":14501000,"position_confidence_ellipse":{"semi_major":10,"semi_minor":50,"semi_major_orientation":1},"altitude":{"value":14750,"confidence":1}}},"high_frequency_container":{"basic_vehicle_container_high_frequency":{"heading":{"value":1800,"confidence":2},"speed":{"value":144,"confidence":3},"drive_direction":0,"vehicle_length":{"value":40,"confidence":0},"vehicle_width":20,"longitudinal_acceleration":{"value":10,"confidence":2},"curvature":{"value":11,"confidence":4},"curvature_calculation_mode":0,"yaw_rate":{"value":562,"confidence":2}}}}}' docker run -it --rm eclipse-mosquitto mosquitto_pub -h test.mosquitto.org -p 8886 -t default/outQueue/v2x/cpm/car_002/1/2/0/2/2/2/0/3/0/2/2/2/2/1/3/1/3/3/3/3/1/1/3/3/2/2 --tls-version tlsv1.2 --capath /etc/ssl/certs/ -m '{"type":"cpm","origin":"self","version":"2.2.0","source_uuid":"car_002","timestamp":1784727122143,"message":{"protocol_version":1,"station_id":666,"management_container":{"reference_position":{"latitude":436005000,"longitude":14501000,"position_confidence_ellipse":{"semi_major":10,"semi_minor":50,"semi_major_orientation":1},"altitude":{"value":14750,"confidence":1}}},"perceived_object_container":[{"object_id":1,"position":{"x_coordinate":{"value":500},"y_coordinate":{"value":-200},"confidence":{"position_confidence_ellipse":{"semi_major_confidence":20,"semi_minor_confidence":30,"semi_major_orientation":1}}}}]}}'NB: if a huge traffic is on the broker, you may retry to be served.
Refresh the map - you should now see 2 CAMs and 2 CPMs with 1 PO at different locations (6 messages).