Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Conditions should not be optional for CBD types #80

Merged
merged 3 commits into from
Sep 6, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 10 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,20 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).


## [0.13.0] - Unreleased

### Changed

- `Conditions` should not be optional as it pertains to `AuthenticatedData` and `AccessControlPolicy` types since conditions-based decryption (CBD) requires conditions. ([#80])

[#80]: https://github.com/nucypher/nucypher-core/pull/78


## [0.12.0] - 2023-08-28

### Changed

- Modified `ThresholdDecryptionResponse` to use `CiphertextHeader` and `AccessControlPolicy` to utilize encapsulation now provided by `ferveo`. ([#74])
- Modified `ThresholdDecryptionRequest` to use `CiphertextHeader` and `AccessControlPolicy` to utilize encapsulation now provided by `ferveo`. ([#74])

### Added

Expand Down
6 changes: 3 additions & 3 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

8 changes: 4 additions & 4 deletions nucypher-core-python/nucypher_core/__init__.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -434,12 +434,12 @@ class MetadataResponse:
@final
class AuthenticatedData:

def __init__(self, public_key: DkgPublicKey, conditions: Optional[Conditions]):
def __init__(self, public_key: DkgPublicKey, conditions: Conditions):
...

public_key: DkgPublicKey

conditions: Optional[Conditions]
conditions: Conditions

def aad(self) -> bytes:
...
Expand All @@ -452,7 +452,7 @@ class AuthenticatedData:
...


def encrypt_for_dkg(data: bytes, public_key: DkgPublicKey, conditions: Optional[Conditions]) -> Tuple[Ciphertext, AuthenticatedData]:
def encrypt_for_dkg(data: bytes, public_key: DkgPublicKey, conditions: Conditions) -> Tuple[Ciphertext, AuthenticatedData]:
...


Expand All @@ -464,7 +464,7 @@ class AccessControlPolicy:

public_key: DkgPublicKey

conditions: Optional[Conditions]
conditions: Conditions

authorization: bytes

Expand Down
39 changes: 11 additions & 28 deletions nucypher-core-python/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ impl Address {
}

#[pyclass(module = "nucypher_core")]
#[derive(derive_more::From, derive_more::AsRef)]
pub struct Conditions {
backend: nucypher_core::Conditions,
}
Expand Down Expand Up @@ -747,13 +748,11 @@ pub struct AuthenticatedData {
#[pymethods]
impl AuthenticatedData {
#[new]
pub fn new(public_key: &DkgPublicKey, conditions: Option<&Conditions>) -> Self {
pub fn new(public_key: &DkgPublicKey, conditions: &Conditions) -> Self {
Self {
backend: nucypher_core::AuthenticatedData::new(
public_key.as_ref(),
conditions
.map(|conditions| conditions.backend.clone())
.as_ref(),
conditions.as_ref(),
),
}
}
Expand All @@ -772,13 +771,8 @@ impl AuthenticatedData {
}

#[getter]
pub fn conditions(&self) -> Option<Conditions> {
self.backend
.conditions
.clone()
.map(|conditions| Conditions {
backend: conditions,
})
pub fn conditions(&self) -> Conditions {
self.backend.conditions.clone().into()
}

#[staticmethod]
Expand All @@ -799,16 +793,11 @@ impl AuthenticatedData {
pub fn encrypt_for_dkg(
data: &[u8],
public_key: &DkgPublicKey,
conditions: Option<&Conditions>,
conditions: &Conditions,
) -> PyResult<(Ciphertext, AuthenticatedData)> {
let (ciphertext, auth_data) = nucypher_core::encrypt_for_dkg(
data,
public_key.as_ref(),
conditions
.map(|conditions| conditions.backend.clone())
.as_ref(),
)
.map_err(FerveoPythonError::FerveoError)?;
let (ciphertext, auth_data) =
nucypher_core::encrypt_for_dkg(data, public_key.as_ref(), conditions.as_ref())
.map_err(FerveoPythonError::FerveoError)?;
Ok((ciphertext.into(), auth_data.into()))
}

Expand Down Expand Up @@ -844,14 +833,8 @@ impl AccessControlPolicy {
}

#[getter]
pub fn conditions(&self) -> Option<Conditions> {
self.backend
.auth_data
.conditions
.clone()
.map(|conditions| Conditions {
backend: conditions,
})
pub fn conditions(&self) -> Conditions {
self.backend.auth_data.conditions.clone().into()
}

#[getter]
Expand Down
32 changes: 13 additions & 19 deletions nucypher-core-wasm/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,7 @@ extern "C" {
// Conditions
//

#[derive(Clone, TryFromJsValue)]
#[derive(Clone, TryFromJsValue, derive_more::From, derive_more::AsRef)]
#[wasm_bindgen]
pub struct Conditions(nucypher_core::Conditions);

Expand Down Expand Up @@ -670,13 +670,11 @@ impl AuthenticatedData {
#[wasm_bindgen(constructor)]
pub fn new(
public_key: &DkgPublicKey,
conditions: &OptionConditions,
conditions: &Conditions,
) -> Result<AuthenticatedData, Error> {
let typed_conditions = try_from_js_option::<Conditions>(conditions)?;

Ok(Self(nucypher_core::AuthenticatedData::new(
public_key.as_ref(),
typed_conditions.as_ref().map(|conditions| &conditions.0),
conditions.as_ref(),
)))
}

Expand All @@ -686,12 +684,12 @@ impl AuthenticatedData {

#[wasm_bindgen(getter, js_name = publicKey)]
pub fn public_key(&self) -> DkgPublicKey {
DkgPublicKey::from(self.0.public_key)
self.0.public_key.into()
}

#[wasm_bindgen(getter)]
pub fn conditions(&self) -> Option<Conditions> {
self.0.conditions.clone().map(Conditions)
pub fn conditions(&self) -> Conditions {
self.0.conditions.clone().into()
}
}

Expand All @@ -702,15 +700,11 @@ impl AuthenticatedData {
pub fn encrypt_for_dkg(
data: &[u8],
public_key: &DkgPublicKey,
conditions: &OptionConditions,
conditions: &Conditions,
) -> Result<DkgEncryptionResult, Error> {
let typed_conditions = try_from_js_option::<Conditions>(conditions)?;
let (ciphertext, auth_data) = nucypher_core::encrypt_for_dkg(
data,
public_key.as_ref(),
typed_conditions.as_ref().map(|conditions| &conditions.0),
)
.map_err(map_js_err)?;
let (ciphertext, auth_data) =
nucypher_core::encrypt_for_dkg(data, public_key.as_ref(), conditions.as_ref())
.map_err(map_js_err)?;
Ok(into_js_array([
JsValue::from(Ciphertext::from(ciphertext)),
JsValue::from(AuthenticatedData::from(auth_data)),
Expand Down Expand Up @@ -748,7 +742,7 @@ impl AccessControlPolicy {

#[wasm_bindgen(getter, js_name = publicKey)]
pub fn public_key(&self) -> DkgPublicKey {
DkgPublicKey::from(self.0.auth_data.public_key)
self.0.auth_data.public_key.into()
}

#[wasm_bindgen(getter)]
Expand All @@ -757,8 +751,8 @@ impl AccessControlPolicy {
}

#[wasm_bindgen(getter)]
pub fn conditions(&self) -> Option<Conditions> {
self.0.auth_data.conditions.clone().map(Conditions)
pub fn conditions(&self) -> Conditions {
self.0.auth_data.conditions.clone().into()
}
}

Expand Down
44 changes: 13 additions & 31 deletions nucypher-core-wasm/tests/wasm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -694,15 +694,12 @@ fn threshold_decryption_request() {

let requester_secret = SessionStaticSecret::random();

let conditions = "{'some': 'condition'}";
let conditions_js: JsValue = Some(Conditions::new(conditions)).into();
let conditions = Conditions::new("{'some': 'condition'}");
let context: JsValue = Some(Context::new("{'user': 'context'}")).into();

let dkg_pk = DkgPublicKey::random();

let auth_data =
AuthenticatedData::new(&dkg_pk, &conditions_js.unchecked_into::<OptionConditions>())
.unwrap();
let auth_data = AuthenticatedData::new(&dkg_pk, &conditions).unwrap();

let authorization = b"we_dont_need_no_stinking_badges";
let acp = AccessControlPolicy::new(&auth_data, authorization).unwrap();
Expand Down Expand Up @@ -801,21 +798,18 @@ fn threshold_decryption_response() {
fn authenticated_data() {
let dkg_pk = DkgPublicKey::random();

let conditions = "{'some': 'condition'}";
let conditions_js: JsValue = Some(Conditions::new(conditions)).into();
let conditions = Conditions::new("{'some': 'condition'}");

let auth_data =
AuthenticatedData::new(&dkg_pk, &conditions_js.unchecked_into::<OptionConditions>())
.unwrap();
let auth_data = AuthenticatedData::new(&dkg_pk, &conditions).unwrap();

assert_eq!(
auth_data.public_key().to_bytes().unwrap(),
dkg_pk.to_bytes().unwrap()
);
assert_eq!(auth_data.conditions().unwrap().to_string(), conditions);
assert!(auth_data.conditions().equals(&conditions));

let mut expected_aad = dkg_pk.to_bytes().unwrap().to_vec();
expected_aad.extend(conditions.as_bytes());
expected_aad.extend(conditions.to_string().as_bytes());

assert_eq!(auth_data.aad().unwrap(), expected_aad.into_boxed_slice());

Expand All @@ -826,22 +820,16 @@ fn authenticated_data() {
deserialized_auth_data.public_key().to_bytes().unwrap(),
dkg_pk.to_bytes().unwrap()
);
assert_eq!(
deserialized_auth_data.conditions().unwrap().to_string(),
conditions,
);
assert!(deserialized_auth_data.conditions().equals(&conditions));
}

#[wasm_bindgen_test]
fn access_control_policy() {
let dkg_pk = DkgPublicKey::random();

let conditions = "{'some': 'condition'}";
let conditions_js: JsValue = Some(Conditions::new(conditions)).into();
let conditions = Conditions::new("{'some': 'condition'}");

let auth_data =
AuthenticatedData::new(&dkg_pk, &conditions_js.unchecked_into::<OptionConditions>())
.unwrap();
let auth_data = AuthenticatedData::new(&dkg_pk, &conditions).unwrap();

let authorization = b"we_dont_need_no_stinking_badges";
let acp = AccessControlPolicy::new(&auth_data, authorization).unwrap();
Expand All @@ -854,7 +842,7 @@ fn access_control_policy() {
authorization.to_vec().into_boxed_slice(),
acp.authorization()
);
assert_eq!(conditions, acp.conditions().unwrap().to_string());
assert!(acp.conditions().equals(&conditions));

// mimic serialization/deserialization over the wire
let serialized_acp = acp.to_bytes();
Expand All @@ -867,25 +855,19 @@ fn access_control_policy() {
authorization.to_vec().into_boxed_slice(),
deserialized_acp.authorization()
);
assert_eq!(
conditions,
deserialized_acp.conditions().unwrap().to_string()
);
assert!(deserialized_acp.conditions().equals(&conditions));

// check aad; expected acp and auth_data acps to be the same
assert_eq!(deserialized_acp.aad(), auth_data.aad());
}

#[wasm_bindgen_test]
fn threshold_message_kit() {
let conditions = "{'some': 'condition'}";
let conditions_js: JsValue = Some(Conditions::new(conditions)).into();
let conditions = Conditions::new("{'some': 'condition'}");

let dkg_pk = DkgPublicKey::random();

let auth_data =
AuthenticatedData::new(&dkg_pk, &conditions_js.unchecked_into::<OptionConditions>())
.unwrap();
let auth_data = AuthenticatedData::new(&dkg_pk, &conditions).unwrap();

let authorization = b"we_dont_need_no_stinking_badges";
let acp = AccessControlPolicy::new(&auth_data, authorization).unwrap();
Expand Down
Loading
Loading