mirror of
https://github.com/chatmail/core.git
synced 2026-04-19 14:36:29 +03:00
feat: key-contacts
This change introduces a new type of contacts
identified by their public key fingerprint
rather than an e-mail address.
Encrypted chats now stay encrypted
and unencrypted chats stay unencrypted.
For example, 1:1 chats with key-contacts
are encrypted and 1:1 chats with address-contacts
are unencrypted.
Groups that have a group ID are encrypted
and can only contain key-contacts
while groups that don't have a group ID ("adhoc groups")
are unencrypted and can only contain address-contacts.
JSON-RPC API `reset_contact_encryption` is removed.
Python API `Contact.reset_encryption` is removed.
"Group tracking plugin" in legacy Python API was removed because it
relied on parsing email addresses from system messages with regexps.
Co-authored-by: Hocuri <hocuri@gmx.de>
Co-authored-by: iequidoo <dgreshilov@gmail.com>
Co-authored-by: B. Petersen <r10s@b44t.com>
This commit is contained in:
@@ -1,10 +1,8 @@
|
||||
use super::*;
|
||||
use crate::aheader::EncryptPreference;
|
||||
use crate::chat::{create_group_chat, ProtectionStatus};
|
||||
use crate::config::Config;
|
||||
use crate::key::DcKey;
|
||||
use crate::securejoin::get_securejoin_qr;
|
||||
use crate::test_utils::{alice_keypair, TestContext};
|
||||
use crate::test_utils::{TestContext, TestContextManager};
|
||||
|
||||
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||
async fn test_decode_http() -> Result<()> {
|
||||
@@ -212,7 +210,7 @@ async fn test_decode_smtp() -> Result<()> {
|
||||
|
||||
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||
async fn test_decode_ideltachat_link() -> Result<()> {
|
||||
let ctx = TestContext::new().await;
|
||||
let ctx = TestContext::new_alice().await;
|
||||
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
@@ -233,7 +231,7 @@ async fn test_decode_ideltachat_link() -> Result<()> {
|
||||
// see issue https://github.com/deltachat/deltachat-core-rust/issues/1969 for more info
|
||||
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||
async fn test_decode_openpgp_tolerance_for_issue_1969() -> Result<()> {
|
||||
let ctx = TestContext::new().await;
|
||||
let ctx = TestContext::new_alice().await;
|
||||
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
@@ -246,7 +244,7 @@ async fn test_decode_openpgp_tolerance_for_issue_1969() -> Result<()> {
|
||||
|
||||
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||
async fn test_decode_openpgp_group() -> Result<()> {
|
||||
let ctx = TestContext::new().await;
|
||||
let ctx = TestContext::new_alice().await;
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
"OPENPGP4FPR:79252762C34C5096AF57958F4FC3D21A81B0F0A7#a=cli%40deltachat.de&g=test%20%3F+test%20%21&x=h-0oKQf2CDK&i=9JEXlxAqGM0&s=0V7LzL9cxRL"
|
||||
@@ -264,7 +262,7 @@ async fn test_decode_openpgp_group() -> Result<()> {
|
||||
}
|
||||
|
||||
// Test it again with lowercased "openpgp4fpr:" uri scheme
|
||||
let ctx = TestContext::new().await;
|
||||
let ctx = TestContext::new_alice().await;
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
"openpgp4fpr:79252762C34C5096AF57958F4FC3D21A81B0F0A7#a=cli%40deltachat.de&g=test%20%3F+test%20%21&x=h-0oKQf2CDK&i=9JEXlxAqGM0&s=0V7LzL9cxRL"
|
||||
@@ -289,7 +287,7 @@ async fn test_decode_openpgp_group() -> Result<()> {
|
||||
|
||||
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||
async fn test_decode_openpgp_invalid_token() -> Result<()> {
|
||||
let ctx = TestContext::new().await;
|
||||
let ctx = TestContext::new_alice().await;
|
||||
|
||||
// Token cannot contain "/"
|
||||
let qr = check_qr(
|
||||
@@ -304,7 +302,7 @@ async fn test_decode_openpgp_invalid_token() -> Result<()> {
|
||||
|
||||
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||
async fn test_decode_openpgp_secure_join() -> Result<()> {
|
||||
let ctx = TestContext::new().await;
|
||||
let ctx = TestContext::new_alice().await;
|
||||
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
@@ -333,7 +331,7 @@ async fn test_decode_openpgp_secure_join() -> Result<()> {
|
||||
}
|
||||
|
||||
// Regression test
|
||||
let ctx = TestContext::new().await;
|
||||
let ctx = TestContext::new_alice().await;
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
"openpgp4fpr:79252762C34C5096AF57958F4FC3D21A81B0F0A7#a=cli%40deltachat.de&n=&i=TbnwJ6lSvD5&s=0ejvbdFSQxB"
|
||||
@@ -353,52 +351,29 @@ async fn test_decode_openpgp_secure_join() -> Result<()> {
|
||||
|
||||
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||
async fn test_decode_openpgp_fingerprint() -> Result<()> {
|
||||
let ctx = TestContext::new().await;
|
||||
let mut tcm = TestContextManager::new();
|
||||
let bob = &tcm.bob().await;
|
||||
let alice = &tcm.alice().await;
|
||||
|
||||
let alice_contact_id = Contact::create(&ctx, "Alice", "alice@example.org")
|
||||
.await
|
||||
.context("failed to create contact")?;
|
||||
let pub_key = alice_keypair().public;
|
||||
let peerstate = Peerstate {
|
||||
addr: "alice@example.org".to_string(),
|
||||
last_seen: 1,
|
||||
last_seen_autocrypt: 1,
|
||||
prefer_encrypt: EncryptPreference::Mutual,
|
||||
public_key: Some(pub_key.clone()),
|
||||
public_key_fingerprint: Some(pub_key.dc_fingerprint()),
|
||||
gossip_key: None,
|
||||
gossip_timestamp: 0,
|
||||
gossip_key_fingerprint: None,
|
||||
verified_key: None,
|
||||
verified_key_fingerprint: None,
|
||||
verifier: None,
|
||||
secondary_verified_key: None,
|
||||
secondary_verified_key_fingerprint: None,
|
||||
secondary_verifier: None,
|
||||
backward_verified_key_id: None,
|
||||
fingerprint_changed: false,
|
||||
};
|
||||
assert!(
|
||||
peerstate.save_to_db(&ctx.ctx.sql).await.is_ok(),
|
||||
"failed to save peerstate"
|
||||
);
|
||||
let alice_contact = bob.add_or_lookup_contact(alice).await;
|
||||
let alice_contact_id = alice_contact.id;
|
||||
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
bob,
|
||||
"OPENPGP4FPR:1234567890123456789012345678901234567890#a=alice@example.org",
|
||||
)
|
||||
.await?;
|
||||
if let Qr::FprMismatch { contact_id, .. } = qr {
|
||||
assert_eq!(contact_id, Some(alice_contact_id));
|
||||
assert_ne!(contact_id.unwrap(), alice_contact_id);
|
||||
} else {
|
||||
bail!("Wrong QR code type");
|
||||
}
|
||||
|
||||
let qr = check_qr(
|
||||
&ctx.ctx,
|
||||
bob,
|
||||
&format!(
|
||||
"OPENPGP4FPR:{}#a=alice@example.org",
|
||||
pub_key.dc_fingerprint()
|
||||
alice_contact.fingerprint().unwrap()
|
||||
),
|
||||
)
|
||||
.await?;
|
||||
@@ -408,14 +383,14 @@ async fn test_decode_openpgp_fingerprint() -> Result<()> {
|
||||
bail!("Wrong QR code type");
|
||||
}
|
||||
|
||||
assert_eq!(
|
||||
assert!(matches!(
|
||||
check_qr(
|
||||
&ctx.ctx,
|
||||
bob,
|
||||
"OPENPGP4FPR:1234567890123456789012345678901234567890#a=bob@example.org",
|
||||
)
|
||||
.await?,
|
||||
Qr::FprMismatch { contact_id: None }
|
||||
);
|
||||
Qr::FprMismatch { .. }
|
||||
));
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user