mirror of
https://github.com/chatmail/core.git
synced 2026-04-02 05:22:14 +03:00
Compare commits
2 Commits
v1.137.3
...
hpk-mimep3
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
828b4b4a8c | ||
|
|
f12893b87e |
@@ -1,7 +1,7 @@
|
||||
use std::ptr;
|
||||
|
||||
use itertools::join;
|
||||
use libc::{free, strcmp};
|
||||
use libc::strcmp;
|
||||
use mmime::clist::*;
|
||||
use mmime::mailimf::types::*;
|
||||
use mmime::mailmime::content::*;
|
||||
@@ -319,13 +319,8 @@ unsafe fn add_parts(
|
||||
let mut chat_id_blocked = Blocked::Not;
|
||||
let mut sort_timestamp = 0;
|
||||
let mut rcvd_timestamp = 0;
|
||||
let mut mime_in_reply_to = std::ptr::null_mut();
|
||||
let mut mime_references = std::ptr::null_mut();
|
||||
|
||||
let cleanup = |mime_in_reply_to: *mut libc::c_char, mime_references: *mut libc::c_char| {
|
||||
free(mime_in_reply_to.cast());
|
||||
free(mime_references.cast());
|
||||
};
|
||||
let mut mime_in_reply_to = String::new();
|
||||
let mut mime_references = String::new();
|
||||
|
||||
// collect the rest information, CC: is added to the to-list, BCC: is ignored
|
||||
// (we should not add BCC to groups as this would split groups. We could add them as "known contacts",
|
||||
@@ -359,7 +354,6 @@ unsafe fn add_parts(
|
||||
message::update_server_uid(context, &rfc724_mid, server_folder.as_ref(), server_uid);
|
||||
}
|
||||
|
||||
cleanup(mime_in_reply_to, mime_references);
|
||||
bail!("Message already in DB");
|
||||
}
|
||||
|
||||
@@ -588,20 +582,14 @@ unsafe fn add_parts(
|
||||
if let Some(field) = mime_parser.lookup_field_typ("In-Reply-To", MAILIMF_FIELD_IN_REPLY_TO) {
|
||||
let fld_in_reply_to = (*field).fld_data.fld_in_reply_to;
|
||||
if !fld_in_reply_to.is_null() {
|
||||
mime_in_reply_to = dc_str_from_clist(
|
||||
(*(*field).fld_data.fld_in_reply_to).mid_list,
|
||||
b" \x00" as *const u8 as *const libc::c_char,
|
||||
)
|
||||
mime_in_reply_to = dc_str_from_clist((*(*field).fld_data.fld_in_reply_to).mid_list, " ")
|
||||
}
|
||||
}
|
||||
|
||||
if let Some(field) = mime_parser.lookup_field_typ("References", MAILIMF_FIELD_REFERENCES) {
|
||||
let fld_references = (*field).fld_data.fld_references;
|
||||
if !fld_references.is_null() {
|
||||
mime_references = dc_str_from_clist(
|
||||
(*(*field).fld_data.fld_references).mid_list,
|
||||
b" \x00" as *const u8 as *const libc::c_char,
|
||||
)
|
||||
mime_references = dc_str_from_clist((*(*field).fld_data.fld_references).mid_list, " ")
|
||||
}
|
||||
}
|
||||
|
||||
@@ -612,97 +600,91 @@ unsafe fn add_parts(
|
||||
let icnt = mime_parser.parts.len();
|
||||
let mut txt_raw = None;
|
||||
|
||||
context
|
||||
.sql
|
||||
.prepare(
|
||||
"INSERT INTO msgs \
|
||||
(rfc724_mid, server_folder, server_uid, chat_id, from_id, to_id, timestamp, \
|
||||
timestamp_sent, timestamp_rcvd, type, state, msgrmsg, txt, txt_raw, param, \
|
||||
bytes, hidden, mime_headers, mime_in_reply_to, mime_references) \
|
||||
VALUES (?,?,?,?,?,?, ?,?,?,?,?,?, ?,?,?,?,?,?, ?,?);",
|
||||
|mut stmt, conn| {
|
||||
for i in 0..icnt {
|
||||
let part = &mut mime_parser.parts[i];
|
||||
if part.is_meta {
|
||||
continue;
|
||||
}
|
||||
context.sql.prepare(
|
||||
"INSERT INTO msgs \
|
||||
(rfc724_mid, server_folder, server_uid, chat_id, from_id, to_id, timestamp, \
|
||||
timestamp_sent, timestamp_rcvd, type, state, msgrmsg, txt, txt_raw, param, \
|
||||
bytes, hidden, mime_headers, mime_in_reply_to, mime_references) \
|
||||
VALUES (?,?,?,?,?,?, ?,?,?,?,?,?, ?,?,?,?,?,?, ?,?);",
|
||||
|mut stmt, conn| {
|
||||
for i in 0..icnt {
|
||||
let part = &mut mime_parser.parts[i];
|
||||
if part.is_meta {
|
||||
continue;
|
||||
}
|
||||
|
||||
if let Some(ref msg) = part.msg {
|
||||
if mime_parser.location_kml.is_some()
|
||||
&& icnt == 1
|
||||
&& (msg == "-location-" || msg.is_empty())
|
||||
{
|
||||
*hidden = 1;
|
||||
if state == MessageState::InFresh {
|
||||
state = MessageState::InNoticed;
|
||||
}
|
||||
if let Some(ref msg) = part.msg {
|
||||
if mime_parser.location_kml.is_some()
|
||||
&& icnt == 1
|
||||
&& (msg == "-location-" || msg.is_empty())
|
||||
{
|
||||
*hidden = 1;
|
||||
if state == MessageState::InFresh {
|
||||
state = MessageState::InNoticed;
|
||||
}
|
||||
}
|
||||
if part.typ == Viewtype::Text {
|
||||
let msg_raw = part.msg_raw.as_ref().cloned().unwrap_or_default();
|
||||
let subject = mime_parser
|
||||
.subject
|
||||
.as_ref()
|
||||
.map(|s| s.to_string())
|
||||
.unwrap_or("".into());
|
||||
txt_raw = Some(format!("{}\n\n{}", subject, msg_raw));
|
||||
}
|
||||
if mime_parser.is_system_message != SystemMessage::Unknown {
|
||||
part.param
|
||||
.set_int(Param::Cmd, mime_parser.is_system_message as i32);
|
||||
}
|
||||
|
||||
/*
|
||||
info!(
|
||||
context,
|
||||
"received mime message {:?}",
|
||||
String::from_utf8_lossy(std::slice::from_raw_parts(
|
||||
imf_raw_not_terminated as *const u8,
|
||||
imf_raw_bytes,
|
||||
))
|
||||
);
|
||||
*/
|
||||
|
||||
stmt.execute(params![
|
||||
rfc724_mid,
|
||||
server_folder.as_ref(),
|
||||
server_uid as libc::c_int,
|
||||
*chat_id as libc::c_int,
|
||||
*from_id as libc::c_int,
|
||||
*to_id as libc::c_int,
|
||||
sort_timestamp,
|
||||
*sent_timestamp,
|
||||
rcvd_timestamp,
|
||||
part.typ,
|
||||
state,
|
||||
msgrmsg,
|
||||
part.msg.as_ref().map_or("", String::as_str),
|
||||
// txt_raw might contain invalid utf8
|
||||
txt_raw.unwrap_or_default(),
|
||||
part.param.to_string(),
|
||||
part.bytes,
|
||||
*hidden,
|
||||
if save_mime_headers {
|
||||
Some(String::from_utf8_lossy(imf_raw))
|
||||
} else {
|
||||
None
|
||||
},
|
||||
to_string_lossy(mime_in_reply_to),
|
||||
to_string_lossy(mime_references),
|
||||
])?;
|
||||
|
||||
txt_raw = None;
|
||||
*insert_msg_id =
|
||||
sql::get_rowid_with_conn(context, conn, "msgs", "rfc724_mid", &rfc724_mid);
|
||||
created_db_entries.push((*chat_id as usize, *insert_msg_id as usize));
|
||||
}
|
||||
Ok(())
|
||||
},
|
||||
)
|
||||
.map_err(|err| {
|
||||
cleanup(mime_in_reply_to, mime_references);
|
||||
err
|
||||
})?;
|
||||
if part.typ == Viewtype::Text {
|
||||
let msg_raw = part.msg_raw.as_ref().cloned().unwrap_or_default();
|
||||
let subject = mime_parser
|
||||
.subject
|
||||
.as_ref()
|
||||
.map(|s| s.to_string())
|
||||
.unwrap_or("".into());
|
||||
txt_raw = Some(format!("{}\n\n{}", subject, msg_raw));
|
||||
}
|
||||
if mime_parser.is_system_message != SystemMessage::Unknown {
|
||||
part.param
|
||||
.set_int(Param::Cmd, mime_parser.is_system_message as i32);
|
||||
}
|
||||
|
||||
/*
|
||||
info!(
|
||||
context,
|
||||
"received mime message {:?}",
|
||||
String::from_utf8_lossy(std::slice::from_raw_parts(
|
||||
imf_raw_not_terminated as *const u8,
|
||||
imf_raw_bytes,
|
||||
))
|
||||
);
|
||||
*/
|
||||
|
||||
stmt.execute(params![
|
||||
rfc724_mid,
|
||||
server_folder.as_ref(),
|
||||
server_uid as libc::c_int,
|
||||
*chat_id as libc::c_int,
|
||||
*from_id as libc::c_int,
|
||||
*to_id as libc::c_int,
|
||||
sort_timestamp,
|
||||
*sent_timestamp,
|
||||
rcvd_timestamp,
|
||||
part.typ,
|
||||
state,
|
||||
msgrmsg,
|
||||
part.msg.as_ref().map_or("", String::as_str),
|
||||
// txt_raw might contain invalid utf8
|
||||
txt_raw.unwrap_or_default(),
|
||||
part.param.to_string(),
|
||||
part.bytes,
|
||||
*hidden,
|
||||
if save_mime_headers {
|
||||
Some(String::from_utf8_lossy(imf_raw))
|
||||
} else {
|
||||
None
|
||||
},
|
||||
mime_in_reply_to,
|
||||
mime_references,
|
||||
])?;
|
||||
|
||||
txt_raw = None;
|
||||
*insert_msg_id =
|
||||
sql::get_rowid_with_conn(context, conn, "msgs", "rfc724_mid", &rfc724_mid);
|
||||
created_db_entries.push((*chat_id as usize, *insert_msg_id as usize));
|
||||
}
|
||||
Ok(())
|
||||
},
|
||||
)?;
|
||||
|
||||
info!(
|
||||
context,
|
||||
@@ -722,8 +704,6 @@ unsafe fn add_parts(
|
||||
}
|
||||
}
|
||||
|
||||
cleanup(mime_in_reply_to, mime_references);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
||||
@@ -74,36 +74,18 @@ pub(crate) fn dc_truncate(buf: &str, approx_chars: usize, do_unwrap: bool) -> Co
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) unsafe fn dc_str_from_clist(
|
||||
list: *const clist,
|
||||
delimiter: *const libc::c_char,
|
||||
) -> *mut libc::c_char {
|
||||
pub(crate) fn dc_str_from_clist(list: *const clist, delimiter: &str) -> String {
|
||||
let mut res = String::new();
|
||||
|
||||
if !list.is_null() {
|
||||
let mut cur: *mut clistiter = (*list).first;
|
||||
while !cur.is_null() {
|
||||
let rfc724_mid = (if !cur.is_null() {
|
||||
(*cur).data
|
||||
} else {
|
||||
ptr::null_mut()
|
||||
}) as *const libc::c_char;
|
||||
|
||||
if !rfc724_mid.is_null() {
|
||||
if !res.is_empty() && !delimiter.is_null() {
|
||||
res += as_str(delimiter);
|
||||
}
|
||||
res += as_str(rfc724_mid);
|
||||
}
|
||||
cur = if !cur.is_null() {
|
||||
(*cur).next
|
||||
} else {
|
||||
ptr::null_mut()
|
||||
for rfc724_mid in unsafe { (*list).into_iter() } {
|
||||
if !res.is_empty() {
|
||||
res += delimiter;
|
||||
}
|
||||
res += as_str(rfc724_mid as *const libc::c_char);
|
||||
}
|
||||
}
|
||||
|
||||
res.strdup()
|
||||
res
|
||||
}
|
||||
|
||||
pub(crate) fn dc_str_to_clist(str: &str, delimiter: &str) -> *mut clist {
|
||||
@@ -1060,17 +1042,11 @@ mod tests {
|
||||
unsafe {
|
||||
let list: *mut clist = dc_str_to_clist("foo bar test", " ");
|
||||
assert_eq!((*list).count, 3);
|
||||
let str: *mut libc::c_char =
|
||||
dc_str_from_clist(list, b" \x00" as *const u8 as *const libc::c_char);
|
||||
|
||||
assert_eq!(
|
||||
CStr::from_ptr(str as *const libc::c_char).to_str().unwrap(),
|
||||
"foo bar test"
|
||||
);
|
||||
let str = dc_str_from_clist(list, " ");
|
||||
assert_eq!(str, "foo bar test");
|
||||
|
||||
clist_free_content(list);
|
||||
clist_free(list);
|
||||
free(str as *mut libc::c_void);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user