Skip to content

Commit c1f9801

Browse files
committed
sample_other
1 parent 48ed5ab commit c1f9801

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

45 files changed

+1102
-459
lines changed

crates/core/src/logic/encryption/encrypted_app_password.rs

Lines changed: 36 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use crate::prelude::*;
1+
use crate::{logic::Salt, prelude::*};
22

33
use secrecy::{ExposeSecret, SecretString};
44
use serde::{Deserialize, Serialize};
@@ -27,23 +27,36 @@ impl HasSample for SecretString {
2727
fn sample() -> Self {
2828
Self::from("encryption password")
2929
}
30+
3031
fn sample_other() -> Self {
3132
Self::from("another encryption password")
3233
}
3334
}
35+
3436
impl HasSample for EncryptedAppPassword {
3537
fn sample() -> Self {
36-
Self::new_by_deriving_and_encrypting(
37-
SecretString::from("super secret"),
38-
SecretString::sample(),
39-
&Salt::sample(),
38+
// SecretString::from("super secret"),
39+
// SecretString::sample(),
40+
// Salt::sample()
41+
Self(
42+
hex::decode(
43+
"3219e571fbb18265b1fb3f36a75c8e7ef4feef52892a5be25d0b9a92154c5de6456cdfe66aa70070",
44+
)
45+
.unwrap(),
4046
)
4147
}
48+
4249
fn sample_other() -> Self {
43-
Self::new_by_deriving_and_encrypting(
44-
SecretString::from("another super secret"),
45-
SecretString::sample_other(),
46-
&Salt::sample(),
50+
// Self::new_by_deriving_and_encrypting(
51+
// SecretString::from("another super secret"),
52+
// SecretString::sample_other(),
53+
// &Salt::sample_other(),
54+
// )
55+
Self(
56+
hex::decode(
57+
"5b4d6fb8f3bc35af4168b6a0e593e69bedc75a9a062b77a36d6d01cbec06faaaaa3b89fbfd4b5b077c0ae0775de5ac1d",
58+
)
59+
.unwrap(),
4760
)
4861
}
4962
}
@@ -86,12 +99,25 @@ impl EncryptedAppPassword {
8699
mod tests {
87100
use super::*;
88101

102+
type Sut = EncryptedAppPassword;
103+
104+
#[test]
105+
fn equality() {
106+
assert_eq!(Sut::sample(), Sut::sample());
107+
assert_eq!(Sut::sample_other(), Sut::sample_other());
108+
}
109+
110+
#[test]
111+
fn inequality() {
112+
assert_ne!(Sut::sample(), Sut::sample_other());
113+
}
114+
89115
#[test]
90116
fn test_encrypted_app_password() {
91117
let app_password = SecretString::from("my_secret_app_password");
92118
let encryption_pwd = SecretString::from("open sesame");
93119
let salt = Salt::sample();
94-
let encrypted = EncryptedAppPassword::new_by_deriving_and_encrypting(
120+
let encrypted = Sut::new_by_deriving_and_encrypting(
95121
app_password.clone(),
96122
encryption_pwd.clone(),
97123
&salt,

crates/core/src/logic/encryption/mod.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,11 @@ mod aes_gcm_sealed_box;
33
mod encrypted_app_password;
44
mod encryption_key;
55
mod pb_hkdf;
6+
mod salt;
67

78
pub use aes_gcm_256::*;
89
pub use aes_gcm_sealed_box::*;
910
pub use encrypted_app_password::*;
1011
pub use encryption_key::*;
1112
pub use pb_hkdf::*;
13+
pub use salt::*;
Lines changed: 5 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -1,50 +1,12 @@
1-
use crate::prelude::*;
1+
use crate::{logic::Salt, prelude::*};
22
use hkdf::Hkdf;
33
use secrecy::{ExposeSecret, SecretString};
4-
use serde_with::serde_as;
54
use sha2::Sha256;
6-
use zeroize::{Zeroize, ZeroizeOnDrop};
75

86
/// A simple `HKDF` based scheme using UTF8 encoding of the password as input.
97
#[derive(Clone, Default, PartialEq, Eq, Hash)]
108
pub struct PbHkdfSha256;
119

12-
#[serde_as]
13-
#[derive(
14-
Clone,
15-
Debug,
16-
PartialEq,
17-
Eq,
18-
Hash,
19-
From,
20-
Deref,
21-
AsRef,
22-
Serialize,
23-
Deserialize,
24-
Zeroize,
25-
ZeroizeOnDrop,
26-
)]
27-
#[serde(transparent)]
28-
pub struct Salt(#[serde_as(as = "serde_with::hex::Hex")] [u8; 16]);
29-
impl Salt {
30-
/// Uses CSPRNG (safe) to generate a salt.
31-
pub fn generate() -> Self {
32-
use rand::RngCore;
33-
let mut salt = [0u8; 16];
34-
rand::rng().fill_bytes(&mut salt);
35-
Self(salt)
36-
}
37-
}
38-
39-
impl HasSample for Salt {
40-
fn sample() -> Self {
41-
Self([0xab; 16])
42-
}
43-
fn sample_other() -> Self {
44-
Self([0xcd; 16])
45-
}
46-
}
47-
4810
impl PbHkdfSha256 {
4911
const INFO: &'static [u8] = b"klirr email encryption";
5012
fn derive_key_with_ikm_salt_info(
@@ -74,27 +36,16 @@ mod tests {
7436
use super::*;
7537
use hex::encode as hex_encode;
7638

39+
type Sut = PbHkdfSha256;
40+
7741
#[test]
7842
fn test_kdf() {
7943
let ikm = "open sesame";
80-
let salt = Salt([0u8; 16]); // Use a fixed salt for deterministic test
81-
let derived = PbHkdfSha256::derive_key(ikm, &salt);
44+
let salt = Salt::from([0u8; 16]); // Use a fixed salt for deterministic test
45+
let derived = Sut::derive_key(ikm, &salt);
8246
assert_eq!(
8347
hex_encode(*derived),
8448
"ce81a9fdee0e4db76e31d9b49ad2d5b09b45647bc56682d62110fbf32c2903b1"
8549
);
8650
}
87-
88-
#[test]
89-
fn test_salt_generate() {
90-
let salt1 = Salt::generate();
91-
let salt2 = Salt::generate();
92-
93-
// Generated salts should be different
94-
assert_ne!(salt1, salt2);
95-
96-
// Salt should not be all zeros
97-
assert_ne!(salt1.0, [0u8; 16]);
98-
assert_ne!(salt2.0, [0u8; 16]);
99-
}
10051
}
Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,76 @@
1+
use serde_with::serde_as;
2+
use zeroize::{Zeroize, ZeroizeOnDrop};
3+
4+
use crate::prelude::*;
5+
6+
/// A cryptographically secure random salt used for key derivation.
7+
/// It is used to ensure that the derived keys are unique even if the
8+
/// input key material is the same.
9+
#[serde_as]
10+
#[derive(
11+
Clone,
12+
Debug,
13+
PartialEq,
14+
Eq,
15+
Hash,
16+
From,
17+
Deref,
18+
AsRef,
19+
Serialize,
20+
Deserialize,
21+
Zeroize,
22+
ZeroizeOnDrop,
23+
)]
24+
#[serde(transparent)]
25+
pub struct Salt(#[serde_as(as = "serde_with::hex::Hex")] [u8; 16]);
26+
27+
impl Salt {
28+
/// Uses CSPRNG (safe) to generate a salt.
29+
pub fn generate() -> Self {
30+
use rand::RngCore;
31+
let mut salt = [0u8; 16];
32+
rand::rng().fill_bytes(&mut salt);
33+
Self(salt)
34+
}
35+
}
36+
37+
impl HasSample for Salt {
38+
fn sample() -> Self {
39+
Self([0xab; 16])
40+
}
41+
42+
fn sample_other() -> Self {
43+
Self([0xcd; 16])
44+
}
45+
}
46+
47+
#[cfg(test)]
48+
mod tests {
49+
use super::*;
50+
51+
type Sut = Salt;
52+
53+
#[test]
54+
fn equality() {
55+
assert_eq!(Sut::sample(), Sut::sample());
56+
assert_eq!(Sut::sample_other(), Sut::sample_other());
57+
}
58+
59+
#[test]
60+
fn inequality() {
61+
assert_ne!(Sut::sample(), Sut::sample_other());
62+
}
63+
64+
#[test]
65+
fn test_salt_generate() {
66+
let salt1 = Salt::generate();
67+
let salt2 = Salt::generate();
68+
69+
// Generated salts should be different
70+
assert_ne!(salt1, salt2);
71+
72+
// Salt should not be all zeros
73+
assert_ne!(*salt1, [0u8; 16]);
74+
assert_ne!(*salt2, [0u8; 16]);
75+
}
76+
}

crates/core/src/models/cost.rs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,3 +17,21 @@ impl HasSample for Cost {
1717
Self::from(dec!(500.0))
1818
}
1919
}
20+
21+
#[cfg(test)]
22+
mod tests {
23+
use super::*;
24+
25+
type Sut = Cost;
26+
27+
#[test]
28+
fn equality() {
29+
assert_eq!(Sut::sample(), Sut::sample());
30+
assert_eq!(Sut::sample_other(), Sut::sample_other());
31+
}
32+
33+
#[test]
34+
fn inequality() {
35+
assert_ne!(Sut::sample(), Sut::sample_other());
36+
}
37+
}

crates/core/src/models/data/data.rs

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -153,6 +153,7 @@ impl<Period: IsPeriod + HasSample> HasSample for Data<Period> {
153153
.expensed_periods(ExpensedPeriods::sample())
154154
.build()
155155
}
156+
156157
fn sample_other() -> Self {
157158
Data::builder()
158159
.information(ProtoInvoiceInfo::sample_other())
@@ -172,14 +173,27 @@ mod tests {
172173
use super::*;
173174
use test_log::test;
174175

176+
type Sut = Data<YearAndMonth>;
177+
178+
#[test]
179+
fn equality() {
180+
assert_eq!(Sut::sample(), Sut::sample());
181+
assert_eq!(Sut::sample_other(), Sut::sample_other());
182+
}
183+
184+
#[test]
185+
fn inequality() {
186+
assert_ne!(Sut::sample(), Sut::sample_other());
187+
}
188+
175189
#[test]
176190
fn test_serialization_sample() {
177-
assert_ron_snapshot!(Data::<YearAndMonth>::sample())
191+
assert_ron_snapshot!(Sut::sample())
178192
}
179193

180194
#[test]
181195
fn test_worked_days_when_ooo_is_greater_than_0() {
182-
let sut = Data::sample();
196+
let sut = Sut::sample();
183197
let partial = sut
184198
.to_partial(
185199
ValidInput::builder()

crates/core/src/models/data/submodels/company_information.rs

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ impl HasSample for CompanyInformation {
2929
fn sample() -> Self {
3030
Self::sample_client()
3131
}
32+
3233
fn sample_other() -> Self {
3334
Self::sample_vendor()
3435
}
@@ -55,3 +56,21 @@ impl CompanyInformation {
5556
.build()
5657
}
5758
}
59+
60+
#[cfg(test)]
61+
mod tests {
62+
use super::*;
63+
64+
type Sut = CompanyInformation;
65+
66+
#[test]
67+
fn equality() {
68+
assert_eq!(Sut::sample(), Sut::sample());
69+
assert_eq!(Sut::sample_other(), Sut::sample_other());
70+
}
71+
72+
#[test]
73+
fn inequality() {
74+
assert_ne!(Sut::sample(), Sut::sample_other());
75+
}
76+
}

0 commit comments

Comments
 (0)