Skip to content
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: 1 addition & 10 deletions Cargo.lock

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

1 change: 0 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,6 @@ bitwarden-send = { path = "crates/bitwarden-send", version = "=1.0.0" }
bitwarden-sm = { path = "bitwarden_license/bitwarden-sm", version = "=1.0.0" }
bitwarden-ssh = { path = "crates/bitwarden-ssh", version = "=1.0.0" }
bitwarden-state = { path = "crates/bitwarden-state", version = "=1.0.0" }
bitwarden-state-migrations = { path = "crates/bitwarden-state-migrations", version = "=1.0.0" }
bitwarden-test = { path = "crates/bitwarden-test", version = "=1.0.0" }
bitwarden-threading = { path = "crates/bitwarden-threading", version = "=1.0.0" }
bitwarden-uniffi-error = { path = "crates/bitwarden-uniffi-error", version = "=1.0.0" }
Expand Down
3 changes: 3 additions & 0 deletions crates/bitwarden-pm/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ uniffi = [
"bitwarden-fido/uniffi",
"bitwarden-generators/uniffi",
"bitwarden-send/uniffi",
"bitwarden-state/uniffi",
"bitwarden-vault/uniffi",
"dep:uniffi"
] # Uniffi bindings
Expand All @@ -33,6 +34,7 @@ wasm = [
"bitwarden-core/wasm",
"bitwarden-exporters/wasm",
"bitwarden-generators/wasm",
"bitwarden-state/wasm",
"bitwarden-vault/wasm",
"dep:wasm-bindgen",
"dep:wasm-bindgen-futures",
Expand All @@ -48,6 +50,7 @@ bitwarden-exporters = { workspace = true }
bitwarden-fido = { workspace = true }
bitwarden-generators = { workspace = true }
bitwarden-send = { workspace = true }
bitwarden-state = { workspace = true }
bitwarden-vault = { workspace = true }

tsify = { workspace = true, optional = true }
Expand Down
7 changes: 7 additions & 0 deletions crates/bitwarden-pm/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ pub mod clients {
#[cfg(feature = "bitwarden-license")]
pub use commercial::CommercialPasswordManagerClient;

pub mod migrations;

/// The main entry point for the Bitwarden Password Manager SDK
pub struct PasswordManagerClient(pub bitwarden_core::Client);

Expand All @@ -46,6 +48,11 @@ impl PasswordManagerClient {
))
}

/// Platform operations
pub fn platform(&self) -> bitwarden_core::platform::PlatformClient {
self.0.platform()
}

/// Auth operations
pub fn auth(&self) -> bitwarden_auth::AuthClient {
self.0.auth_new()
Expand Down
32 changes: 32 additions & 0 deletions crates/bitwarden-pm/src/migrations.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
//! Manages repository migrations for the Bitwarden SDK.

use bitwarden_state::repository::{RepositoryItem, RepositoryMigrationStep, RepositoryMigrations};
use bitwarden_vault::{Cipher, Folder};

/// Returns a list of all SDK-managed repository migrations.
pub fn get_sdk_managed_migrations() -> RepositoryMigrations {
use RepositoryMigrationStep::*;
RepositoryMigrations::new(vec![
// Add any new migrations here. Note that order matters, and that removing a repository
// requires a separate migration step using `Remove(...)`.
Add(Cipher::data()),
Add(Folder::data()),
])
}

/// Macro to create the client managed repositories for the SDK.
/// To add a new repository, add it to the list in the macro invocation.
/// This is meant to be used by the final application crates (e.g., bitwarden-uniffi,
/// bitwarden-wasm-internal, bw).
#[macro_export]
macro_rules! create_client_managed_repositories {
($container_name:ident, $macro:ident) => {
$macro! {
$container_name;
// List any SDK-managed repositories here. The format is:
// <fully qualified path to the item>, <item type idenfier>, <field name>, <name of the repository implementation>
::bitwarden_vault::Cipher, Cipher, cipher, CipherRepository;
::bitwarden_vault::Folder, Folder, folder, FolderRepository;
}
};
}
21 changes: 0 additions & 21 deletions crates/bitwarden-state-migrations/Cargo.toml

This file was deleted.

4 changes: 0 additions & 4 deletions crates/bitwarden-state-migrations/README.md

This file was deleted.

15 changes: 0 additions & 15 deletions crates/bitwarden-state-migrations/src/lib.rs

This file was deleted.

58 changes: 18 additions & 40 deletions crates/bitwarden-state/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,21 +39,20 @@ need to define some functions in `bitwarden-wasm-internal` and `bitwarden-uniffi
applications to provide their `Repository` implementations. The implementations themselves will be
very simple as we provide macros that take care of the brunt of the work.

### Client-Managed State in WASM
To add support for a new `Repository`, add it to the list defined at the end of
`crates/bitwarden-pm/src/migrations.rs`.

For WASM, we need to define a new `Repository` for our type and provide a function that will accept
it. This is done in the file `crates/bitwarden-wasm-internal/src/platform/mod.rs`, you can check the
provided example:

```rust,ignore
repository::create_wasm_repository!(CipherRepository, Cipher, "Repository<Cipher>");

#[wasm_bindgen]
impl StateClient {
pub fn register_cipher_repository(&self, store: CipherRepository) {
let store = store.into_channel_impl();
self.0.platform().state().register_client_managed(store)
}
```rust
macro_rules! create_client_managed_repositories {
($container_name:ident, $macro:ident) => {
$macro! {
$container_name;
// List any SDK-managed repositories here. The format is:
// <fully qualified path to the item>, <item type idenfier>, <field name>, <name of the repository implementation>
::bitwarden_vault::Cipher, Cipher, cipher, CipherRepository;
::bitwarden_vault::Folder, Folder, folder, FolderRepository;
}
};
Comment on lines +45 to +55
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

praise: Nice idea! Using macros do define the repositories in a place where we're not actually able to depend on them ๐Ÿ‘

}
```

Expand Down Expand Up @@ -90,30 +89,9 @@ export async function initializeState(
stateClient: StateClient,
stateProvider: StateProvider,
): Promise<void> {
await stateClient.register_cipher_repository(
new RepositoryRecord(userId, stateProvider, new CipherRecordMapper()),
);
}
```

### Client-Managed State in UniFFI

For UniFFI, we need to define a new `Repository` for our type and provide a function that will
accept it. This is done in the file `crates/bitwarden-uniffi/src/platform/mod.rs`, you can check the
provided example:

```rust,ignore
repository::create_uniffi_repository!(CipherRepository, Cipher);

#[uniffi::export]
impl StateClient {
pub fn register_cipher_repository(&self, store: Arc<dyn CipherRepository>) {
let store_internal = UniffiRepositoryBridge::new(store);
self.0
.platform()
.state()
.register_client_managed(store_internal)
}
stateClient.register_client_managed_repositories({
cipher: new RepositoryRecord(userId, stateProvider, new CipherRecordMapper()),
});
}
```

Expand Down Expand Up @@ -187,8 +165,8 @@ SDK. To add support for an SDK managed `Repository`, a new migration step needs

### How to initialize SDK-Managed State

Go to `crates/bitwarden-state-migrations/src/lib.rs` and add a line with your type, as shown below.
In this example we're registering `Cipher` and `Folder` as SDK managed.
Go to `crates/bitwarden-pm/src/migrations.rs` and add a line with your type, as shown below. In this
example we're registering `Cipher` and `Folder` as SDK managed.

```rust,ignore
/// Returns a list of all SDK-managed repository migrations.
Expand Down
1 change: 0 additions & 1 deletion crates/bitwarden-uniffi/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,6 @@ bitwarden-pm = { workspace = true, features = ["uniffi"] }
bitwarden-send = { workspace = true, features = ["uniffi"] }
bitwarden-ssh = { workspace = true, features = ["uniffi"] }
bitwarden-state = { workspace = true, features = ["uniffi"] }
bitwarden-state-migrations = { workspace = true, features = ["uniffi"] }
bitwarden-uniffi-error = { workspace = true }
bitwarden-vault = { workspace = true, features = ["uniffi"] }
chrono = { workspace = true, features = ["std"] }
Expand Down
16 changes: 11 additions & 5 deletions crates/bitwarden-uniffi/src/platform/mod.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
#![allow(deprecated)]

use std::sync::Arc;

use bitwarden_core::{Client, platform::FingerprintRequest};
use bitwarden_fido::ClientFido2Ext;
use bitwarden_state::DatabaseConfiguration;
use bitwarden_vault::Cipher;
use repository::UniffiRepositoryBridge;
use repository::{UniffiRepositoryBridge, create_uniffi_repositories};

use crate::error::Result;

Expand Down Expand Up @@ -45,24 +46,29 @@ impl PlatformClient {
#[derive(uniffi::Object)]
pub struct StateClient(Client);

repository::create_uniffi_repository!(CipherRepository, Cipher);

#[derive(uniffi::Record)]
pub struct SqliteConfiguration {
db_name: String,
folder_path: String,
}

bitwarden_pm::create_client_managed_repositories!(Repositories, create_uniffi_repositories);

#[uniffi::export]
impl StateClient {
#[deprecated(note = "Use `register_client_managed_repositories` instead")]
pub fn register_cipher_repository(&self, repository: Arc<dyn CipherRepository>) {
let cipher = UniffiRepositoryBridge::new(repository);
self.0.platform().state().register_client_managed(cipher);
}

pub fn register_client_managed_repositories(&self, repositories: Repositories) {
repositories.register_all(&self.0.platform().state());
}

/// Initialize the database for SDK managed repositories.
pub async fn initialize_state(&self, configuration: SqliteConfiguration) -> Result<()> {
let migrations = bitwarden_state_migrations::get_sdk_managed_migrations();
let migrations = bitwarden_pm::migrations::get_sdk_managed_migrations();

self.0
.platform()
Expand Down
Loading
Loading