diff --git a/src/password_manager/manager.py b/src/password_manager/manager.py index 9d26481..541a94d 100644 --- a/src/password_manager/manager.py +++ b/src/password_manager/manager.py @@ -1387,6 +1387,11 @@ class PasswordManager: except Exception as e: logging.error(f"Error generating TOTP code: {e}", exc_info=True) print(colored(f"Error: Failed to generate TOTP code: {e}", "red")) + choice = input("Archive this entry? (y/N): ").strip().lower() + if choice == "y": + self.entry_manager.archive_entry(index) + self.is_dirty = True + self.last_update = time.time() pause() return if entry_type == EntryType.SSH.value: @@ -1422,6 +1427,11 @@ class PasswordManager: except Exception as e: logging.error(f"Error deriving SSH key pair: {e}", exc_info=True) print(colored(f"Error: Failed to derive SSH keys: {e}", "red")) + choice = input("Archive this entry? (y/N): ").strip().lower() + if choice == "y": + self.entry_manager.archive_entry(index) + self.is_dirty = True + self.last_update = time.time() pause() return if entry_type == EntryType.SEED.value: @@ -1472,6 +1482,11 @@ class PasswordManager: except Exception as e: logging.error(f"Error deriving seed phrase: {e}", exc_info=True) print(colored(f"Error: Failed to derive seed phrase: {e}", "red")) + choice = input("Archive this entry? (y/N): ").strip().lower() + if choice == "y": + self.entry_manager.archive_entry(index) + self.is_dirty = True + self.last_update = time.time() pause() return if entry_type == EntryType.PGP.value: @@ -1505,6 +1520,11 @@ class PasswordManager: except Exception as e: logging.error(f"Error deriving PGP key: {e}", exc_info=True) print(colored(f"Error: Failed to derive PGP key: {e}", "red")) + choice = input("Archive this entry? (y/N): ").strip().lower() + if choice == "y": + self.entry_manager.archive_entry(index) + self.is_dirty = True + self.last_update = time.time() pause() return if entry_type == EntryType.NOSTR.value: @@ -1538,6 +1558,11 @@ class PasswordManager: except Exception as e: logging.error(f"Error deriving Nostr keys: {e}", exc_info=True) print(colored(f"Error: Failed to derive Nostr keys: {e}", "red")) + choice = input("Archive this entry? (y/N): ").strip().lower() + if choice == "y": + self.entry_manager.archive_entry(index) + self.is_dirty = True + self.last_update = time.time() pause() return @@ -1625,6 +1650,11 @@ class PasswordManager: print(colored(f" {label}: {value}", "cyan")) else: print(colored("Error: Failed to retrieve the password.", "red")) + choice = input("Archive this entry? (y/N): ").strip().lower() + if choice == "y": + self.entry_manager.archive_entry(index) + self.is_dirty = True + self.last_update = time.time() pause() except Exception as e: logging.error(f"Error during password retrieval: {e}", exc_info=True) diff --git a/src/tests/test_custom_fields_display.py b/src/tests/test_custom_fields_display.py index f8966fc..50745ae 100644 --- a/src/tests/test_custom_fields_display.py +++ b/src/tests/test_custom_fields_display.py @@ -42,7 +42,7 @@ def test_retrieve_entry_shows_custom_fields(monkeypatch, capsys): ], ) - inputs = iter(["0", "y"]) + inputs = iter(["0", "y", "n"]) monkeypatch.setattr("builtins.input", lambda *a, **k: next(inputs)) pm.handle_retrieve_entry() diff --git a/src/tests/test_manager_retrieve_totp.py b/src/tests/test_manager_retrieve_totp.py index b67fe27..ae0f8d2 100644 --- a/src/tests/test_manager_retrieve_totp.py +++ b/src/tests/test_manager_retrieve_totp.py @@ -43,7 +43,8 @@ def test_handle_retrieve_totp_entry(monkeypatch, capsys): entry_mgr.add_totp("Example", TEST_SEED) - monkeypatch.setattr("builtins.input", lambda *a, **k: "0") + inputs = iter(["0", "n"]) + monkeypatch.setattr("builtins.input", lambda *a, **k: next(inputs)) monkeypatch.setattr(pm.entry_manager, "get_totp_code", lambda *a, **k: "123456") monkeypatch.setattr( pm.entry_manager, "get_totp_time_remaining", lambda *a, **k: 1 diff --git a/src/tests/test_manager_workflow.py b/src/tests/test_manager_workflow.py index ec72c70..5a95cd1 100644 --- a/src/tests/test_manager_workflow.py +++ b/src/tests/test_manager_workflow.py @@ -46,6 +46,7 @@ def test_manager_workflow(monkeypatch): pm.nostr_client = FakeNostrClient() pm.fingerprint_dir = tmp_path pm.is_dirty = False + pm.secret_mode_enabled = False inputs = iter( [ @@ -56,6 +57,7 @@ def test_manager_workflow(monkeypatch): "n", # add custom field "", # length (default) "0", # retrieve index + "n", # archive entry prompt "0", # modify index "", # new label "user", # new username diff --git a/src/tests/test_nostr_qr.py b/src/tests/test_nostr_qr.py index fe8cc84..f967c5c 100644 --- a/src/tests/test_nostr_qr.py +++ b/src/tests/test_nostr_qr.py @@ -44,7 +44,8 @@ def test_show_qr_for_nostr_keys(monkeypatch): idx = entry_mgr.add_nostr_key("main") npub, _ = entry_mgr.get_nostr_key_pair(idx, TEST_SEED) - monkeypatch.setattr("builtins.input", lambda *a, **k: str(idx)) + inputs = iter([str(idx), "n"]) + monkeypatch.setattr("builtins.input", lambda *a, **k: next(inputs)) responses = iter([True, False]) monkeypatch.setattr( "password_manager.manager.confirm_action", diff --git a/src/tests/test_secret_mode.py b/src/tests/test_secret_mode.py index 7087396..e11f7a2 100644 --- a/src/tests/test_secret_mode.py +++ b/src/tests/test_secret_mode.py @@ -41,7 +41,8 @@ def test_password_retrieve_secret_mode(monkeypatch, capsys): pm, entry_mgr = setup_pm(tmp) entry_mgr.add_entry("example", 8) - monkeypatch.setattr("builtins.input", lambda *a, **k: "0") + inputs = iter(["0", "n"]) + monkeypatch.setattr("builtins.input", lambda *a, **k: next(inputs)) called = [] monkeypatch.setattr( "password_manager.manager.copy_to_clipboard", @@ -89,7 +90,8 @@ def test_password_retrieve_no_secret_mode(monkeypatch, capsys): pm.secret_mode_enabled = False entry_mgr.add_entry("example", 8) - monkeypatch.setattr("builtins.input", lambda *a, **k: "0") + inputs = iter(["0", "n"]) + monkeypatch.setattr("builtins.input", lambda *a, **k: next(inputs)) called = [] monkeypatch.setattr( "password_manager.manager.copy_to_clipboard",