///|
fn pdf_write_required_aes_iv_provider(
provider : ((Int, Int, Int) -> @core.PdfBytes raise @core.PdfError)?,
) -> ((Int, Int, Int) -> @core.PdfBytes raise @core.PdfError) raise @core.PdfError {
match provider {
Some(provider) => provider
None => raise RandomBytesUnavailable
}
}
///|
fn pdf_write_required_aesv3_random_provider(
provider : ((@crypt_core.PdfAesV3RandomField, Int) -> @core.PdfBytes raise @core.PdfError)?,
) -> ((@crypt_core.PdfAesV3RandomField, Int) -> @core.PdfBytes raise @core.PdfError) raise @core.PdfError {
match provider {
Some(provider) => provider
None => raise RandomBytesUnavailable
}
}
///|
fn pdf_write_apply_options_encryption(
document : PdfDocument,
encryption : @writer.PdfWriteEncryption,
file_id : BytesView,
aes_iv_provider : ((Int, Int, Int) -> @core.PdfBytes raise @core.PdfError)?,
aesv3_random_provider : ((@crypt_core.PdfAesV3RandomField, Int) -> @core.PdfBytes raise @core.PdfError)?,
) -> PdfDocument raise @core.PdfError {
match encryption.encryption_method {
PdfEncryption40Bit =>
document.encrypt_40bit(
encryption.user_password,
encryption.owner_password,
encryption.denied_permissions,
file_id~,
)
PdfEncryption128Bit =>
document.encrypt_128bit(
encryption.user_password,
encryption.owner_password,
encryption.denied_permissions,
file_id~,
)
PdfEncryptionAES128(encrypt_metadata) => {
let iv_provider = pdf_write_required_aes_iv_provider(aes_iv_provider)
document.encrypt_128bit_aesv2_with_iv_provider(
encryption.user_password,
encryption.owner_password,
encryption.denied_permissions,
iv_provider,
encrypt_metadata~,
file_id~,
)
}
PdfEncryptionAES256(encrypt_metadata) => {
let random_provider = pdf_write_required_aesv3_random_provider(
aesv3_random_provider,
)
let iv_provider = pdf_write_required_aes_iv_provider(aes_iv_provider)
document.encrypt_256bit_aesv3_with_providers(
encryption.user_password,
encryption.owner_password,
encryption.denied_permissions,
random_provider,
iv_provider,
encrypt_metadata~,
file_id~,
)
}
PdfEncryptionAES256ISO(encrypt_metadata) => {
let random_provider = pdf_write_required_aesv3_random_provider(
aesv3_random_provider,
)
let iv_provider = pdf_write_required_aes_iv_provider(aes_iv_provider)
document.encrypt_256bit_aesv3_iso_with_providers(
encryption.user_password,
encryption.owner_password,
encryption.denied_permissions,
random_provider,
iv_provider,
encrypt_metadata~,
file_id~,
)
}
PdfEncryptionAlreadyEncrypted => document.copy()
}
}
///|
/// One-call writer with optional encryption, IDs, incremental update, and mode.
///
/// The input document is copied before IDs or encryption are applied.
/// `update_from` selects incremental output. `make_id` controls generated
/// trailer IDs for unencrypted writes; encrypted writes always use the provided
/// `file_id` or generate one through the encryption helper. AES modes require
/// the corresponding IV and random providers.
pub fn pdf_write_document_options(
document : PdfDocument,
encryption? : @writer.PdfWriteEncryption? = None,
update_from? : @core.PdfBytes? = None,
make_id? : Bool = true,
id_path? : String = "",
mode? : @writer.PdfWriteMode = PdfWriteClassic,
file_id? : BytesView = [],
aes_iv_provider? : ((Int, Int, Int) -> @core.PdfBytes raise @core.PdfError)? = None,
aesv3_random_provider? : ((@crypt_core.PdfAesV3RandomField, Int) -> @core.PdfBytes raise @core.PdfError)? = None,
) -> @core.PdfBytes raise @core.PdfError {
let prepared = match encryption {
Some(encryption) =>
pdf_write_apply_options_encryption(
document, encryption, file_id, aes_iv_provider, aesv3_random_provider,
)
None =>
if make_id {
document.copy_with_current_id(id_path)
} else {
document.copy()
}
}
match update_from {
Some(original) =>
pdf_write_document_incremental_update_with_mode(original, prepared, mode)
None => pdf_write_document_with_mode(prepared, mode)
}
}
///|
/// Encrypt with 40-bit ARC4 and serialize in the selected write mode.
pub fn pdf_write_encrypted_40bit_document(
document : PdfDocument,
user_password : BytesView,
owner_password : BytesView,
denied_permissions : ArrayView[@crypt_core.PdfPermission],
mode? : @writer.PdfWriteMode = PdfWriteClassic,
file_id? : BytesView = [],
) -> @core.PdfBytes raise @core.PdfError {
pdf_write_document_with_mode(
document.encrypt_40bit(
user_password,
owner_password,
denied_permissions,
file_id~,
),
mode,
)
}
///|
/// Encrypt with 128-bit ARC4 revision 3 and serialize in the selected mode.
pub fn pdf_write_encrypted_128bit_document(
document : PdfDocument,
user_password : BytesView,
owner_password : BytesView,
denied_permissions : ArrayView[@crypt_core.PdfPermission],
mode? : @writer.PdfWriteMode = PdfWriteClassic,
file_id? : BytesView = [],
) -> @core.PdfBytes raise @core.PdfError {
pdf_write_document_with_mode(
document.encrypt_128bit(
user_password,
owner_password,
denied_permissions,
file_id~,
),
mode,
)
}
///|
/// Encrypt with revision-4 ARC4 crypt filters and serialize.
///
/// `encrypt_metadata=false` follows the PDF revision-4 no-metadata behavior.
pub fn pdf_write_encrypted_128bit_r4_document(
document : PdfDocument,
user_password : BytesView,
owner_password : BytesView,
denied_permissions : ArrayView[@crypt_core.PdfPermission],
encrypt_metadata? : Bool = true,
mode? : @writer.PdfWriteMode = PdfWriteClassic,
file_id? : BytesView = [],
) -> @core.PdfBytes raise @core.PdfError {
pdf_write_document_with_mode(
document.encrypt_128bit_r4(
user_password,
owner_password,
denied_permissions,
encrypt_metadata~,
file_id~,
),
mode,
)
}
///|
/// Encrypt with AESV2 and serialize.
///
/// `iv_provider` supplies IVs by object number, generation, and per-object
/// index. This allows deterministic fixtures or secure caller-provided IVs.
pub fn pdf_write_encrypted_aesv2_document_with_iv_provider(
document : PdfDocument,
user_password : BytesView,
owner_password : BytesView,
denied_permissions : ArrayView[@crypt_core.PdfPermission],
iv_provider : (Int, Int, Int) -> @core.PdfBytes raise @core.PdfError,
encrypt_metadata? : Bool = true,
mode? : @writer.PdfWriteMode = PdfWriteClassic,
file_id? : BytesView = [],
) -> @core.PdfBytes raise @core.PdfError {
pdf_write_document_with_mode(
document.encrypt_128bit_aesv2_with_iv_provider(
user_password,
owner_password,
denied_permissions,
iv_provider,
encrypt_metadata~,
file_id~,
),
mode,
)
}
///|
/// Encrypt with AESV3/AES-256 and serialize.
///
/// `random_provider` supplies file keys, salts, and permissions padding;
/// `iv_provider` supplies object-data IVs. `iso=true` selects the ISO/PDF 2.0
/// AESV3 hash variant.
pub fn pdf_write_encrypted_aesv3_document_with_providers(
document : PdfDocument,
user_password : BytesView,
owner_password : BytesView,
denied_permissions : ArrayView[@crypt_core.PdfPermission],
random_provider : (@crypt_core.PdfAesV3RandomField, Int) -> @core.PdfBytes raise @core.PdfError,
iv_provider : (Int, Int, Int) -> @core.PdfBytes raise @core.PdfError,
iso? : Bool = false,
encrypt_metadata? : Bool = true,
mode? : @writer.PdfWriteMode = PdfWriteClassic,
file_id? : BytesView = [],
) -> @core.PdfBytes raise @core.PdfError {
pdf_write_document_with_mode(
document.encrypt_256bit_aesv3_with_providers(
user_password,
owner_password,
denied_permissions,
random_provider,
iv_provider,
iso~,
encrypt_metadata~,
file_id~,
),
mode,
)
}
///|
/// Encrypt with the ISO AESV3/AES-256 variant and serialize.
pub fn pdf_write_encrypted_aesv3_iso_document_with_providers(
document : PdfDocument,
user_password : BytesView,
owner_password : BytesView,
denied_permissions : ArrayView[@crypt_core.PdfPermission],
random_provider : (@crypt_core.PdfAesV3RandomField, Int) -> @core.PdfBytes raise @core.PdfError,
iv_provider : (Int, Int, Int) -> @core.PdfBytes raise @core.PdfError,
encrypt_metadata? : Bool = true,
mode? : @writer.PdfWriteMode = PdfWriteClassic,
file_id? : BytesView = [],
) -> @core.PdfBytes raise @core.PdfError {
pdf_write_encrypted_aesv3_document_with_providers(
document,
user_password,
owner_password,
denied_permissions,
random_provider,
iv_provider,
iso=true,
encrypt_metadata~,
mode~,
file_id~,
)
}