Files
telepathy-padfoot/src/padfoot/channel/messages.rs

130 lines
4.1 KiB
Rust

use crate::padfoot::{convert_msg, DbusAction, VarArg};
use crate::telepathy;
use dbus::message::SignalArgs;
use dbus::tree::MethodErr;
use dc::constants::Viewtype;
use dc::message::{Message, MessageState};
use deltachat as dc;
use std::collections::HashMap;
use super::{Channel, Result};
impl AsRef<dyn telepathy::ChannelInterfaceMessages + 'static> for std::sync::Arc<Channel> {
fn as_ref(&self) -> &(dyn telepathy::ChannelInterfaceMessages + 'static) {
&**self
}
}
impl telepathy::ChannelInterfaceMessages for Channel {
fn send_message(&self, parts: Vec<HashMap<&str, VarArg>>, flags: u32) -> Result<String> {
println!("Channel::send_message({:?}, {})", parts, flags);
if parts.len() != 2 {
return Err(MethodErr::no_arg());
}
let _meta = &parts[0];
let content = &parts[1];
let content_type = content["content-type"].0.as_str().unwrap();
if content_type != "text/plain" {
println!("FIXME: can only send text/plain messages right now");
return Err(MethodErr::no_arg());
}
let text_opt = content["content"].0.as_str().map(|s| s.to_string());
let mut delta_msg = Message::new(Viewtype::Text); // FIXME: this won't always be plaintext
delta_msg.set_text(text_opt.clone());
let ctx = self.ctx.read().unwrap();
let msg_id = match dc::chat::send_msg(&ctx, self.chat_id, &mut delta_msg) {
Ok(msg_id) => msg_id,
Err(e) => {
println!(" Failed to send message: {}", e);
return Err(MethodErr::no_arg());
}
};
let token = format!("{}", msg_id.to_u32());
let dbus_parts = convert_msg(&delta_msg);
let messages_sig = telepathy::ChannelInterfaceMessagesMessageSent {
content: dbus_parts,
flags: 0,
message_token: token.clone(),
}
.to_emit_message(&self.path());
let text_sig = telepathy::ChannelTypeTextSent {
timestamp: delta_msg.get_timestamp() as u32,
type_: 0,
text: text_opt.or_else(|| Some("".to_string())).unwrap(),
}
.to_emit_message(&self.path());
self.actq.send(DbusAction::Signal(messages_sig)).unwrap();
self.actq.send(DbusAction::Signal(text_sig)).unwrap();
Ok(token)
}
fn get_pending_message_content(
&self,
message_id: u32,
parts: Vec<u32>,
) -> Result<HashMap<u32, VarArg>> {
println!(
"Channel::get_pending_message_content({}, {:?})",
message_id, parts
);
Err(MethodErr::no_arg())
}
fn supported_content_types(&self) -> Result<Vec<String>> {
println!("Channel::supported_content_types()");
Ok(vec!["text/plain".to_string()]) // TODO: image support
}
fn message_types(&self) -> Result<Vec<u32>> {
println!("Channel::message_types()");
Ok(vec![0]) // Normal messages. FIXME: MDNs too
}
fn message_part_support_flags(&self) -> Result<u32> {
println!("Channel::message_part_support_flags()");
Ok(0) // FIXME: support multipart messages
}
// Return value is an array of array of message parts
fn pending_messages(&self) -> Result<Vec<Vec<HashMap<String, VarArg>>>> {
println!("Channel::pending_messages()");
let mut out = Vec::<Vec<HashMap<String, VarArg>>>::new();
let ctx = self.ctx.read().unwrap();
for msg_id in dc::chat::get_chat_msgs(&ctx, self.chat_id, 0, None) {
if let Ok(msg) = dc::message::Message::load_from_db(&ctx, msg_id) {
match msg.get_state() {
MessageState::InFresh | MessageState::InNoticed => {
println!(" A message: {:?}", msg);
out.push(convert_msg(&msg))
}
_ => continue,
}
}
}
Ok(out) // FIXME: check for pending messages
}
fn delivery_reporting_support(&self) -> Result<u32> {
println!("Channel::delivery_reporting_support()");
Ok(0) // FIXME: MDNs
}
}