use relay_protocol::{Annotated, Empty, FromValue, IntoValue, Object, Value};
use crate::processor::ProcessValue;
use crate::protocol::LenientString;
#[derive(Clone, Debug, Default, PartialEq, Empty, FromValue, IntoValue, ProcessValue)]
pub struct AppContext {
#[metastructure(pii = "maybe")]
pub app_start_time: Annotated<String>,
#[metastructure(pii = "maybe")]
pub device_app_hash: Annotated<String>,
pub build_type: Annotated<String>,
pub app_identifier: Annotated<String>,
pub app_name: Annotated<String>,
pub app_version: Annotated<String>,
pub app_build: Annotated<LenientString>,
pub app_memory: Annotated<u64>,
pub in_foreground: Annotated<bool>,
#[metastructure(skip_serialization = "empty")]
pub view_names: Annotated<Vec<Annotated<String>>>,
#[metastructure(additional_properties, retain = "true", pii = "maybe")]
pub other: Object<Value>,
}
impl super::DefaultContext for AppContext {
fn default_key() -> &'static str {
"app"
}
fn from_context(context: super::Context) -> Option<Self> {
match context {
super::Context::App(c) => Some(*c),
_ => None,
}
}
fn cast(context: &super::Context) -> Option<&Self> {
match context {
super::Context::App(c) => Some(c),
_ => None,
}
}
fn cast_mut(context: &mut super::Context) -> Option<&mut Self> {
match context {
super::Context::App(c) => Some(c),
_ => None,
}
}
fn into_context(self) -> super::Context {
super::Context::App(Box::new(self))
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::protocol::Context;
#[test]
fn test_app_context_roundtrip() {
let json = r#"{
"app_start_time": "2018-02-08T22:21:57Z",
"device_app_hash": "4c793e3776474877ae30618378e9662a",
"build_type": "testflight",
"app_identifier": "foo.bar.baz",
"app_name": "Baz App",
"app_version": "1.0",
"app_build": "100001",
"app_memory": 22883948,
"in_foreground": true,
"view_names": [
"FooViewController",
"BarViewController"
],
"other": "value",
"type": "app"
}"#;
let context = Annotated::new(Context::App(Box::new(AppContext {
app_start_time: Annotated::new("2018-02-08T22:21:57Z".to_string()),
device_app_hash: Annotated::new("4c793e3776474877ae30618378e9662a".to_string()),
build_type: Annotated::new("testflight".to_string()),
app_identifier: Annotated::new("foo.bar.baz".to_string()),
app_name: Annotated::new("Baz App".to_string()),
app_version: Annotated::new("1.0".to_string()),
app_build: Annotated::new("100001".to_string().into()),
app_memory: Annotated::new(22883948),
in_foreground: Annotated::new(true),
view_names: Annotated::new(vec![
Annotated::new("FooViewController".to_string()),
Annotated::new("BarViewController".to_string()),
]),
other: {
let mut map = Object::new();
map.insert(
"other".to_string(),
Annotated::new(Value::String("value".to_string())),
);
map
},
})));
assert_eq!(context, Annotated::from_json(json).unwrap());
assert_eq!(json, context.to_json_pretty().unwrap());
}
}