Skip to content

StrategicProjects/pdfsigner

Repository files navigation

pdfsigner pdfsigner website

CRAN status CRAN downloads License: GPL v3 powered by pdf_signer

pdfsigner is an R package to digitally sign PDF documents with a PKCS#12 keystore and verify their signatures.

The package is powered by a bundled, pure-Rust backend (the pdf_signer crate, wrapped with extendr). It no longer shells out to Java (BatchPDFSignPortable.jar) or Poppler (pdfsig): no Java runtime, OpenSSL, or external command-line tools are required — only a Rust toolchain at install time.

Installation

Requires a Rust toolchain (cargo, rustc) to compile the bundled backend. Install Rust from https://rustup.rs, then:

# install.packages("remotes")
remotes::install_github("StrategicProjects/pdfsigner")

What it does

  • PAdES signatures up to B-LTA via pades_level: "bb" (CAdES signing-certificate-v2), "bt" (+ RFC 3161 signature timestamp), "blt" (+ a /DSS with the certificate chain and CRLs), "blta" (+ a document timestamp over the whole file). Levels "bt"+ need a tsa_url.
  • Incremental updates: signing again appends only, so earlier signatures stay valid — multi-signature is supported.
  • Visible or invisible signatures, with a custom text box + validation link.
  • Cryptographic verification of every signature (re-derives the signed byte range, checks the message digest and the signer's RSA signature).

Usage

sign_pdf()

library(pdfsigner)

sign_pdf(
  pdf_file          = "input.pdf",
  output_file       = "signed.pdf",
  keystore_path     = "keystore.p12",      # or env var KEYSTORE_PATH
  keystore_password = "password",          # or env var KEY_PASSWORD
  signtext          = "Document digitally signed by CastLab",
  validate_link     = "https://castlab.org/validate",
  reason            = "Approval",
  translate         = TRUE,                 # Portuguese date label
  font              = "Arial.ttf",          # embed a TrueType/OpenType font
  image             = "logo.png",           # draw a PNG/JPEG logo in the box
  tsa_url           = "http://timestamp.digicert.com",
  pades_level       = "blta"                # bb | bt | blt | blta
)

A visible signature box is drawn whenever signtext is non-empty; geometry is controlled by page, x, y, width, height, font_size and border. Pass font to embed a TrueType/OpenType font (WinAnsi/Latin-1 glyphs; the default is Helvetica) and image to draw a PNG/JPEG logo in the box. Omit signtext for an invisible signature.

verify_pdf_signature()

result <- verify_pdf_signature("signed.pdf")
length(result)                              # number of signatures
vapply(result, function(s) s$valid, logical(1))
result[[1]]$signer                          # signer distinguished name

Each entry is a named list: valid, signer, chain_trusted, covers_whole_document, signed_len, byte_range, detail.

Pass roots (a PEM file of trusted roots, e.g. the ICP-Brasil AC Raiz set) to validate each signer certificate chain; chain_trusted is then TRUE/FALSE (and NA when no roots are given):

verify_pdf_signature("signed.pdf", roots = "icp-brasil-roots.pem")

TSA / CRL endpoints over HTTPS are supported (the bundled Rust backend is built with its https feature, using rustls).

Generating a test certificate

openssl req -x509 -newkey rsa:2048 -keyout key.pem -out cert.pem -days 365 -nodes
openssl pkcs12 -export -inkey key.pem -in cert.pem -out keystore.p12

Architecture

pdfsigner architecture: the R interface (sign_pdf / verify_pdf_signature) calls the extendr bridge, which links the pure-Rust pdf_signer crate and its vendored dependencies, producing PAdES-signed PDFs and a verification report.

The R functions call a thin extendr bridge that links the pure-Rust pdf_signer crate. Every Rust dependency is vendored under src/rust/vendor.tar.xz so the package builds offline (CRAN policy: SystemRequirements: Cargo, rustc).

License

GPL-3. The bundled pdf_signer crate and its vendored Rust dependencies retain their own licenses.

About

PDF Signing and Signature Verification with BatchPDFSign and pdfsig

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages