diff --git a/tests/unit/crypto/test_encryptor.py b/tests/unit/crypto/test_encryptor.py index a4f4a61f5..bb394c243 100644 --- a/tests/unit/crypto/test_encryptor.py +++ b/tests/unit/crypto/test_encryptor.py @@ -85,6 +85,45 @@ async def test_encrypt_empty_data(encryptor): assert decrypted == b"" +@pytest.mark.asyncio +async def test_decrypt_empty_plaintext(encryptor): + """Test decrypting empty plaintext bytes (not encrypted-empty, but raw b''). + + Regression test: decrypt() used to raise 'Ciphertext too short' on empty + files because it checked length before the magic header. + """ + account_id = "test_account" + decrypted = await encryptor.decrypt(account_id, b"") + assert decrypted == b"" + + +@pytest.mark.asyncio +@pytest.mark.parametrize("data", [b"X", b"AB", b"ABC"]) +async def test_decrypt_short_plaintext_less_than_4_bytes(encryptor, data): + """Test decrypting plaintext shorter than 4 bytes (magic length). + + Regression test: these used to raise InvalidMagicError('Ciphertext too short') + because length was checked before the magic prefix. + """ + account_id = "test_account" + decrypted = await encryptor.decrypt(account_id, data) + assert decrypted == data + + +@pytest.mark.asyncio +async def test_decrypt_magic_prefix_without_full_header(encryptor): + """Test decrypting data that starts with 'OVE1' but has no valid envelope. + + Should raise CorruptedCiphertextError because the envelope header is + incomplete (needs at least 12 bytes). + """ + account_id = "test_account" + from openviking.crypto.exceptions import CorruptedCiphertextError + + with pytest.raises(CorruptedCiphertextError): + await encryptor.decrypt(account_id, b"OVE1") + + @pytest.mark.asyncio async def test_different_accounts(encryptor): """Test encryption/decryption across different accounts."""