go-crypt/crypt/crypt_test.go

129 lines
3.9 KiB
Go
Raw Permalink Normal View History

package crypt
import (
"bytes"
"testing"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)
func TestEncryptDecrypt_Good(t *testing.T) {
plaintext := []byte("hello, world!")
passphrase := []byte("correct-horse-battery-staple")
encrypted, err := Encrypt(plaintext, passphrase)
assert.NoError(t, err)
assert.NotEqual(t, plaintext, encrypted)
decrypted, err := Decrypt(encrypted, passphrase)
assert.NoError(t, err)
assert.Equal(t, plaintext, decrypted)
}
func TestEncryptDecrypt_Bad(t *testing.T) {
plaintext := []byte("secret data")
passphrase := []byte("correct-passphrase")
wrongPassphrase := []byte("wrong-passphrase")
encrypted, err := Encrypt(plaintext, passphrase)
assert.NoError(t, err)
_, err = Decrypt(encrypted, wrongPassphrase)
assert.Error(t, err)
}
func TestEncryptDecryptAES_Good(t *testing.T) {
plaintext := []byte("hello, AES world!")
passphrase := []byte("my-secure-passphrase")
encrypted, err := EncryptAES(plaintext, passphrase)
assert.NoError(t, err)
assert.NotEqual(t, plaintext, encrypted)
decrypted, err := DecryptAES(encrypted, passphrase)
assert.NoError(t, err)
assert.Equal(t, plaintext, decrypted)
}
// --- Phase 0 Additions ---
// TestWrongPassphraseDecrypt_Bad verifies wrong passphrase returns error, not corrupt data.
func TestWrongPassphraseDecrypt_Bad(t *testing.T) {
plaintext := []byte("sensitive payload")
passphrase := []byte("correct-passphrase")
wrongPassphrase := []byte("wrong-passphrase")
encrypted, err := Encrypt(plaintext, passphrase)
require.NoError(t, err)
decrypted, err := Decrypt(encrypted, wrongPassphrase)
assert.Error(t, err, "wrong passphrase must return an error")
assert.Nil(t, decrypted, "wrong passphrase must not return partial data")
// Same for AES variant
encryptedAES, err := EncryptAES(plaintext, passphrase)
require.NoError(t, err)
decryptedAES, err := DecryptAES(encryptedAES, wrongPassphrase)
assert.Error(t, err, "wrong passphrase must return an error (AES)")
assert.Nil(t, decryptedAES, "wrong passphrase must not return partial data (AES)")
}
// TestEmptyPlaintextRoundTrip_Good verifies encrypt/decrypt of empty plaintext.
func TestEmptyPlaintextRoundTrip_Good(t *testing.T) {
passphrase := []byte("test-passphrase")
// ChaCha20
encrypted, err := Encrypt([]byte{}, passphrase)
require.NoError(t, err)
assert.NotEmpty(t, encrypted, "ciphertext should include salt + nonce even for empty plaintext")
decrypted, err := Decrypt(encrypted, passphrase)
require.NoError(t, err)
assert.Empty(t, decrypted, "decrypted empty plaintext should be empty")
// AES-GCM
encryptedAES, err := EncryptAES([]byte{}, passphrase)
require.NoError(t, err)
assert.NotEmpty(t, encryptedAES)
decryptedAES, err := DecryptAES(encryptedAES, passphrase)
require.NoError(t, err)
assert.Empty(t, decryptedAES)
}
// TestLargePlaintextRoundTrip_Good verifies encrypt/decrypt of a 1MB payload.
func TestLargePlaintextRoundTrip_Good(t *testing.T) {
passphrase := []byte("large-payload-passphrase")
plaintext := bytes.Repeat([]byte("X"), 1024*1024) // 1MB
// ChaCha20
encrypted, err := Encrypt(plaintext, passphrase)
require.NoError(t, err)
assert.Greater(t, len(encrypted), len(plaintext), "ciphertext should be larger than plaintext")
decrypted, err := Decrypt(encrypted, passphrase)
require.NoError(t, err)
assert.Equal(t, plaintext, decrypted)
// AES-GCM
encryptedAES, err := EncryptAES(plaintext, passphrase)
require.NoError(t, err)
decryptedAES, err := DecryptAES(encryptedAES, passphrase)
require.NoError(t, err)
assert.Equal(t, plaintext, decryptedAES)
}
// TestDecryptCiphertextTooShort_Ugly verifies short ciphertext is rejected.
func TestDecryptCiphertextTooShort_Ugly(t *testing.T) {
_, err := Decrypt([]byte("short"), []byte("pass"))
assert.Error(t, err)
assert.Contains(t, err.Error(), "too short")
_, err = DecryptAES([]byte("short"), []byte("pass"))
assert.Error(t, err)
assert.Contains(t, err.Error(), "too short")
}