gistools/readers/osm/info.rs
1use super::primitive::PrimitiveBlock;
2use alloc::{
3 string::{String, ToString},
4 vec,
5 vec::Vec,
6};
7use pbf::{ProtoRead, Protobuf};
8use serde::{Deserialize, Serialize};
9
10/// Info Block - decoded into an object
11#[derive(Debug, Default, Clone, Serialize, Deserialize, PartialEq)]
12pub struct InfoBlock {
13 /// The version of the object. Default is -1
14 pub version: i32,
15 /// (millisec_stamp = time_stamp*dateGranularity.)
16 pub time_stamp: Option<i64>,
17 /// The changeset id
18 pub changeset: Option<i64>,
19 /// The uid
20 pub uid: Option<i32>,
21 /// String IDs for usernames. Pull string from local Primitive Block
22 pub user_sid: Option<String>,
23 /// The visible flag is used to store history information. It indicates that
24 /// the current object version has been created by a delete operation on the
25 /// OSM API.
26 /// When a writer sets this flag, it MUST add a required_features tag with
27 /// value "HistoricalInformation" to the HeaderBlock.
28 /// If this flag is not available for some object it MUST be assumed to be
29 /// true if the file has the required_features tag "HistoricalInformation"
30 /// set.
31 pub visible: bool, // default true
32}
33
34/// Optional metadata that may be included into each primitive.
35#[derive(Debug, Clone, PartialEq)]
36pub struct Info {
37 /// The version of the object. Default is -1
38 pub version: i32,
39 /// (millisec_stamp = time_stamp*dateGranularity.)
40 pub time_stamp: Option<i64>,
41 /// The changeset id
42 pub changeset: Option<i64>,
43 /// The uid
44 pub uid: Option<i32>,
45 /// String IDs for usernames. Pull string from local Primitive Block
46 pub user_sid: Option<u32>,
47 /// The visible flag is used to store history information. It indicates that
48 /// the current object version has been created by a delete operation on the
49 /// OSM API.
50 /// When a writer sets this flag, it MUST add a required_features tag with
51 /// value "HistoricalInformation" to the HeaderBlock.
52 /// If this flag is not available for some object it MUST be assumed to be
53 /// true if the file has the required_features tag "HistoricalInformation"
54 /// set.
55 pub visible: bool, // default true
56}
57impl Default for Info {
58 fn default() -> Self {
59 Self {
60 version: -1,
61 time_stamp: None,
62 changeset: None,
63 uid: None,
64 user_sid: None,
65 visible: true,
66 }
67 }
68}
69impl Info {
70 /// Converts the Info object to an InfoBlock with the injected correct time stamp and user name
71 pub fn to_block(&self, pb: &PrimitiveBlock) -> InfoBlock {
72 InfoBlock {
73 version: self.version,
74 time_stamp: self.time_stamp.map(|ts| ts * pb.date_granularity as i64),
75 changeset: self.changeset,
76 uid: self.uid,
77 user_sid: self.user_sid.map(|sid| pb.get_string(sid as usize).to_string()),
78 visible: self.visible,
79 }
80 }
81}
82/// Read in the contents of the Info block
83impl ProtoRead for Info {
84 fn read(&mut self, tag: u64, pb: &mut Protobuf) {
85 match tag {
86 1 => self.version = pb.read_s_varint(),
87 2 => self.time_stamp = Some(pb.read_s_varint()),
88 3 => self.changeset = Some(pb.read_s_varint()),
89 4 => self.uid = Some(pb.read_s_varint()),
90 5 => self.user_sid = Some(pb.read_varint()),
91 6 => self.visible = pb.read_varint(),
92 _ => panic!("unknown tag {}", tag),
93 }
94 }
95}
96
97/// DenseInfo
98#[derive(Debug, Default, Clone, PartialEq)]
99pub struct DenseInfo {
100 version: Vec<i32>,
101 time_stamp: Vec<i64>, // DELTA coded (millisec_stamp = time_stamp*dateGranularity.)
102 changeset: Vec<i64>,
103 uid: Vec<i32>, // DELTA coded
104 user_sid: Vec<u32>, // String IDs for usernames. DELTA coded
105 // The visible flag is used to store history information. It indicates that
106 // the current object version has been created by a delete operation on the
107 // OSM API.
108 // When a writer sets this flag, it MUST add a required_features tag with
109 // value "HistoricalInformation" to the HeaderBlock.
110 // If this flag is not available for some object it MUST be assumed to be
111 // true if the file has the required_features tag "HistoricalInformation"
112 // set.
113 visible: Vec<bool>,
114}
115/// Read in the contents of the Dense Info block
116impl ProtoRead for DenseInfo {
117 fn read(&mut self, tag: u64, pb: &mut Protobuf) {
118 match tag {
119 1 => self.version = pb.read_s_packed(),
120 2 => self.time_stamp = pb.read_s_packed(),
121 3 => self.changeset = pb.read_s_packed(),
122 4 => self.uid = pb.read_s_packed(),
123 5 => self.user_sid = pb.read_packed(),
124 6 => self.visible = pb.read_packed(),
125 _ => panic!("unknown tag {}", tag),
126 }
127 }
128}
129impl DenseInfo {
130 /// Get the info objects
131 pub fn infos(&self) -> Vec<Info> {
132 let mut res: Vec<Info> = vec![];
133 let mut cur_time_stamp = 0;
134 let mut cur_uid = 0;
135 for i in 0..self.version.len() {
136 cur_time_stamp += self.time_stamp[i];
137 cur_uid += self.uid[i];
138 res.push(Info {
139 version: self.version[i],
140 time_stamp: Some(cur_time_stamp),
141 changeset: Some(self.changeset[i]),
142 uid: Some(cur_uid),
143 user_sid: self.user_sid.get(i).copied(),
144 visible: self.visible.get(i).copied().unwrap_or(true),
145 });
146 }
147 res
148 }
149}