Show TOTP codes in password details (#75)
This commit is contained in:
1 parent
9759162eff
commit
2026637a0e
9 files changed
+640
-110
No files matched your search
@@ -145,6 +145,30 @@ impl MobileEntryCopy {
|
||||
}
|
||||
}
|
||||
|
||||
pub struct MobileEntryPresentation {
|
||||
page: MobileEntryPage,
|
||||
totp: Option<MobileTotpDetail>,
|
||||
cache_notice: Option<String>,
|
||||
}
|
||||
|
||||
impl MobileEntryPresentation {
|
||||
pub fn page(&self) -> &MobileEntryPage {
|
||||
&self.page
|
||||
}
|
||||
|
||||
pub fn totp(&self) -> Option<&MobileTotpDetail> {
|
||||
self.totp.as_ref()
|
||||
}
|
||||
|
||||
pub fn cache_notice(&self) -> Option<&str> {
|
||||
self.cache_notice.as_deref()
|
||||
}
|
||||
|
||||
pub fn into_parts(self) -> (MobileEntryPage, Option<MobileTotpDetail>, Option<String>) {
|
||||
(self.page, self.totp, self.cache_notice)
|
||||
}
|
||||
}
|
||||
|
||||
impl MobileAuthenticationState {
|
||||
pub fn unlocked(self) -> bool {
|
||||
self.unlocked
|
||||
@@ -385,9 +409,32 @@ impl MobileAuthentication {
|
||||
.map_err(MobileAuthenticationError::authentication)
|
||||
}
|
||||
|
||||
pub fn entry_page(&self, path: &str) -> Result<MobileEntryPage, MobileAuthenticationError> {
|
||||
pub fn entry_page(
|
||||
&self,
|
||||
path: &str,
|
||||
unix_seconds: u64,
|
||||
) -> Result<MobileEntryPresentation, MobileAuthenticationError> {
|
||||
let document = self.open_active_document(path)?;
|
||||
Ok(MobileEntryPage::from_document(&document))
|
||||
let ciphertext = document
|
||||
.original_ciphertext()
|
||||
.ok_or_else(|| entry_detail("Password Entry Is Unavailable", "entry does not exist"))?;
|
||||
let shared = self.status()?.watch_shared_totp_entries.clone();
|
||||
let cache_path = self.config.source().with_file_name("totp-catalog.toml");
|
||||
let reconciliation = MobileTotpService::new(&self.repository, &self.keys)
|
||||
.reconcile_document(
|
||||
&document,
|
||||
ciphertext,
|
||||
Some(unix_seconds),
|
||||
&shared,
|
||||
&cache_path,
|
||||
)
|
||||
.map_err(totp_error)?;
|
||||
let (totp, cache_notice) = reconciliation.into_parts();
|
||||
Ok(MobileEntryPresentation {
|
||||
page: MobileEntryPage::from_document(&document),
|
||||
totp,
|
||||
cache_notice,
|
||||
})
|
||||
}
|
||||
|
||||
pub fn reveal_entry_field(
|
||||
@@ -591,6 +638,7 @@ impl MobileAuthentication {
|
||||
EntryDocumentService::new(&self.repository, &self.keys)
|
||||
.save_recoverable(&document, None, &mut committer)
|
||||
.map_err(document_error)?;
|
||||
self.reconcile_saved_document(&document);
|
||||
Ok(MobileEntryPage::from_document(&document))
|
||||
}
|
||||
|
||||
@@ -764,6 +812,7 @@ impl MobileAuthentication {
|
||||
self.restore_editor(editor, draft)?;
|
||||
return Err(document_error(error));
|
||||
}
|
||||
self.reconcile_saved_document(draft.document());
|
||||
Ok(MobileEntryPage::from_document(draft.document()))
|
||||
}
|
||||
|
||||
@@ -954,6 +1003,25 @@ impl MobileAuthentication {
|
||||
.open(path, &mut provider)
|
||||
.map_err(document_error)
|
||||
}
|
||||
|
||||
fn reconcile_saved_document(&self, document: &EntryDocument) {
|
||||
let Ok(ciphertext) = self.repository.read_entry(document.path()) else {
|
||||
return;
|
||||
};
|
||||
let Ok(status) = self.status() else {
|
||||
return;
|
||||
};
|
||||
let shared = status.watch_shared_totp_entries.clone();
|
||||
drop(status);
|
||||
let cache_path = self.config.source().with_file_name("totp-catalog.toml");
|
||||
let _ = MobileTotpService::new(&self.repository, &self.keys).reconcile_document(
|
||||
document,
|
||||
&ciphertext,
|
||||
None,
|
||||
&shared,
|
||||
&cache_path,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
struct KeyOnlyProvider<'a> {
|
||||
|
||||
Reference in new issue
Block a user