aboutsummaryrefslogtreecommitdiff
path: root/src/message/signalproxy
diff options
context:
space:
mode:
Diffstat (limited to 'src/message/signalproxy')
-rw-r--r--src/message/signalproxy/initdata.rs8
-rw-r--r--src/message/signalproxy/initrequest.rs4
-rw-r--r--src/message/signalproxy/mod.rs3
-rw-r--r--src/message/signalproxy/objects/aliasmanager.rs156
-rw-r--r--src/message/signalproxy/objects/ircchannel.rs289
-rw-r--r--src/message/signalproxy/objects/ircuser.rs201
-rw-r--r--src/message/signalproxy/objects/mod.rs6
-rw-r--r--src/message/signalproxy/objects/network.rs369
-rw-r--r--src/message/signalproxy/objects/networkinfo.rs169
-rw-r--r--src/message/signalproxy/rpccall.rs4
-rw-r--r--src/message/signalproxy/syncmessage.rs12
-rw-r--r--src/message/signalproxy/translation/aos_soa.rs1134
-rw-r--r--src/message/signalproxy/translation/mod.rs6
13 files changed, 2319 insertions, 42 deletions
diff --git a/src/message/signalproxy/initdata.rs b/src/message/signalproxy/initdata.rs
index e4fb077..abeacad 100644
--- a/src/message/signalproxy/initdata.rs
+++ b/src/message/signalproxy/initdata.rs
@@ -14,8 +14,8 @@ impl Serialize for InitData {
let mut res = VariantList::new();
res.push(Variant::i32(MessageType::InitData as i32));
- res.push(Variant::StringUTF8(self.class_name.clone()));
- res.push(Variant::StringUTF8(self.object_name.clone()));
+ res.push(Variant::ByteArray(self.class_name.clone()));
+ res.push(Variant::ByteArray(self.object_name.clone()));
res.append(&mut self.init_data.clone());
@@ -32,8 +32,8 @@ impl Deserialize for InitData {
Ok((
size,
Self {
- class_name: match_variant!(res.remove(0), Variant::StringUTF8),
- object_name: match_variant!(res.remove(0), Variant::StringUTF8),
+ class_name: match_variant!(res.remove(0), Variant::ByteArray),
+ object_name: match_variant!(res.remove(0), Variant::ByteArray),
init_data: res,
},
))
diff --git a/src/message/signalproxy/initrequest.rs b/src/message/signalproxy/initrequest.rs
index 59eee2d..5190e0a 100644
--- a/src/message/signalproxy/initrequest.rs
+++ b/src/message/signalproxy/initrequest.rs
@@ -29,8 +29,8 @@ impl Deserialize for InitRequest {
Ok((
size,
Self {
- class_name: match_variant!(res.remove(0), Variant::StringUTF8),
- object_name: match_variant!(res.remove(0), Variant::StringUTF8),
+ class_name: match_variant!(res.remove(0), Variant::ByteArray),
+ object_name: match_variant!(res.remove(0), Variant::ByteArray),
},
))
}
diff --git a/src/message/signalproxy/mod.rs b/src/message/signalproxy/mod.rs
index 4e99fb0..9887af7 100644
--- a/src/message/signalproxy/mod.rs
+++ b/src/message/signalproxy/mod.rs
@@ -7,6 +7,9 @@ pub mod objects;
mod rpccall;
mod syncmessage;
+mod translation;
+pub use translation::*;
+
pub use heartbeat::*;
pub use initdata::*;
pub use initrequest::*;
diff --git a/src/message/signalproxy/objects/aliasmanager.rs b/src/message/signalproxy/objects/aliasmanager.rs
index 828caaa..b816778 100644
--- a/src/message/signalproxy/objects/aliasmanager.rs
+++ b/src/message/signalproxy/objects/aliasmanager.rs
@@ -1,4 +1,6 @@
-use crate::primitive::{Variant, VariantMap};
+use crate::primitive::{StringList, Variant, VariantList, VariantMap};
+
+use crate::message::signalproxy::Network;
#[derive(Clone, Debug, std::cmp::PartialEq)]
pub struct AliasManager {
@@ -11,36 +13,134 @@ pub struct Alias {
expansion: String,
}
-impl AliasManager {
- /// Client to Server
- ///
- /// Replaces all properties of the object with the content of the
- /// "properties" parameter. This parameter is in network representation.
- ///
- fn request_update(self: &mut Self, properties: VariantMap) {
- self.update(properties);
+impl Network for AliasManager {
+ type Item = VariantList;
+
+ fn to_network(&self) -> VariantList {
+ let mut res = VariantList::new();
+
+ res.push(Variant::ByteArray(s!("Aliases")));
+
+ let (names, expansions) = self.aliases.iter().fold(
+ (StringList::new(), StringList::new()),
+ |(mut names, mut expansions), alias| {
+ names.push(alias.name.clone());
+ expansions.push(alias.expansion.clone());
+ return (names, expansions);
+ },
+ );
+
+ let mut map = VariantMap::new();
+ map.insert(s!("names"), Variant::StringList(names));
+ map.insert(s!("expansions"), Variant::StringList(expansions));
+
+ res.push(Variant::VariantMap(map));
+
+ return res;
+ }
+
+ fn from_network(input: crate::primitive::VariantList) -> Self {
+ let input = match &input[1] {
+ Variant::VariantMap(input) => input,
+ _ => unimplemented!(),
+ };
+
+ let names = match_variant!(input.get("names").unwrap(), Variant::StringList);
+ let expansions = match_variant!(input.get("expansions").unwrap(), Variant::StringList);
+
+ AliasManager {
+ aliases: names
+ .iter()
+ .zip(expansions)
+ .map(|(name, expansion)| Alias {
+ name: name.clone(),
+ expansion,
+ })
+ .collect(),
+ }
+ }
+}
+
+#[cfg(test)]
+mod tests {
+ use super::*;
+
+ fn get_src() -> AliasManager {
+ AliasManager {
+ aliases: vec![
+ Alias {
+ name: s!("j"),
+ expansion: s!("/join $0"),
+ },
+ Alias {
+ name: s!("ns"),
+ expansion: s!("/msg nickserv $0"),
+ },
+ ],
+ }
+ }
+
+ fn get_dest() -> VariantList {
+ vec![
+ Variant::ByteArray(s!("Aliases")),
+ Variant::VariantMap(map! {
+ s!("names") => Variant::StringList(
+ vec![
+ s!("j"),
+ s!("ns"),
+ ],
+ ),
+ s!("expansions") => Variant::StringList(
+ vec![
+ s!("/join $0"),
+ s!("/msg nickserv $0"),
+ ],
+ ),
+ }),
+ ]
}
- /// Server to Client
- fn add_alias(self: &mut Self, name: String, expansion: String) {
- self.aliases.push(Alias { name, expansion });
+ #[test]
+ fn aliasmanager_to_network() {
+ assert_eq!(get_src().to_network(), get_dest())
}
- /// Server to Client
- ///
- /// Replaces all properties of the object with the content of the
- /// "properties" parameter. This parameter is in network representation.
- ///
- fn update(self: &mut Self, properties: VariantMap) {
- let mut alias: Vec<Alias> = Vec::new();
-
- // for (i, name) in match_variant!(properties[&"Aliases".to_string()], Variant::String) {
- // alias.push(Alias {
- // name,
- // expansion: match_variant!(properties["Aliases"], Variant::String)["expansions"][i],
- // })
- // }
-
- self.aliases = alias
+ #[test]
+ fn aliasmanager_from_network() {
+ assert_eq!(AliasManager::from_network(get_dest()), get_src())
}
}
+
+// impl AliasManager {
+// /// Client to Server
+// ///
+// /// Replaces all properties of the object with the content of the
+// /// "properties" parameter. This parameter is in network representation.
+// ///
+// fn request_update(self: &mut Self, properties: VariantMap) {
+// self.update(properties);
+// }
+
+// /// Server to Client
+// fn add_alias(self: &mut Self, name: String, expansion: String) {
+// self.aliases.push(Alias { name, expansion });
+// }
+
+// /// Server to Client
+// ///
+// /// Replaces all properties of the object with the content of the
+// /// "properties" parameter. This parameter is in network representation.
+// ///
+// fn update(self: &mut Self, properties: VariantMap) {
+// let mut alias: Vec<Alias> = Vec::new();
+
+// // for (i, name) in match_variant!(properties[&"Aliases".to_string()], Variant::String) {
+// // alias.push(Alias {
+// // name,
+// // expansion: match_variant!(properties["Aliases"], Variant::String)["expansions"][i],
+// // })
+// // }
+
+// self.aliases = alias
+// }
+// }
diff --git a/src/message/signalproxy/objects/ircchannel.rs b/src/message/signalproxy/objects/ircchannel.rs
new file mode 100644
index 0000000..cd5cd3e
--- /dev/null
+++ b/src/message/signalproxy/objects/ircchannel.rs
@@ -0,0 +1,289 @@
+use std::collections::HashMap;
+
+use crate::primitive::{StringList, Variant, VariantMap};
+
+#[allow(unused_imports)]
+use crate::message::signalproxy::Network;
+
+#[allow(dead_code)]
+#[derive(Debug, Clone, PartialEq)]
+pub struct IrcChannel {
+ channel_modes_a: HashMap<char, StringList>,
+ channel_modes_b: HashMap<char, String>,
+ channel_modes_c: HashMap<char, String>,
+ channel_modes_d: String,
+ user_modes: HashMap<String, String>,
+ name: String,
+ topic: String,
+ password: String,
+ encrypted: bool,
+}
+
+impl Network for IrcChannel {
+ type Item = VariantMap;
+
+ fn to_network(&self) -> Self::Item {
+ let mut res = VariantMap::new();
+
+ res.insert(
+ s!("ChanModes"),
+ Variant::VariantList({
+ let mut map = VariantMap::new();
+
+ map.insert(
+ s!("A"),
+ Variant::VariantMap(
+ self.channel_modes_a
+ .iter()
+ .map(|(k, v)| (k.to_string(), Variant::StringList(v.clone())))
+ .collect(),
+ ),
+ );
+ map.insert(
+ s!("B"),
+ Variant::VariantMap(
+ self.channel_modes_b
+ .iter()
+ .map(|(k, v)| (k.to_string(), Variant::String(v.clone())))
+ .collect(),
+ ),
+ );
+ map.insert(
+ s!("C"),
+ Variant::VariantMap(
+ self.channel_modes_c
+ .iter()
+ .map(|(k, v)| (k.to_string(), Variant::String(v.clone())))
+ .collect(),
+ ),
+ );
+ map.insert(s!("D"), Variant::String(self.channel_modes_d.clone()));
+
+ vec![Variant::VariantMap(map)]
+ }),
+ );
+
+ res.insert(
+ s!("UserModes"),
+ Variant::VariantList(vec![Variant::VariantMap(
+ self.user_modes
+ .iter()
+ .map(|(k, v)| (k.clone(), Variant::String(v.clone())))
+ .collect(),
+ )]),
+ );
+ res.insert(
+ s!("name"),
+ Variant::VariantList(vec![Variant::String(self.name.clone())]),
+ );
+ res.insert(
+ s!("topic"),
+ Variant::VariantList(vec![Variant::String(self.topic.clone())]),
+ );
+ res.insert(
+ s!("password"),
+ Variant::VariantList(vec![Variant::String(self.password.clone())]),
+ );
+ res.insert(
+ s!("encrypted"),
+ Variant::VariantList(vec![Variant::bool(self.encrypted.clone())]),
+ );
+
+ res
+ }
+ fn from_network(input: Self::Item) -> Self {
+ Self {
+ channel_modes_a: match_variant!(
+ match_variant!(
+ match_variant!(input.get("ChanModes").unwrap(), Variant::VariantList)[0],
+ Variant::VariantMap
+ )
+ .get("B")
+ .unwrap(),
+ Variant::VariantMap
+ )
+ .iter()
+ .map(|(k, v)| {
+ (
+ k.chars().nth(0).unwrap(),
+ match_variant!(v, Variant::StringList),
+ )
+ })
+ .collect(),
+ channel_modes_b: match_variant!(
+ match_variant!(
+ match_variant!(input.get("ChanModes").unwrap(), Variant::VariantList)[0],
+ Variant::VariantMap
+ )
+ .get("B")
+ .unwrap(),
+ Variant::VariantMap
+ )
+ .iter()
+ .map(|(k, v)| {
+ (
+ k.chars().nth(0).unwrap(),
+ match_variant!(v, Variant::String),
+ )
+ })
+ .collect(),
+ channel_modes_c: match_variant!(
+ match_variant!(
+ match_variant!(input.get("ChanModes").unwrap(), Variant::VariantList)[0],
+ Variant::VariantMap
+ )
+ .get("C")
+ .unwrap(),
+ Variant::VariantMap
+ )
+ .iter()
+ .map(|(k, v)| {
+ (
+ k.chars().nth(0).unwrap(),
+ match_variant!(v, Variant::String),
+ )
+ })
+ .collect(),
+ channel_modes_d: match_variant!(
+ match_variant!(
+ match_variant!(input.get("ChanModes").unwrap(), Variant::VariantList)[0],
+ Variant::VariantMap
+ )
+ .get("D")
+ .unwrap(),
+ Variant::String
+ ),
+ user_modes: match_variant!(
+ match_variant!(input.get("UserModes").unwrap(), Variant::VariantList)[0],
+ Variant::VariantMap
+ )
+ .iter()
+ .map(|(k, v)| (k.clone(), match_variant!(v, Variant::String)))
+ .collect(),
+ name: match_variant!(
+ match_variant!(input.get("name").unwrap(), Variant::VariantList)[0],
+ Variant::String
+ ),
+ topic: match_variant!(
+ match_variant!(input.get("topic").unwrap(), Variant::VariantList)[0],
+ Variant::String
+ ),
+ password: match_variant!(
+ match_variant!(input.get("password").unwrap(), Variant::VariantList)[0],
+ Variant::String
+ ),
+ encrypted: match_variant!(
+ match_variant!(input.get("encrypted").unwrap(), Variant::VariantList)[0],
+ Variant::bool
+ ),
+ }
+ }
+}
+
+#[cfg(test)]
+mod tests {
+ use super::*;
+
+ fn get_network() -> VariantMap {
+ VariantMap::from(map! {
+ s!("encrypted") => Variant::VariantList(
+ vec![
+ Variant::bool(
+ false,
+ ),
+ ],
+ ),
+ s!("topic") => Variant::VariantList(
+ vec![
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("password") => Variant::VariantList(
+ vec![
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("ChanModes") => Variant::VariantList(
+ vec![
+ Variant::VariantMap(map!
+ {
+ s!("B") => Variant::VariantMap(map!
+ {},
+ ),
+ s!("D") => Variant::String(
+ s!("tCnT"),
+ ),
+ s!("C") => Variant::VariantMap(map!
+ {
+ s!("j") => Variant::String(
+ s!("5:1"),
+ ),
+ s!("x") => Variant::String(
+ s!("10:5"),
+ ),
+ s!("f") => Variant::String(
+ s!("30:5"),
+ ),
+ s!("F") => Variant::String(
+ s!("5:60"),
+ ),
+ },
+ ),
+ s!("A") => Variant::VariantMap(map!
+ {},
+ ),
+ },
+ ),
+ ],
+ ),
+ s!("UserModes") => Variant::VariantList(
+ vec![
+ Variant::VariantMap(map!
+ {
+ s!("audron") => Variant::String(
+ s!("o"),
+ ),
+ s!("audron_") => Variant::String(
+ s!(""),
+ ),
+ },
+ ),
+ ],
+ ),
+ s!("name") => Variant::VariantList(
+ vec![
+ Variant::String(
+ s!("#audron-test"),
+ ),
+ ],
+ )
+ })
+ }
+ fn get_runtime() -> IrcChannel {
+ IrcChannel {
+ channel_modes_a: map! {},
+ channel_modes_b: map! {},
+ channel_modes_c: map! { 'j' => s!("5:1"), 'x' => s!("10:5"), 'f' => s!("30:5"), 'F' => s!("5:60") },
+ channel_modes_d: s!("tCnT"),
+ user_modes: map! { s!("audron") => s!("o"), s!("audron_") => s!("") },
+ name: s!("#audron-test"),
+ topic: s!(""),
+ password: s!(""),
+ encrypted: false,
+ }
+ }
+
+ #[test]
+ fn ircchannel_to_network() {
+ assert_eq!(get_runtime().to_network(), get_network())
+ }
+
+ #[test]
+ fn ircchannel_from_network() {
+ assert_eq!(IrcChannel::from_network(get_network()), get_runtime())
+ }
+}
diff --git a/src/message/signalproxy/objects/ircuser.rs b/src/message/signalproxy/objects/ircuser.rs
new file mode 100644
index 0000000..0ce597f
--- /dev/null
+++ b/src/message/signalproxy/objects/ircuser.rs
@@ -0,0 +1,201 @@
+use crate::primitive::{DateTime, StringList};
+
+#[allow(unused_imports)]
+use crate::message::signalproxy::Network;
+use libquassel_derive::Network;
+
+#[allow(dead_code)]
+#[derive(Debug, Clone, PartialEq, Network)]
+#[network(repr = "maplist")]
+pub struct IrcUser {
+ user: String,
+ host: String,
+ nick: String,
+ #[network(rename = "realName")]
+ real_name: String,
+ account: String,
+ away: bool,
+ #[network(rename = "awayMessage")]
+ away_message: String,
+ #[network(rename = "idleTime")]
+ idle_time: DateTime,
+ #[network(rename = "loginTime")]
+ login_time: DateTime,
+ server: String,
+ #[network(rename = "ircOperator")]
+ irc_operator: String,
+ #[network(rename = "lastAwayMessageTime")]
+ last_away_message_time: DateTime,
+ #[network(rename = "whoisServiceReply")]
+ whois_service_reply: String,
+ #[network(rename = "suserHost")]
+ suser_host: String,
+ encrypted: bool,
+ channels: StringList,
+ #[network(rename = "userModes")]
+ user_modes: String,
+}
+
+#[cfg(test)]
+mod tests {
+ use crate::primitive::{Variant, VariantMap};
+ use time::OffsetDateTime;
+
+ use super::*;
+
+ fn get_runtime() -> IrcUser {
+ IrcUser {
+ user: s!("NickServ"),
+ host: s!("services"),
+ nick: s!("NickServ"),
+ real_name: s!(""),
+ account: s!(""),
+ away: false,
+ away_message: s!(""),
+ idle_time: OffsetDateTime::unix_epoch(),
+ login_time: OffsetDateTime::unix_epoch(),
+ server: s!(""),
+ irc_operator: s!(""),
+ last_away_message_time: OffsetDateTime::unix_epoch(),
+ whois_service_reply: s!(""),
+ suser_host: s!(""),
+ encrypted: false,
+ channels: StringList::new(),
+ user_modes: s!(""),
+ }
+ }
+
+ fn get_network() -> VariantMap {
+ map! {
+ s!("suserHost") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("lastAwayMessageTime") => Variant::VariantList(vec!
+ [
+ Variant::DateTime(
+ OffsetDateTime::unix_epoch() ,
+ ),
+ ],
+ ),
+ s!("away") => Variant::VariantList(vec!
+ [
+ Variant::bool(
+ false,
+ ),
+ ],
+ ),
+ s!("ircOperator") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("account") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("loginTime") => Variant::VariantList(vec!
+ [
+ Variant::DateTime(
+ OffsetDateTime::unix_epoch()
+ ),
+ ],
+ ),
+ s!("userModes") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("host") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!("services"),
+ ),
+ ],
+ ),
+ s!("whoisServiceReply") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("channels") => Variant::VariantList(vec!
+ [
+ Variant::StringList(vec!
+ [],
+ ),
+ ],
+ ),
+ s!("realName") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("nick") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!("NickServ"),
+ ),
+ ],
+ ),
+ s!("idleTime") => Variant::VariantList(vec!
+ [
+ Variant::DateTime(
+ OffsetDateTime::unix_epoch()
+ ),
+ ],
+ ),
+ s!("encrypted") => Variant::VariantList(vec!
+ [
+ Variant::bool(
+ false,
+ ),
+ ],
+ ),
+ s!("awayMessage") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ s!("user") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!("NickServ"),
+ ),
+ ],
+ ),
+ s!("server") => Variant::VariantList(vec!
+ [
+ Variant::String(
+ s!(""),
+ ),
+ ],
+ ),
+ }
+ }
+
+ #[test]
+ fn ircuser_to_network() {
+ assert_eq!(get_runtime().to_network(), get_network())
+ }
+
+ #[test]
+ fn ircuser_from_network() {
+ assert_eq!(IrcUser::from_network(get_network()), get_runtime())
+ }
+}
diff --git a/src/message/signalproxy/objects/mod.rs b/src/message/signalproxy/objects/mod.rs
index a84f6fa..a313312 100644
--- a/src/message/signalproxy/objects/mod.rs
+++ b/src/message/signalproxy/objects/mod.rs
@@ -1,9 +1,15 @@
// mod aliasmanager;
// mod backlogmanager;
+mod aliasmanager;
mod buffersyncer;
mod identity;
+mod ircchannel;
+mod ircuser;
+mod network;
+mod networkinfo;
+pub use aliasmanager::*;
pub use buffersyncer::*;
pub use identity::*;
diff --git a/src/message/signalproxy/objects/network.rs b/src/message/signalproxy/objects/network.rs
new file mode 100644
index 0000000..cb1edd2
--- /dev/null
+++ b/src/message/signalproxy/objects/network.rs
@@ -0,0 +1,369 @@
+use crate::primitive::{StringList, Variant, VariantList, VariantMap};
+
+#[allow(unused_imports)]
+use libquassel_derive::Network;
+
+use std::collections::HashMap;
+
+use num_derive::{FromPrimitive, ToPrimitive};
+use num_traits::{FromPrimitive, ToPrimitive};
+
+use super::{ircchannel::IrcChannel, ircuser::IrcUser, networkinfo::NetworkInfo};
+
+#[derive(Debug, Clone)]
+pub struct Network {
+ my_nick: String,
+ latency: i32,
+ current_server: String,
+ is_connected: bool,
+ connection_state: ConnectionState,
+ // prefixes: Vec<char>,
+ // prefix_modes: Vec<char>,
+ // channel_modes: HashMap<ChannelModeType, Vec<char>>,
+ irc_users: HashMap<String, IrcUser>,
+ irc_channels: HashMap<String, IrcChannel>,
+ supports: HashMap<String, String>,
+ caps: HashMap<String, String>,
+ caps_enabled: Vec<String>,
+ network_info: NetworkInfo,
+}
+
+// impl crate::message::signalproxy::Network for Network {
+// type Item = VariantList;
+
+// fn to_network(&self) -> Self::Item {
+// let mut res = Self::Item::new();
+
+// res.push(Variant::ByteArray(s!("myNick")));
+// res.push(Variant::String(self.my_nick.clone()));
+// res.push(Variant::ByteArray(s!("latency")));
+// res.push(Variant::i32(self.latency));
+// res.push(Variant::ByteArray(s!("currentServer")));
+// res.push(Variant::String(self.current_server.clone()));
+// res.push(Variant::ByteArray(s!("isConnected")));
+// res.push(Variant::bool(self.is_connected));
+// res.push(Variant::ByteArray(s!("connectionState")));
+// res.push(Variant::i32(self.connection_state.clone() as i32));
+
+// res.push(Variant::ByteArray(s!("Supports")));
+// res.push(Variant::VariantMap(
+// self.supports
+// .iter()
+// .map(|(k, v)| (k.clone(), Variant::String(v.clone())))
+// .collect(),
+// ));
+
+// res.push(Variant::ByteArray(s!("Caps")));
+// res.push(Variant::VariantMap(
+// self.caps
+// .iter()
+// .map(|(k, v)| (k.clone(), Variant::String(v.clone())))
+// .collect(),
+// ));
+
+// res.push(Variant::ByteArray(s!("CapsEnabled")));
+// res.push(Variant::VariantList(
+// self.caps_enabled
+// .iter()
+// .map(|v| Variant::String(v.clone()))
+// .collect(),
+// ));
+
+// {
+// let mut map = VariantMap::new();
+
+// map.insert(
+// s!("Users"),
+// Variant::VariantMap(self.irc_users.iter().fold(
+// HashMap::new(),
+// |mut res, (_, v)| {
+// res.extend(v.to_network());
+
+// res
+// },
+// )),
+// );
+
+// let channels = self
+// .irc_channels
+// .iter()
+// .fold(HashMap::new(), |mut res, (_, v)| {
+// res.extend(v.to_network());
+
+// res
+// });
+
+// map.insert(s!("Channels"), Variant::VariantMap(channels));
+
+// res.push(Variant::ByteArray(s!("IrcUsersAndChannels")));
+// res.push(Variant::VariantMap(map));
+// }
+
+// res.extend(self.network_info.to_network());
+
+// res
+// }
+
+// fn from_network(input: Self::Item) -> Self {
+// let users_and_channels = match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("IrcUsersAndChannels")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::VariantMap
+// );
+
+// let res = Self {
+// my_nick: match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("myNick")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::String
+// ),
+// latency: match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("latency")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::i32
+// ),
+// current_server: match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("currentServer")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::String
+// ),
+// is_connected: match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("isConnected")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::bool
+// ),
+// connection_state: ConnectionState::from_i32(match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("connectionState")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::i32
+// ))
+// .unwrap(),
+// irc_users: match_variant!(
+// users_and_channels.get("Users").unwrap(),
+// Variant::VariantMap
+// )
+// .iter()
+// .map(|(k, v)| (k, IrcUser::from_network(v))),
+// irc_channels: match_variant!(
+// users_and_channels.get("Channels").unwrap(),
+// Variant::VariantMap
+// )
+// .iter()
+// .map(|(k, v)| (k, match_variant!(v, Variant::VariantList))),
+// supports: match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("Supports")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::VariantMap
+// )
+// .iter()
+// .map(|(k, v)| (k.clone(), match_variant!(v, Variant::String)))
+// .collect(),
+// caps: match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("Caps")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::VariantMap
+// )
+// .iter()
+// .map(|(k, v)| (k.clone(), match_variant!(v, Variant::String)))
+// .collect(),
+// caps_enabled: match_variant!(
+// input
+// .iter()
+// .nth(
+// input
+// .iter()
+// .position(|x| *x == Variant::ByteArray(s!("CapsEnabled")))
+// .unwrap()
+// )
+// .unwrap(),
+// Variant::VariantList
+// )
+// .iter()
+// .map(|v| match_variant!(v, Variant::String))
+// .collect(),
+// network_info: NetworkInfo::from_network(input),
+// };
+
+// todo!()
+// }
+// }
+
+#[allow(dead_code)]
+#[derive(Debug, Clone, PartialEq, Network)]
+#[network(repr = "map")]
+pub struct NetworkServer {
+ #[network(rename = "Host")]
+ pub host: String,
+ #[network(rename = "Port")]
+ pub port: u32,
+ #[network(rename = "Password")]
+ pub password: String,
+ #[network(rename = "UseSSL")]
+ pub use_ssl: bool,
+ #[network(rename = "sslVerify")]
+ pub ssl_verify: bool,
+ #[network(rename = "sslVersion")]
+ pub ssl_version: i32,
+ #[network(rename = "UseProxy")]
+ pub use_proxy: bool,
+ #[network(rename = "ProxyType")]
+ pub proxy_type: i32,
+ #[network(rename = "ProxyHost")]
+ pub proxy_host: String,
+ #[network(rename = "ProxyPort")]
+ pub proxy_port: u32,
+ #[network(rename = "ProxyUser")]
+ pub proxy_user: String,
+ #[network(rename = "ProxyPass")]
+ pub proxy_pass: String,
+}
+
+#[cfg(test)]
+mod tests {
+ use super::*;
+ use crate::message::signalproxy::translation::Network;
+
+ fn networkserver_get_network() -> VariantMap {
+ map! {
+ s!("ProxyHost") => Variant::String(
+ s!("localhost"),
+ ),
+ s!("sslVerify") => Variant::bool(
+ true,
+ ),
+ s!("UseSSL") => Variant::bool(
+ true,
+ ),
+ s!("Port") => Variant::u32(
+ 6697,
+ ),
+ s!("Password") => Variant::String(
+ s!(""),
+ ),
+ s!("ProxyType") => Variant::i32(
+ 1,
+ ),
+ s!("sslVersion") => Variant::i32(
+ 0,
+ ),
+ s!("ProxyUser") => Variant::String(
+ s!(""),
+ ),
+ s!("ProxyPass") => Variant::String(
+ s!(""),
+ ),
+ s!("Host") => Variant::String(
+ s!("irc.snoonet.org"),
+ ),
+ s!("ProxyPort") => Variant::u32(
+ 8080,
+ ),
+ s!("UseProxy") => Variant::bool(
+ false,
+ ),
+ }
+ }
+ fn networkserver_get_runtime() -> NetworkServer {
+ NetworkServer {
+ host: s!("irc.snoonet.org"),
+ port: 6697,
+ password: s!(""),
+ use_ssl: true,
+ ssl_verify: true,
+ ssl_version: 0,
+ use_proxy: false,
+ proxy_type: 1,
+ proxy_host: s!("localhost"),
+ proxy_port: 8080,
+ proxy_user: s!(""),
+ proxy_pass: s!(""),
+ }
+ }
+
+ #[test]
+ fn network_server_to_network() {
+ assert_eq!(
+ networkserver_get_runtime().to_network(),
+ networkserver_get_network()
+ )
+ }
+}
+
+#[allow(dead_code)]
+#[derive(Debug, Clone, PartialEq, FromPrimitive, ToPrimitive)]
+#[repr(C)]
+enum ConnectionState {
+ Disconnected = 0x00,
+ Connecting = 0x01,
+ Initializing = 0x02,
+ Initialized = 0x03,
+ Reconnecting = 0x04,
+ Disconnecting = 0x05,
+}
+
+#[allow(dead_code)]
+#[derive(Debug, Clone, PartialEq, FromPrimitive, ToPrimitive)]
+#[repr(C)]
+enum ChannelModeType {
+ NotAChanmode = 0x00,
+ AChanmode = 0x01,
+ BChanmode = 0x02,
+ CChanmode = 0x04,
+ DChanmode = 0x08,
+}
diff --git a/src/message/signalproxy/objects/networkinfo.rs b/src/message/signalproxy/objects/networkinfo.rs
new file mode 100644
index 0000000..a7f0a3c
--- /dev/null
+++ b/src/message/signalproxy/objects/networkinfo.rs
@@ -0,0 +1,169 @@
+use crate::primitive::{StringList, Variant};
+
+#[allow(unused_imports)]
+use libquassel_derive::Network;
+
+use crate::message::objects::network::NetworkServer;
+
+#[allow(dead_code)]
+#[derive(Debug, Clone, PartialEq, Network)]
+#[network(repr = "list")]
+pub struct NetworkInfo {
+ #[network(rename = "networkName")]
+ pub network_name: String,
+
+ #[network(
+ rename = "ServerList",
+ override_type = "VariantList",
+ to_map = "|server| Variant::VariantMap(server.to_network())",
+ from_map = "|server| NetworkServer::from_network(match_variant!(server, Variant::VariantMap))"
+ )]
+ pub server_list: Vec<NetworkServer>,
+ #[network(rename = "perform")]
+ pub perform: StringList,
+
+ #[network(rename = "autoIdentifyService")]
+ pub auto_identify_service: String,
+ #[network(rename = "autoIdentifyPassword")]
+ pub auto_identify_password: String,
+
+ #[network(rename = "saslAccount")]
+ pub sasl_account: String,
+ #[network(rename = "saslPassword")]
+ pub sasl_password: String,
+
+ // ByteArray
+ #[network(rename = "codecForServer", override_type = "ByteArray")]
+ pub codec_for_server: String,
+ #[network(rename = "codecForEncoding", override_type = "ByteArray")]
+ pub codec_for_encoding: String,
+ #[network(rename = "codecForDecoding", override_type = "ByteArray")]
+ pub codec_for_decoding: String,
+
+ // TODO add these type aliases or usertypes in variants
+ // pub network_id: NetworkId,
+ // pub identity_id: IdentityId,
+ #[network(rename = "msgRateBurstSize")]
+ pub msg_rate_burst_size: u32,
+ #[network(rename = "msgRateMessageDelay")]
+ pub msg_rate_message_delay: u32,
+
+ #[network(rename = "autoReconnectInterval")]
+ pub auto_reconnect_interval: u32,
+ #[network(rename = "autoReconnectRetries")]
+ pub auto_reconnect_retries: u16,
+
+ #[network(rename = "rejoinChannels")]
+ pub rejoin_channels: bool,
+ #[network(rename = "useRandomServer")]
+ pub use_random_server: bool,
+ #[network(rename = "useAutoIdentify")]
+ pub use_auto_identify: bool,
+ #[network(rename = "useSasl")]
+ pub use_sasl: bool,
+ #[network(rename = "useAutoReconnect")]
+ pub use_auto_reconnect: bool,
+ #[network(rename = "unlimitedReconnectRetries")]
+ pub unlimited_reconnect_retries: bool,
+ #[network(rename = "useCustomMessageRate")]
+ pub use_custom_message_rate: bool,
+ #[network(rename = "unlimitedMessageRate")]
+ pub unlimited_message_rate: bool,
+ // #[network(rename = "autoAwayActive")]
+ // pub auto_away_active: bool,
+}
+
+#[cfg(test)]
+mod tests {
+ use crate::{
+ message::objects::network::NetworkServer,
+ primitive::{Variant, VariantList},
+ };
+
+ use super::*;
+ use crate::message::signalproxy::translation::Network;
+
+ use pretty_assertions::{assert_eq, assert_ne};
+
+ fn get_network() -> VariantList {
+ vec![
+ Variant::ByteArray(s!("networkName")),
+ Variant::String(s!("snoonet")),
+ Variant::ByteArray(s!("ServerList")),
+ Variant::VariantList(vec![]),
+ Variant::ByteArray(s!("perform")),
+ Variant::StringList(vec![s!("")]),
+ Variant::ByteArray(s!("autoIdentifyService")),
+ Variant::String(s!("NickServ")),
+ Variant::ByteArray(s!("autoIdentifyPassword")),
+ Variant::String(s!("")),
+ Variant::ByteArray(s!("saslAccount")),
+ Variant::String(s!("")),
+ Variant::ByteArray(s!("saslPassword")),
+ Variant::String(s!("")),
+ Variant::ByteArray(s!("codecForServer")),
+ Variant::ByteArray(s!("")),
+ Variant::ByteArray(s!("codecForEncoding")),
+ Variant::ByteArray(s!("")),
+ Variant::ByteArray(s!("codecForDecoding")),
+ Variant::ByteArray(s!("")),
+ Variant::ByteArray(s!("msgRateBurstSize")),
+ Variant::u32(5),
+ Variant::ByteArray(s!("msgRateMessageDelay")),
+ Variant::u32(2200),
+ Variant::ByteArray(s!("autoReconnectInterval")),
+ Variant::u32(60),
+ Variant::ByteArray(s!("autoReconnectRetries")),
+ Variant::u16(20),
+ Variant::ByteArray(s!("rejoinChannels")),
+ Variant::bool(true),
+ Variant::ByteArray(s!("useRandomServer")),
+ Variant::bool(false),
+ Variant::ByteArray(s!("useAutoIdentify")),
+ Variant::bool(false),
+ Variant::ByteArray(s!("useSasl")),
+ Variant::bool(false),
+ Variant::ByteArray(s!("useAutoReconnect")),
+ Variant::bool(true),
+ Variant::ByteArray(s!("unlimitedReconnectRetries")),
+ Variant::bool(false),
+ Variant::ByteArray(s!("useCustomMessageRate")),
+ Variant::bool(false),
+ Variant::ByteArray(s!("unlimitedMessageRate")),
+ Variant::bool(false),
+ ]
+ }
+
+ fn get_runtime() -> NetworkInfo {
+ NetworkInfo {
+ network_name: s!("snoonet"),
+ server_list: vec![],
+ perform: vec![s!("")],
+ auto_identify_service: s!("NickServ"),
+ auto_identify_password: s!(""),
+ sasl_account: s!(""),
+ sasl_password: s!(""),
+ codec_for_server: s!(""),
+ codec_for_encoding: s!(""),
+ codec_for_decoding: s!(""),
+ msg_rate_burst_size: 5,
+ msg_rate_message_delay: 2200,
+ auto_reconnect_interval: 60,
+ auto_reconnect_retries: 20,
+ rejoin_channels: true,
+ use_random_server: false,
+ use_auto_identify: false,
+ use_sasl: false,
+ use_auto_reconnect: true,
+ unlimited_reconnect_retries: false,
+ use_custom_message_rate: false,
+ unlimited_message_rate: false,
+ // auto_away_active: (),
+ }
+ }
+
+ #[test]
+ fn networkinfo_to_network() {
+ assert_eq!(get_runtime().to_network(), get_network())
+ }
+}
diff --git a/src/message/signalproxy/rpccall.rs b/src/message/signalproxy/rpccall.rs
index 2eac86d..2755ea1 100644
--- a/src/message/signalproxy/rpccall.rs
+++ b/src/message/signalproxy/rpccall.rs
@@ -27,7 +27,7 @@ impl Serialize for RpcCall {
match self {
RpcCall::DisplayMessage(msg) => {
- res.push(Variant::StringUTF8("2displayMsg(Message)".to_string()));
+ res.push(Variant::ByteArray("2displayMsg(Message)".to_string()));
res.push(Variant::Message(msg.message.clone()));
}
}
@@ -42,7 +42,7 @@ impl Deserialize for RpcCall {
res.remove(0);
- let rpc = match_variant!(res.remove(0), Variant::StringUTF8);
+ let rpc = match_variant!(res.remove(0), Variant::ByteArray);
match rpc.as_str() {
"2displayMsg(Message)" => {
diff --git a/src/message/signalproxy/syncmessage.rs b/src/message/signalproxy/syncmessage.rs
index 737f3e0..b58659a 100644
--- a/src/message/signalproxy/syncmessage.rs
+++ b/src/message/signalproxy/syncmessage.rs
@@ -17,9 +17,9 @@ impl Serialize for SyncMessage {
let mut res = VariantList::new();
res.push(Variant::i32(MessageType::SyncMessage as i32));
- res.push(Variant::StringUTF8(self.class_name.clone()));
- res.push(Variant::StringUTF8(self.object_name.clone()));
- res.push(Variant::StringUTF8(self.slot_name.clone()));
+ res.push(Variant::ByteArray(self.class_name.clone()));
+ res.push(Variant::ByteArray(self.object_name.clone()));
+ res.push(Variant::ByteArray(self.slot_name.clone()));
res.append(&mut self.params.clone());
@@ -36,9 +36,9 @@ impl Deserialize for SyncMessage {
Ok((
size,
Self {
- class_name: match_variant!(res.remove(0), Variant::StringUTF8),
- object_name: match_variant!(res.remove(0), Variant::StringUTF8),
- slot_name: match_variant!(res.remove(0), Variant::StringUTF8),
+ class_name: match_variant!(res.remove(0), Variant::ByteArray),
+ object_name: match_variant!(res.remove(0), Variant::ByteArray),
+ slot_name: match_variant!(res.remove(0), Variant::ByteArray),
params: res,
},
))
diff --git a/src/message/signalproxy/translation/aos_soa.rs b/src/message/signalproxy/translation/aos_soa.rs
new file mode 100644
index 0000000..c070aea
--- /dev/null
+++ b/src/message/signalproxy/translation/aos_soa.rs
@@ -0,0 +1,1134 @@
+// InitData {
+// class_name: "AliasManager",
+// object_name: "",
+// init_data: [
+// Variant::ByteArray(
+// "Aliases",
+// ),
+// Variant::VariantMap(
+// {
+// "names": Variant::StringList(
+// [
+// "j",
+// "ns",
+// "nickserv",
+// "cs",
+// "chanserv",
+// "hs",
+// "hostserv",
+// "wii",
+// "back",
+// "inxi",
+// "sysinfo",
+// ],
+// ),
+// "expansions": Variant::StringList(
+// [
+// "/join $0",
+// "/msg nickserv $0",
+// "/msg nickserv $0",
+// "/msg chanserv $0",
+// "/msg chanserv $0",
+// "/msg hostserv $0",
+// "/msg hostserv $0",
+// "/whois $0 $0",
+// "/quote away",
+// "/exec inxi $0",
+// "/exec inxi -d",
+// ],
+// ),
+// },
+// ),
+// ],
+// },
+
+// InitData {
+// class_name: "Network",
+// object_name: "2",
+// init_data: [
+// ByteArray(
+// "Caps",
+// ),
+// VariantMap(
+// {
+// "message-tags": String(
+// "",
+// ),
+// "multi-prefix": String(
+// "",
+// ),
+// "echo-message": String(
+// "",
+// ),
+// "away-notify": String(
+// "",
+// ),
+// "inspircd.org/standard-replies": String(
+// "",
+// ),
+// "sasl": String(
+// "",
+// ),
+// "labeled-response": String(
+// "",
+// ),
+// "inspircd.org/poison": String(
+// "",
+// ),
+// "account-tag": String(
+// "",
+// ),
+// "userhost-in-names": String(
+// "",
+// ),
+// "account-notify": String(
+// "",
+// ),
+// "extended-join": String(
+// "",
+// ),
+// "server-time": String(
+// "",
+// ),
+// "chghost": String(
+// "",
+// ),
+// "setname": String(
+// "",
+// ),
+// "cap-notify": String(
+// "",
+// ),
+// "batch": String(
+// "",
+// ),
+// "sts": String(
+// "duration=15552000,preload",
+// ),
+// "invite-notify": String(
+// "",
+// ),
+// },
+// ),
+// ByteArray(
+// "CapsEnabled",
+// ),
+// VariantList(
+// [
+// String(
+// "account-notify",
+// ),
+// String(
+// "away-notify",
+// ),
+// String(
+// "cap-notify",
+// ),
+// String(
+// "chghost",
+// ),
+// String(
+// "extended-join",
+// ),
+// String(
+// "multi-prefix",
+// ),
+// String(
+// "userhost-in-names",
+// ),
+// ],
+// ),
+// ByteArray(
+// "IrcUsersAndChannels",
+// ),
+// VariantMap(
+// {
+// "Users": VariantMap(
+// {
+// "suserHost": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// ],
+// ),
+// "lastAwayMessageTime": VariantList(
+// [
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// ],
+// ),
+// "away": VariantList(
+// [
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// ],
+// ),
+// "ircOperator": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// ],
+// ),
+// "account": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "*",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "audron",
+// ),
+// ],
+// ),
+// "loginTime": VariantList(
+// [
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// ],
+// ),
+// "userModes": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "Iwxi",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// ],
+// ),
+// "host": VariantList(
+// [
+// String(
+// "services",
+// ),
+// String(
+// "irc-tar.hr0.2d7ge7.IP",
+// ),
+// String(
+// "services",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "user/audron",
+// ),
+// ],
+// ),
+// "whoisServiceReply": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// ],
+// ),
+// "channels": VariantList(
+// [
+// StringList(
+// [],
+// ),
+// StringList(
+// [
+// "#audron-test",
+// ],
+// ),
+// StringList(
+// [],
+// ),
+// StringList(
+// [],
+// ),
+// StringList(
+// [
+// "#audron-test",
+// ],
+// ),
+// ],
+// ),
+// "realName": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "Quassel IRC User",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "Max Audron <audron@cocaine.farm>",
+// ),
+// ],
+// ),
+// "nick": VariantList(
+// [
+// String(
+// "NickServ",
+// ),
+// String(
+// "audron_",
+// ),
+// String(
+// "Global",
+// ),
+// String(
+// "irc.snoonet.org",
+// ),
+// String(
+// "audron",
+// ),
+// ],
+// ),
+// "idleTime": VariantList(
+// [
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// DateTime(
+// OffsetDateTime {
+// utc_datetime: PrimitiveDateTime {
+// date: Date {
+// year: 1970,
+// ordinal: 1,
+// },
+// time: Time {
+// hour: 0,
+// minute: 0,
+// second: 0,
+// nanosecond: 0,
+// },
+// },
+// offset: UtcOffset {
+// seconds: 0,
+// },
+// },
+// ),
+// ],
+// ),
+// "encrypted": VariantList(
+// [
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// bool(
+// false,
+// ),
+// ],
+// ),
+// "awayMessage": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// ],
+// ),
+// "user": VariantList(
+// [
+// String(
+// "NickServ",
+// ),
+// String(
+// "quassel",
+// ),
+// String(
+// "Global",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "audron",
+// ),
+// ],
+// ),
+// "server": VariantList(
+// [
+// String(
+// "",
+// ),
+// String(
+// "irc.snoonet.org",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "",
+// ),
+// String(
+// "irc.snoonet.org",
+// ),
+// ],
+// ),
+// },
+// ),
+// "Channels": VariantMap(
+// {
+// "encrypted": VariantList(
+// [
+// bool(
+// false,
+// ),
+// ],
+// ),
+// "topic": VariantList(
+// [
+// String(
+// "",
+// ),
+// ],
+// ),
+// "password": VariantList(
+// [
+// String(
+// "",
+// ),
+// ],
+// ),
+// "ChanModes": VariantList(
+// [
+// VariantMap(
+// {
+// "B": VariantMap(
+// {},
+// ),
+// "D": String(
+// "tCnT",
+// ),
+// "C": VariantMap(
+// {
+// "j": String(
+// "5:1",
+// ),
+// "x": String(
+// "10:5",
+// ),
+// "f": String(
+// "30:5",
+// ),
+// "F": String(
+// "5:60",
+// ),
+// },
+// ),
+// "A": VariantMap(
+// {},
+// ),
+// },
+// ),
+// ],
+// ),
+// "UserModes": VariantList(
+// [
+// VariantMap(
+// {
+// "audron": String(
+// "o",
+// ),
+// "audron_": String(
+// "",
+// ),
+// },
+// ),
+// ],
+// ),
+// "name": VariantList(
+// [
+// String(
+// "#audron-test",
+// ),
+// ],
+// ),
+// },
+// ),
+// },
+// ),
+// ByteArray(
+// "ServerList",
+// ),
+// VariantList(
+// [
+// VariantMap(
+// {
+// "ProxyHost": String(
+// "localhost",
+// ),
+// "sslVerify": bool(
+// true,
+// ),
+// "UseSSL": bool(
+// true,
+// ),
+// "Port": u32(
+// 6697,
+// ),
+// "Password": String(
+// "",
+// ),
+// "ProxyType": i32(
+// 1,
+// ),
+// "sslVersion": i32(
+// 0,
+// ),
+// "ProxyUser": String(
+// "",
+// ),
+// "ProxyPass": String(
+// "",
+// ),
+// "Host": String(
+// "irc.snoonet.org",
+// ),
+// "ProxyPort": u32(
+// 8080,
+// ),
+// "UseProxy": bool(
+// false,
+// ),
+// },
+// ),
+// ],
+// ),
+// ByteArray(
+// "Supports",
+// ),
+// VariantMap(
+// {
+// "NAMESX": String(
+// "",
+// ),
+// "MAXTARGETS": String(
+// "20",
+// ),
+// "NICKLEN": String(
+// "27",
+// ),
+// "SILENCE": String(
+// "32",
+// ),
+// "PREFIX": String(
+// "(Yohv)!@%+",
+// ),
+// "TOPICLEN": String(
+// "307",
+// ),
+// "UHNAMES": String(
+// "",
+// ),
+// "STATUSMSG": String(
+// "!@%+",
+// ),
+// "SECURELIST": String(
+// "60",
+// ),
+// "ACCEPT": String(
+// "16",
+// ),
+// "CHANNELLEN": String(
+// "64",
+// ),
+// "KEYLEN": String(
+// "32",
+// ),
+// "EXTBAN": String(
+// ",ABCNOQRSTUacjmprsz",
+// ),
+// "CHANMODES": String(
+// "IXZbegw,k,FHJLWdfjlx,ABCDKMNOPQRSTcimnprstuz",
+// ),
+// "KICKLEN": String(
+// "255",
+// ),
+// "ESILENCE": String(
+// "CcdiNnPpTtx",
+// ),
+// "HOSTLEN": String(
+// "64",
+// ),
+// "CHANLIMIT": String(
+// "#:200",
+// ),
+// "USERMODES": String(
+// ",,s,BHILRSTWcdghikorwx",
+// ),
+// "CLIENTTAGDENY": String(
+// "*",
+// ),
+// "CHANTYPES": String(
+// "#",
+// ),
+// "NETWORK": String(
+// "Snoonet",
+// ),
+// "INVEX": String(
+// "I",
+// ),
+// "ELIST": String(
+// "CMNTU",
+// ),
+// "CALLERID": String(
+// "g",
+// ),
+// "BOT": String(
+// "B",
+// ),
+// "NAMELEN": String(
+// "128",
+// ),
+// "USERIP": String(
+// "",
+// ),
+// "MODES": String(
+// "50",
+// ),
+// "WATCH": String(
+// "30",
+// ),
+// "MAXLIST": String(
+// "I:1024,X:1024,b:1024,e:1024,g:1024,w:1024",
+// ),
+// "USERLEN": String(
+// "11",
+// ),
+// "CASEMAPPING": String(
+// "rfc1459",
+// ),
+// "REMOVE": String(
+// "",
+// ),
+// "LINELEN": String(
+// "512",
+// ),
+// "AWAYLEN": String(
+// "200",
+// ),
+// "EXCEPTS": String(
+// "e",
+// ),
+// "WHOX": String(
+// "",
+// ),
+// "SAFELIST": String(
+// "",
+// ),
+// },
+// ),
+// ByteArray(
+// "autoIdentifyPassword",
+// ),
+// String(
+// "",
+// ),
+// ByteArray(
+// "autoIdentifyService",
+// ),
+// String(
+// "NickServ",
+// ),
+// ByteArray(
+// "autoReconnectInterval",
+// ),
+// u32(
+// 60,
+// ),
+// ByteArray(
+// "autoReconnectRetries",
+// ),
+// u16(
+// 20,
+// ),
+// ByteArray(
+// "codecForDecoding",
+// ),
+// ByteArray(
+// "",
+// ),
+// ByteArray(
+// "codecForEncoding",
+// ),
+// ByteArray(
+// "",
+// ),
+// ByteArray(
+// "codecForServer",
+// ),
+// ByteArray(
+// "",
+// ),
+// ByteArray(
+// "connectionState",
+// ),
+// i32(
+// 3,
+// ),
+// ByteArray(
+// "currentServer",
+// ),
+// String(
+// "travincal.snoonet.org",
+// ),
+// ByteArray(
+// "identityId",
+// ),
+// i32(
+// 1,
+// ),
+// ByteArray(
+// "isConnected",
+// ),
+// bool(
+// true,
+// ),
+// ByteArray(
+// "latency",
+// ),
+// i32(
+// 13,
+// ),
+// ByteArray(
+// "msgRateBurstSize",
+// ),
+// u32(
+// 5,
+// ),
+// ByteArray(
+// "msgRateMessageDelay",
+// ),
+// u32(
+// 2200,
+// ),
+// ByteArray(
+// "myNick",
+// ),
+// String(
+// "audron_",
+// ),
+// ByteArray(
+// "networkName",
+// ),
+// String(
+// "snoonet",
+// ),
+// ByteArray(
+// "perform",
+// ),
+// StringList(
+// [
+// "",
+// ],
+// ),
+// ByteArray(
+// "rejoinChannels",
+// ),
+// bool(
+// true,
+// ),
+// ByteArray(
+// "saslAccount",
+// ),
+// String(
+// "",
+// ),
+// ByteArray(
+// "saslPassword",
+// ),
+// String(
+// "",
+// ),
+// ByteArray(
+// "unlimitedMessageRate",
+// ),
+// bool(
+// false,
+// ),
+// ByteArray(
+// "unlimitedReconnectRetries",
+// ),
+// bool(
+// false,
+// ),
+// ByteArray(
+// "useAutoIdentify",
+// ),
+// bool(
+// false,
+// ),
+// ByteArray(
+// "useAutoReconnect",
+// ),
+// bool(
+// true,
+// ),
+// ByteArray(
+// "useCustomMessageRate",
+// ),
+// bool(
+// false,
+// ),
+// ByteArray(
+// "useRandomServer",
+// ),
+// bool(
+// false,
+// ),
+// ByteArray(
+// "useSasl",
+// ),
+// bool(
+// false,
+// ),
+// ],
+// },
diff --git a/src/message/signalproxy/translation/mod.rs b/src/message/signalproxy/translation/mod.rs
new file mode 100644
index 0000000..bbb8b3f
--- /dev/null
+++ b/src/message/signalproxy/translation/mod.rs
@@ -0,0 +1,6 @@
+pub trait Network {
+ type Item;
+
+ fn to_network(&self) -> Self::Item;
+ fn from_network(input: Self::Item) -> Self;
+}