Skip to content

Encryption

Tayra uses AES-256-GCM (Galois/Counter Mode) for all field-level encryption. This is an authenticated encryption algorithm that provides both confidentiality and integrity -- if the ciphertext or bound context is tampered with, decryption fails with a CryptographicException.

AES-256-GCM

AES-GCM is the recommended symmetric encryption mode for modern applications:

  • Authenticated -- The authentication tag detects any modification to the ciphertext.
  • Non-deterministic -- Each encryption produces different ciphertext because a fresh random nonce is used every time.
  • Performance -- Hardware-accelerated on modern CPUs via AES-NI instructions.
  • Standard -- NIST SP 800-38D, widely adopted in TLS 1.3, IPsec, and SSH.

Tayra uses the .NET System.Security.Cryptography.AesGcm class, which delegates to the OS cryptographic provider (OpenSSL on Linux, CNG on Windows, CommonCrypto on macOS).

Wire Format

Every encrypted value produced by Tayra follows a versioned binary format:

┌───────────┬──────────┬──────────────┬──────────────┐
│ Version   │ Nonce    │ Ciphertext   │ Auth Tag     │
│ (1 byte)  │ (12 B)   │ (N bytes)    │ (16 bytes)   │
└───────────┴──────────┴──────────────┴──────────────┘
ComponentSizeDescription
Version1 byteFormat version. 0x01 is legacy (no context binding). 0x02 adds associated-data context binding for stronger misuse resistance.
Nonce12 bytes (96 bits)Randomly generated per encryption operation using RandomNumberGenerator.
CiphertextN bytesThe encrypted data. Same length as the plaintext input.
Auth Tag16 bytes (128 bits)GCM authentication tag for tamper detection.

Total overhead: 29 bytes per encrypted value (1 + 12 + 16).

For string fields, the binary output is Base64-encoded before being stored in the property, which adds approximately 33% to the encoded size.

Associated Data Context Binding

Version 0x02 payloads bind encryption to field context using AES-GCM associated data (AAD).

  • AAD is authenticated but not encrypted.
  • Tayra binds encrypted values to context components: entity type, field name, and field group.
  • Moving ciphertext between fields with the same key scope fails authentication at decrypt time.

This reduces substitution/mix-and-match attacks in scenarios where one subject/group key protects multiple fields.

Backward compatibility is preserved:

  • Existing 0x01 payloads remain decryptable.
  • New field-level encryptions use 0x02.

Nonce Generation

Each encryption operation generates a fresh 12-byte (96-bit) nonce using System.Security.Cryptography.RandomNumberGenerator:

  • The nonce is never reused for the same key. AES-GCM security depends on nonce uniqueness.
  • The nonce is stored alongside the ciphertext (in the wire format), so it does not need to be tracked separately.
  • With 96-bit random nonces and AES-256 keys, the probability of a collision is negligible for practical data volumes (birthday bound: ~2^48 encryptions per key).

Nonce Reuse

Reusing a nonce with the same key completely breaks AES-GCM security, allowing an attacker to recover plaintext and forge authentication tags. Tayra prevents this by generating a cryptographically random nonce for every encryption operation.

Key Sizes

Tayra supports three AES key sizes:

Key SizeBytesConfiguration
128 bits16 bytesopts.KeySizeInBits = 128
192 bits24 bytesopts.KeySizeInBits = 192
256 bits32 bytesopts.KeySizeInBits = 256 (default)

AES-256 is the default and recommended setting. All three sizes use the same wire format -- the key size is determined by the key itself, not stored in the ciphertext.

String Encryption

For [PersonalData] string fields, Tayra:

  1. Encodes the string to UTF-8 bytes.
  2. Encrypts the bytes using AES-GCM (producing a versioned wire format, 0x02 for new writes).
  3. Encodes the result as a Base64 string.
  4. Stores the Base64 string back in the property.

Decryption reverses this: Base64 decode, AES-GCM decrypt, UTF-8 decode.

Binary Encryption

For [SerializedPersonalData] fields, Tayra:

  1. Serializes the value to bytes using a built-in binary serializer.
  2. Encrypts the bytes using AES-GCM (version 0x02 for new writes).
  3. Stores the raw encrypted bytes (not Base64) in the companion byte[]? property.

Partial Redaction

When a redaction strategy is set on a [PersonalData] attribute (via the Redaction property), Tayra embeds the redacted value in the ciphertext string using a prefix format:

TAYRA_M:{redacted_value}\n{base64_ciphertext}

During decryption:

  • If the key exists, the prefix is stripped and the ciphertext is decrypted normally.
  • If the key has been deleted (crypto-shredding), the redacted value is extracted and returned.

Searchable Encrypted Fields

Since AES-256-GCM is non-deterministic, you cannot query encrypted fields directly. Tayra provides HMAC blind indexes as a companion feature — one-way hashes stored alongside encrypted fields that enable equality queries without exposing plaintext.

See Also