Referência da API Ruby
O PDF Oxide oferece bindings nativos para Ruby (gem pdf_oxide) construídos com FFI sobre o C ABI do cdylib. A gem empacota uma biblioteca nativa pré-compilada e espelha a estrutura de 9 classes do binding Java sob o namespace PdfOxide.
gem install pdf_oxide
require 'pdf_oxide'
Para a API Rust, veja a Referência da API Rust. Para a API Python, veja a Referência da API Python. Para detalhes de tipos, veja Tipos e Enums.
Todos os objetos que detêm um handle (PdfDocument, Pdf, DocumentEditor) são donos de memória nativa e devem ser fechados. O padrão idiomático é a forma com bloco, que fecha automaticamente; #close é idempotente.
PdfOxide (módulo)
Pontos de entrada de conveniência de nível superior e chaves globais de processo.
PdfOxide.open(source, password: nil) { |doc| ... } -> PdfDocument
Abre um PDF para leitura. Delega para PdfDocument.open. Aceita o caminho de um arquivo ou bytes brutos de PDF; a forma com bloco fecha automaticamente.
PdfOxide.version -> String
Retorna a string de versão da biblioteca (ex.: "0.3.69").
PdfOxide.set_max_ops_per_stream(limit) -> Integer
Define o limite global de processo para operadores de content stream. Um limit negativo restaura o padrão (1.000.000); qualquer valor não negativo se torna o limite explícito. Retorna o limite anterior.
PdfOxide.set_preserve_unmapped_glyphs(preserve) -> Integer
Alterna a flag global de processo para preservação de U+FFFD (glifo não mapeado) usada pela extração de texto. Valores truthy/não zero preservam; falsey/0 filtram (o padrão). Retorna o valor anterior (0 ou 1).
PdfDocument
O ponto de entrada principal somente leitura de um PDF: extração, busca, conversão, renderização e acesso a páginas.
doc = PdfOxide::PdfDocument.open('invoice.pdf')
Construtor e métodos de classe
PdfOxide::PdfDocument.open(source, password: nil) { |doc| ... } -> PdfDocument
Abre um PDF a partir de um caminho no sistema de arquivos ou de bytes brutos de PDF (detectados automaticamente pela assinatura mágica %PDF- em entradas binárias). A forma com bloco fecha automaticamente; a forma sem bloco retorna o documento. Levanta FileNotFoundError, ParseError ou EncryptedError.
PdfOxide::PdfDocument.new(source, password: nil) -> PdfDocument
Constrói diretamente, sem bloco. Prefira .open.
PdfOxide::PdfDocument.extract_text(source, page: 0) -> String
Auxiliar de uma só chamada: abre, extrai o texto de uma única página e fecha.
Informações do documento
doc.page_count -> Integer
Número de páginas no documento.
doc.pdf_version -> String
String de versão do PDF (ex.: "1.7"), ou "unknown" se indisponível.
doc.encrypted? -> Boolean
Se o PDF carrega um dicionário de criptografia.
doc.path -> String
Caminho absoluto a partir do qual o documento foi aberto (ou <in-memory> para documentos abertos a partir de bytes).
Autenticação
doc.authenticate(password) -> Boolean
Autentica contra a criptografia deste documento. Retorna true em caso de sucesso ou para documentos não criptografados.
Extração de texto
doc.extract_text(page_index) -> String
Extrai texto puro de uma única página (índice começando em zero); vazio para páginas sem camada de texto.
doc.extract_structured(page) -> Hash
Extrai uma representação estruturada de uma página como um Hash com page_index, page_width, page_height e regions (cada uma com kind, text, bbox, spans, column_index).
doc.extract_text_auto(page_index) -> String
Extração com roteamento automático: texto nativo onde houver, OCR para regiões digitalizadas quando o recurso ocr estiver disponível, com fallback nativo gracioso (nunca levanta “OCR unavailable”).
Conversão
doc.to_markdown(page_index = nil) -> String
Converte uma página para Markdown, ou o documento inteiro quando page_index é nil.
doc.to_html(page_index = nil) -> String
Converte uma página para HTML, ou o documento inteiro quando page_index é nil.
Busca
doc.search(query, case_sensitive: false, regex: false) -> Array<Hash>
Busca no documento. Cada correspondência é { page:, text:, bbox: { x:, y:, width:, height: } }. Passe regex: true para interpretar query como uma expressão regular (levanta UnsupportedFeatureError se o build não tiver busca por regex).
Formulários
doc.form_fields -> Array<Hash>
Campos AcroForm como hashes { name:, value:, type:, page: }. Retorna [] quando o build não tem o accessor de extração de formulários.
Renderização
doc.render(page_index, dpi: 150) -> String
Renderiza uma única página em bytes PNG (BINARY) no DPI fornecido.
doc.render_with_layers(page_index, dpi: 150, format: 0,
background: [1.0, 1.0, 1.0, 1.0], transparent: false,
render_annotations: true, jpeg_quality: 90,
excluded_layers: []) -> String
Renderiza uma página com toda a superfície de RenderOptions mais filtragem de camadas Optional-Content-Group (OCG). format: 0 = PNG, 1 = JPEG; excluded_layers lista os /Names de OCG a suprimir. Retorna os bytes da imagem codificada (BINARY).
Acesso a páginas
doc.page(index) -> PdfPage
Uma view leve PdfPage da página em index.
doc.pages -> Array<PdfPage>
Todas as páginas do documento (avaliação eager).
Auto-extração
doc.auto_extractor -> AutoExtractor
O AutoExtractor configurado para este documento (memoizado).
Ciclo de vida
doc.close -> nil
Libera o handle nativo. Idempotente.
doc.open? -> Boolean
doc.closed? -> Boolean
Se o documento ainda está aberto / já foi fechado.
PdfPage
Uma view leve por página tomada emprestada de um PdfDocument. Não detém handle nativo próprio. Construída via PdfDocument#page ou #pages.
page = doc.page(0)
Atributos
page.parent -> PdfDocument
page.index -> Integer
O documento dono e o índice da página (começando em zero).
Geometria
page.width -> Float
page.height -> Float
Largura e altura da página em unidades do espaço de usuário do PDF.
page.media_box -> Hash
page.crop_box -> Hash
{ x:, y:, width:, height: } para a media box / crop box (a crop box recorre à media box).
page.rotation -> Integer
Rotação da página em graus.
Texto
page.text -> String
Extrai o texto desta página (equivalente a parent.extract_text(index)).
page.to_s -> String
page.inspect -> String
Rótulo curto de inspeção (#<PdfOxide::PdfPage index=N>).
Cria e salva PDFs: fontes Markdown/HTML/texto/imagem, exportação para bytes e planejamento de divisão por marcadores.
pdf = PdfOxide::Pdf.from_markdown("# Title\n\nBody")
Métodos de fábrica
PdfOxide::Pdf.from_markdown(markdown) { |pdf| ... } -> Pdf
Constrói um PDF a partir de Markdown.
PdfOxide::Pdf.from_html(html) { |pdf| ... } -> Pdf
Constrói um PDF a partir de HTML (o CSS é respeitado via o pipeline html_css).
PdfOxide::Pdf.from_text(text) { |pdf| ... } -> Pdf
Constrói um PDF a partir de texto puro.
PdfOxide::Pdf.from_images(images) { |pdf| ... } -> Pdf
Constrói um PDF a partir de um array de blobs de bytes JPEG/PNG (formato detectado automaticamente pelos magic bytes).
PdfOxide::Pdf.create_empty { |pdf| ... } -> Pdf
Cria um PDF em branco de página única.
Auxiliares estáticos
PdfOxide::Pdf.version -> String
A versão da biblioteca.
PdfOxide::Pdf.prefetch_models(languages) -> String
Pré-carrega modelos de OCR para as tags de idioma BCP-47/ISO fornecidas. Retorna o caminho do diretório de cache (vazio em builds sem OCR).
PdfOxide::Pdf.prefetch_available? -> Boolean
Se o build suporta o provisionamento de modelos de OCR.
PdfOxide::Pdf.plan_split_by_bookmarks_count(source_pdf, level) -> Integer
Conta os segmentos de divisão por marcadores que resultariam de dividir source_pdf (bytes brutos) no level (1 = nível superior, 0 = todos), sem produzir saída.
Métodos de instância
pdf.to_bytes -> String
O PDF como bytes codificados em BINARY.
pdf.save(path) -> String
Grava o PDF em path. Retorna o caminho absoluto gravado.
pdf.close -> nil
pdf.closed? -> Boolean
Libera o handle nativo (idempotente) / se ele já foi fechado.
DocumentEditor
Editor do lado de escrita: tarjamento destrutivo, limpeza de metadados, preenchimento de formulários e salvamento incremental. Toda operação de tarjamento falha de forma fechada (um retorno diferente de zero levanta exceção).
PdfOxide::DocumentEditor.open('source.pdf') do |ed|
ed.add_redaction(page: 0, rect: [100, 200, 300, 250])
ed.apply_redactions!
ed.save_to('redacted.pdf')
end
Construtor
PdfOxide::DocumentEditor.open(source) { |ed| ... } -> DocumentEditor
Abre um editor sobre um PDF em disco ou bytes em memória. A forma com bloco fecha automaticamente.
PdfOxide::DocumentEditor.new(source) -> DocumentEditor
Constrói diretamente, sem bloco.
Tarjamento
ed.add_redaction(page:, rect:, color: [0.0, 0.0, 0.0]) -> self
Enfileira um retângulo de tarjamento (rect = [x1, y1, x2, y2] no espaço de usuário do PDF; color = [r, g, b]). Não é aplicado até apply_redactions!.
ed.redaction_count(page) -> Integer
Total de tarjamentos enfileirados para a página.
ed.apply_redactions!(scrub_metadata: false, fill_color: [0.0, 0.0, 0.0]) -> self
Aplica todos os tarjamentos enfileirados de forma destrutiva, opcionalmente limpando /Info, XMP e JS.
ed.scrub_metadata -> self
Remove os metadados sem regiões de tarjamento.
Formulários
ed.set_form_field(name, value) -> self
Define um campo AcroForm pelo nome completo separado por pontos. Um value Boolean mira em uma checkbox/radio; caso contrário define um valor de texto.
Salvamento e ciclo de vida
ed.save_to(path) -> String
Salva o PDF editado. Retorna o caminho absoluto gravado.
ed.to_bytes -> String
O PDF editado como bytes codificados em BINARY.
ed.close -> nil
ed.closed? -> Boolean
Libera o handle nativo (idempotente) / se ele já foi fechado.
AutoExtractor
Auto-extração com razões tipadas (roteamento texto-vs-OCR com fallback nativo gracioso). Construído a partir de um PdfDocument.
ax = PdfOxide::AutoExtractor.new(doc)
result = ax.extract_page(0)
warn "degraded: #{result[:reason]}" unless ax.ok?(result[:reason])
Construtor e atributo
PdfOxide::AutoExtractor.new(document) -> AutoExtractor
Envolve um PdfDocument para auto-extração.
ax.document -> PdfDocument
O documento envolvido.
Classificação
ax.classify_page(page_index) -> Hash
Classificador barato por página (sem OCR/rasterização). Retorna { reason:, kind:, confidence:, classification: }.
ax.classify_document -> Hash
Classificador do documento inteiro; retorna o envelope JSON decodificado.
Extração
ax.extract_text(page_index) -> Hash
Extrai o texto de uma página via o roteador automático; retorna { text:, reason:, kind:, confidence:, classification: }.
ax.extract_page(page_index, options: nil) -> Hash
Extração rica por página, retornando o envelope completo PageExtraction (texto + bbox por região + razão + confiança) mesclado em um Hash.
Predicados
ax.ok?(reason) -> Boolean
Se reason representa uma extração limpa.
ax.ocr_fallback?(reason) -> Boolean
Se o caminho de fallback gracioso de OCR-indisponível foi acionado.
PdfOxide::AutoExtractor.prefetch_available? -> Boolean
Se o build suporta o provisionamento de OCR.
Constantes
AutoExtractor::REASONS — array congelado de símbolos de razão tipados (:ok, :native_text_high_confidence, :no_text_layer_present, :ocr_requested_but_unavailable, etc.). AutoExtractor::PAGE_KINDS — símbolos de tipo de página (:text_layer, :scanned, :image_text, :mixed, :empty).
MarkdownConverter
Módulo sem estado que converte um PdfDocument para Markdown ou HTML.
PdfOxide::MarkdownConverter.to_markdown(doc, page_index = nil) -> String
Converte uma página (ou o documento inteiro quando page_index é nil) para Markdown.
PdfOxide::MarkdownConverter.to_html(doc, page_index = nil) -> String
Converte uma página (ou o documento inteiro) para HTML.
PdfPolicy
Política global de governança criptográfica de processo com semântica set-once. Chame .set antes de qualquer outra operação do PDF Oxide.
PdfOxide::PdfPolicy.current -> Symbol
O modo de política atual do processo (:compat, :strict ou :fips_strict).
PdfOxide::PdfPolicy.set(mode) -> Symbol
Define o modo de política global de processo. Levanta exceção se já estiver definido ou não for suportado pelo build.
PdfOxide::PdfPolicy.compat -> Symbol
PdfOxide::PdfPolicy.strict -> Symbol
PdfOxide::PdfPolicy.fips_strict -> Symbol
Símbolos de modo predefinidos: aceitar todos os algoritmos / rejeitar algoritmos legados / apenas FIPS 140-3.
PdfPolicy::MODES — mapeamento congelado de símbolos de modo para ordinais do cdylib.
PdfSigner
Assinador de assinatura digital PAdES B-B / B-T / B-LT / B-LTA. A assinatura é uma operação de segurança: todo retorno diferente de zero falha de forma fechada.
PdfOxide::PdfSigner.new(certificate_handle) -> PdfSigner
Constrói um assinador a partir de um handle opaco de credenciais PKCS#12/PEM.
signer.sign(pdf, level:, tsa_url: nil, reason: nil, location: nil) -> String
Assina bytes brutos de PDF no nível PAdES solicitado (:b, :t, :lt, :lta). Um tsa_url é obrigatório para níveis >= :t. Retorna os bytes do PDF assinado codificados em BINARY.
PdfOxide::PdfSigner.sign(pdf:, certificate_handle:, level:, tsa_url: nil, reason: nil, location: nil) -> String
Conveniência estática: assina sem construir uma instância de assinador.
PdfOxide::PdfSigner.pades_level(signature_handle) -> Integer
O ordinal do nível PAdES de um handle de assinatura existente.
PdfOxide::PdfSigner.document_has_timestamp?(document_handle) -> Boolean
Se o documento carrega um /DocTimeStamp de escopo de documento.
PdfSigner::LEVELS — mapeamento congelado de símbolos de nível para códigos. PdfSigner::PadesSignOptions — FFI::Struct empacotado que espelha o layout C de PadesSignOptionsC.
PdfValidator
Validação sem estado de conformidade PDF/A e PDF/UA.
PdfOxide::PdfValidator.pdf_a?(doc, level: :a1b) -> Boolean
Se o documento está em conformidade com PDF/A para level (:a1b, :a1a, :a2b, :a2a, :a2u, :a3b, :a3a, :a3u).
PdfOxide::PdfValidator.pdf_ua?(doc, level: :ua1) -> Boolean
Se o documento está em conformidade com PDF/UA para level (:ua1 ou :ua2).
PdfOxide::PdfValidator.validate_pdf_a(doc, level: :a1b) -> Hash
Resultado PDF/A simplificado: { compliant:, violations: }.
PdfOxide::PdfValidator.validate_pdf_ua(doc, level: :ua1) -> Hash
Resultado PDF/UA simplificado: { compliant:, violations: }.
PdfValidator::PDF_A_LEVELS e PdfValidator::PDF_UA_LEVELS — mapeamentos congelados de nível para ordinal.
Tratamento de erros
Todas as exceções do PDF Oxide derivam de PdfOxide::Error. Os códigos de erro nativos mapeiam 1-para-1 para as subclasses abaixo.
begin
doc = PdfOxide::PdfDocument.open('file.pdf')
text = doc.extract_text(0)
rescue PdfOxide::FileNotFoundError
warn 'file not found'
rescue PdfOxide::ParseError => e
warn "malformed PDF: #{e.message}"
rescue PdfOxide::Error => e
warn "PDF error: #{e.message}"
ensure
doc&.close
end
| Exceção | Causa |
|---|---|
Error |
Classe base para todos os erros do PDF Oxide |
UnsupportedPlatformError |
Plataforma host não suportada pelo cdylib embutido |
ArgumentError |
Argumento falhou na validação antes da chamada nativa |
IoError |
Falha de sistema de arquivos / E/S |
FileNotFoundError |
Arquivo ausente (especializa IoError) |
ParseError |
Cabeçalho malformado, xref corrompida, falha de extração |
StateError |
Ordem de operação incorreta |
InvalidStateError |
Operação sobre um handle já fechado (especializa StateError) |
EncryptedError |
Falha de criptografia / senha incorreta |
PermissionError |
PDF criptografado sem permissão de extração/assinatura |
UnsupportedFeatureError |
Recurso não compilado neste build do cdylib |
SignatureError |
Falha de assinatura / verificação PAdES |
RedactionError |
Falha de tarjamento destrutivo (falha de forma fechada) |
ComplianceError |
Falha de validação PDF/A · PDF/UA |
SearchError |
Falha de busca de texto nativa |
InternalError |
Falha genérica do lado nativo |
Exemplo completo
require 'pdf_oxide'
# --- Extraction ---
PdfOxide::PdfDocument.open('input.pdf') do |doc|
puts "Pages: #{doc.page_count}"
doc.page_count.times do |i|
puts "Page #{i + 1}: #{doc.extract_text(i).length} characters"
end
# Search
doc.search('configuration', case_sensitive: false).each do |m|
puts "Page #{m[:page] + 1}: '#{m[:text]}' at (#{m[:bbox][:x]}, #{m[:bbox][:y]})"
end
# Render page 1 to PNG
File.binwrite('page1.png', doc.render(0, dpi: 150))
end
# --- Creation ---
PdfOxide::Pdf.from_markdown("# Report\n\nGenerated by PDF Oxide.") do |pdf|
pdf.save('report.pdf')
end
# --- Redaction ---
PdfOxide::DocumentEditor.open('source.pdf') do |ed|
ed.add_redaction(page: 0, rect: [100, 200, 300, 250])
ed.apply_redactions!(scrub_metadata: true)
ed.save_to('redacted.pdf')
end
# --- Validation ---
PdfOxide::PdfDocument.open('archive.pdf') do |doc|
puts "PDF/A-1b compliant: #{PdfOxide::PdfValidator.pdf_a?(doc, level: :a1b)}"
end
Other Language Bindings
O PDF Oxide oferece bindings nativos para todos os principais ecossistemas: Rust, Python, Node.js, WASM, C#, Golang, Java, PHP, C++, Swift, Kotlin, Dart, R, Julia, Zig, Scala, Clojure, Objective-C e Elixir.
Próximos passos
- Tipos e Enums — todos os tipos e enums compartilhados
- Referência da API Page — iteração consistente por página entre os bindings
- Primeiros Passos com Ruby — tutorial