NAME

File::SOPS::Metadata - SOPS metadata section handling

VERSION

version 0.002

SYNOPSIS

use File::SOPS::Metadata;

# Create new metadata
my $meta = File::SOPS::Metadata->new(
    unencrypted_suffix => '_unencrypted',
);

# Add age recipient
$meta->add_age_recipient(
    recipient => 'age1ql3z7hjy54pw3hyww5ayyfg7zqgvc7w3j2elw8zmrj2kg5sfn9aqmcac8p',
    enc       => '-----BEGIN AGE ENCRYPTED FILE-----...',
);

# Update timestamp
$meta->update_lastmodified;

# Set MAC
$meta->mac($mac_string);

# Convert to hash for serialization
my $hash = $meta->to_hash;

# Parse from existing hash
my $meta = File::SOPS::Metadata->from_hash($sops_section);

DESCRIPTION

File::SOPS::Metadata manages the sops metadata section of encrypted files. This section contains:

  • Encrypted data keys for each recipient/backend

  • MAC for tamper detection

  • Timestamp of last modification

  • Rules for which keys should be encrypted

  • SOPS version information

age

ArrayRef of age-encrypted data keys. Each entry is a HashRef with:

{
    recipient => 'age1...',
    enc       => '-----BEGIN AGE ENCRYPTED FILE-----...'
}

Defaults to [].

pgp

ArrayRef of PGP-encrypted data keys. Not yet implemented. Defaults to [].

kms

ArrayRef of AWS KMS-encrypted data keys. Not yet implemented. Defaults to [].

gcp_kms

ArrayRef of Google Cloud KMS-encrypted data keys. Not yet implemented. Defaults to [].

azure_kv

ArrayRef of Azure Key Vault-encrypted data keys. Not yet implemented. Defaults to [].

hc_vault

ArrayRef of HashiCorp Vault-encrypted data keys. Not yet implemented. Defaults to [].

mac

Message Authentication Code over the entire encrypted data structure.

Stored as an encrypted value string: ENC[AES256_GCM,data:...,iv:...,tag:...,type:str]

lastmodified

ISO 8601 timestamp of last modification. Example: 2025-01-10T12:00:00Z

version

SOPS version string. Defaults to 3.7.3 for compatibility with the Go implementation.

unencrypted_suffix

Keys ending with this suffix are not encrypted (but are included in MAC).

Defaults to _unencrypted.

Example: api_key_unencrypted would not be encrypted.

encrypted_suffix

If set, only keys ending with this suffix are encrypted.

Defaults to undef (all keys are encrypted unless they match unencrypted rules).

unencrypted_regex

Regular expression for keys that should not be encrypted.

Defaults to undef.

encrypted_regex

Regular expression for keys that should be encrypted.

Defaults to undef.

from_hash

my $meta = File::SOPS::Metadata->from_hash($hash);

Class method to create a Metadata object from a HashRef.

Typically used when parsing the sops section from a YAML/JSON file.

Returns undef if the input is not a HashRef.

to_hash

my $hash = $meta->to_hash;

Converts the Metadata object to a HashRef for serialization.

This HashRef is written to the sops section of the encrypted file.

update_lastmodified

$meta->update_lastmodified;

Sets lastmodified to the current time in ISO 8601 format (UTC).

Returns $self for chaining.

add_age_recipient

$meta->add_age_recipient(
    recipient => 'age1ql3z7hjy54pw3hyww5ayyfg7zqgvc7w3j2elw8zmrj2kg5sfn9aqmcac8p',
    enc       => '-----BEGIN AGE ENCRYPTED FILE-----...',
);

Adds an age recipient with their encrypted data key.

The enc parameter should be the PEM-armored age-encrypted data key.

Returns $self for chaining.

get_age_encrypted_keys

my @keys = $meta->get_age_encrypted_keys;

Returns a list of age-encrypted data key entries (HashRefs).

Each entry has recipient and enc fields.

should_encrypt_key

if ($meta->should_encrypt_key('api_key')) {
    # Encrypt this key
}

Determines if a hash key should be encrypted based on suffix/regex rules.

Rules are applied in this order:

1. If unencrypted_suffix is set and key ends with it, return false
2. If encrypted_suffix is set, return true if key ends with it, else false
3. If unencrypted_regex is set and key matches, return false
4. If encrypted_regex is set and key matches, return true, else false
5. Default: return true (encrypt everything)

Returns true if the key should be encrypted, false otherwise.

SEE ALSO

SUPPORT

Issues

Please report bugs and feature requests on GitHub at https://github.com/Getty/p5-file-sops/issues.

CONTRIBUTING

Contributions are welcome! Please fork the repository and submit a pull request.

AUTHOR

Torsten Raudssus <torsten@raudssus.de>

COPYRIGHT AND LICENSE

This software is copyright (c) 2026 by Torsten Raudssus.

This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself.