Skip to content

Commit 8cbc9d0

Browse files
committed
Make self reporting into a setting
1 parent 8fb3a75 commit 8cbc9d0

File tree

5 files changed

+71
-13
lines changed

5 files changed

+71
-13
lines changed

deltachat-jsonrpc/src/api.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -361,9 +361,10 @@ impl CommandApi {
361361
Ok(BlobObject::create_and_deduplicate(&ctx, file, file)?.to_abs_path())
362362
}
363363

364+
/// Deprecated 2025-04. Use the "self_reporting" config instead.
364365
async fn draft_self_report(&self, account_id: u32) -> Result<u32> {
365366
let ctx = self.get_context(account_id).await?;
366-
Ok(ctx.draft_self_report().await?.to_u32())
367+
Ok(ctx.send_self_report().await?.to_u32())
367368
}
368369

369370
/// Sets the given configuration key.

src/config.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -428,6 +428,13 @@ pub enum Config {
428428
/// used for signatures, encryption to self and included in `Autocrypt` header.
429429
KeyId,
430430

431+
/// Send statistics to Delta Chat's developers.
432+
/// Can be exposed to the user as a setting.
433+
SelfReporting,
434+
435+
/// Last time statistics were sent to Delta Chat's developers
436+
LastSelfReportSent,
437+
431438
/// This key is sent to the self_reporting bot so that the bot can recognize the user
432439
/// without storing the email address
433440
SelfReportingId,

src/context.rs

Lines changed: 44 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,9 @@ use crate::download::DownloadState;
2828
use crate::events::{Event, EventEmitter, EventType, Events};
2929
use crate::imap::{FolderMeaning, Imap, ServerMetadata};
3030
use crate::key::{load_self_public_key, load_self_secret_key, DcKey as _};
31+
use crate::log::LogExt;
3132
use crate::login_param::{ConfiguredLoginParam, EnteredLoginParam};
32-
use crate::message::{self, Message, MessageState, MsgId};
33+
use crate::message::{self, Message, MessageState, MsgId, Viewtype};
3334
use crate::param::{Param, Params};
3435
use crate::peer_channels::Iroh;
3536
use crate::peerstate::Peerstate;
@@ -1032,6 +1033,18 @@ impl Context {
10321033
.await?
10331034
.to_string(),
10341035
);
1036+
res.insert(
1037+
"self_reporting",
1038+
self.get_config_bool(Config::SelfReporting)
1039+
.await?
1040+
.to_string(),
1041+
);
1042+
res.insert(
1043+
"last_self_report_sent",
1044+
self.get_config_i64(Config::LastSelfReportSent)
1045+
.await?
1046+
.to_string(),
1047+
);
10351048

10361049
let elapsed = time_elapsed(&self.creation_time);
10371050
res.insert("uptime", duration_to_str(elapsed));
@@ -1151,7 +1164,8 @@ impl Context {
11511164
Some(id) => id,
11521165
None => {
11531166
let id = create_id();
1154-
self.set_config(Config::SelfReportingId, Some(&id)).await?;
1167+
self.set_config_internal(Config::SelfReportingId, Some(&id))
1168+
.await?;
11551169
id
11561170
}
11571171
};
@@ -1165,7 +1179,15 @@ impl Context {
11651179
///
11661180
/// On the other end, a bot will receive the message and make it available
11671181
/// to Delta Chat's developers.
1168-
pub async fn draft_self_report(&self) -> Result<ChatId> {
1182+
pub async fn send_self_report(&self) -> Result<ChatId> {
1183+
info!(self, "Sending self report.");
1184+
// Setting `Config::LastHousekeeping` at the beginning avoids endless loops when things do not
1185+
// work out for whatever reason or are interrupted by the OS.
1186+
self.set_config_internal(Config::LastSelfReportSent, Some(&time().to_string()))
1187+
.await
1188+
.log_err(self)
1189+
.ok();
1190+
11691191
const SELF_REPORTING_BOT: &str = "self_reporting@testrun.org";
11701192

11711193
let contact_id = Contact::create(self, "Statistics bot", SELF_REPORTING_BOT).await?;
@@ -1196,9 +1218,26 @@ impl Context {
11961218
.set_protection(self, ProtectionStatus::Protected, time(), Some(contact_id))
11971219
.await?;
11981220

1199-
let mut msg = Message::new_text(self.get_self_report().await?);
1221+
let mut msg = Message::new(Viewtype::File);
1222+
msg.set_text(
1223+
"The attachment contains anonymous usage statistics, \
1224+
because you enabled this in the settings. \
1225+
This helps us improve the security of Delta Chat. \
1226+
See TODO[blog post] for more information."
1227+
.to_string(),
1228+
);
1229+
msg.set_file_from_bytes(
1230+
self,
1231+
"statistics.txt",
1232+
self.get_self_report().await?.as_bytes(),
1233+
Some("text/plain"),
1234+
)?;
12001235

1201-
chat_id.set_draft(self, Some(&mut msg)).await?;
1236+
crate::chat::send_msg(self, chat_id, &mut msg)
1237+
.await
1238+
.context("Failed to send self_reporting message")
1239+
.log_err(self)
1240+
.ok();
12021241

12031242
Ok(chat_id)
12041243
}

src/context/context_tests.rs

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -595,18 +595,15 @@ async fn test_get_next_msgs() -> Result<()> {
595595
async fn test_draft_self_report() -> Result<()> {
596596
let alice = TestContext::new_alice().await;
597597

598-
let chat_id = alice.draft_self_report().await?;
599-
let msg = get_chat_msg(&alice, chat_id, 0, 1).await;
598+
let chat_id = alice.send_self_report().await?;
599+
let msg = get_chat_msg(&alice, chat_id, 0, 2).await;
600600
assert_eq!(msg.get_info_type(), SystemMessage::ChatProtectionEnabled);
601601

602602
let chat = Chat::load_from_db(&alice, chat_id).await?;
603603
assert!(chat.is_protected());
604604

605-
let mut draft = chat_id.get_draft(&alice).await?.unwrap();
606-
assert!(draft.text.starts_with("core_version"));
607-
608-
// Test that sending into the protected chat works:
609-
let _sent = alice.send_msg(chat_id, &mut draft).await;
605+
let statistics_msg = get_chat_msg(&alice, chat_id, 1, 2).await;
606+
assert_eq!(statistics_msg.get_filename().unwrap(), "statistics.txt");
610607

611608
Ok(())
612609
}

src/scheduler.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -500,6 +500,20 @@ async fn inbox_fetch_idle(ctx: &Context, imap: &mut Imap, mut session: Session)
500500
}
501501
};
502502

503+
//#[cfg(target_os = "android")] TODO
504+
if ctx.get_config_bool(Config::SelfReporting).await? {
505+
match ctx.get_config_i64(Config::LastSelfReportSent).await {
506+
Ok(last_selfreport_time) => {
507+
let next_selfreport_time = last_selfreport_time.saturating_add(30); // TODO increase to 1 day or 1 week
508+
if next_selfreport_time <= time() {
509+
ctx.send_self_report().await?;
510+
}
511+
}
512+
Err(err) => {
513+
warn!(ctx, "Failed to get last self_reporting time: {}", err);
514+
}
515+
}
516+
}
503517
match ctx.get_config_bool(Config::FetchedExistingMsgs).await {
504518
Ok(fetched_existing_msgs) => {
505519
if !fetched_existing_msgs {

0 commit comments

Comments
 (0)