2 pontos por GN⁺ 2025-02-11 | 1 comentários | Compartilhar no WhatsApp
  • PDFSyntax é uma biblioteca Python focada no capítulo 7, “Syntax”, da PDF Specification, usada para inspecionar e transformar a estrutura interna de arquivos PDF até o nível de bytes
  • Foi escrita do zero em Python puro e é uma biblioteca leve sem dependências, com foco em simplicidade e imutabilidade
  • O modo de edição padrão é a atualização incremental não destrutiva permitida pela especificação PDF, adicionando uma seção de alterações ao fim do arquivo original, com possibilidade de reverter ou consolidar em uma única revisão
  • A CLI oferece overview, disasm, text, fonts, browse etc.; browse gera uma saída amigável do código-fonte do PDF e permite explorar a estrutura interna em HTML estático com hyperlinks
  • No momento, é um projeto em andamento com qualidade beta; a API pode mudar a qualquer momento e, embora use licença MIT, ainda não aceita contribuições externas

Inspeção e transformação da estrutura interna de PDFs

  • PDFSyntax é uma biblioteca Python para inspecionar e transformar a estrutura interna de arquivos PDF
  • Foca no capítulo 7, “Syntax”, da Portable Document Format (PDF) Specification
  • Implementa o gerenciamento da estrutura do documento até o nível de bytes para usos como:
    • acesso a metadados
    • rotação de páginas
    • operações de leitura/escrita de PDF
    • acesso e manipulação de objetos internos

Direção de design

  • As funções internas são expostas como um toolkit de API para operações de leitura/escrita de PDF
  • Parte dos recursos também é oferecida como CLI para uso no terminal ou no navegador
  • A biblioteca foi escrita em Python puro e não tem dependências externas
  • Dá prioridade à simplicidade e à imutabilidade
  • O modo de edição padrão é a atualização incremental: em vez de sobrescrever o original, adiciona as mudanças ao fim do arquivo original
    • Se necessário, é possível reverter revisões
    • Também é possível consolidar todas as revisões em uma só

Instalação e uso da CLI

  • Pode ser instalada via PyPI
pip install pdfsyntax
  • O formato básico de uso da CLI é o seguinte
pdfsyntax COMMAND FILE
  • Se instalada a partir do código-fonte, pode ser executada na forma mais longa
python3 -m pdfsyntax COMMAND FILE
  • Os principais comandos para análise rápida de PDFs são:
    • overview: exibe informações em texto sobre estrutura e metadados
    • disasm: imprime um dump da estrutura do arquivo no terminal
    • text: exibe o texto extraído preservando a disposição espacial, como em um scan
    • fonts: exibe a lista de fontes usadas
    • browse: gera uma saída amigável do código-fonte do PDF e cria um HTML estático com hyperlinks para facilitar a navegação pela estrutura interna

Forma de uso da API

  • O PDFSyntax é composto principalmente por funções simples
  • Com readfile, é possível ler um PDF, e com metadata, obter os metadados em forma de dict do Python
>>> from pdfsyntax import readfile, metadata
>>> doc = readfile("samples/simple_text_string.pdf")
>>> metadata(doc)
  • O objeto Doc é praticamente a única classe dedicada e armazena o estado interno do documento
    • conteúdo em cache ou memoizado do arquivo original
    • alterações de adição, modificação e remoção de conteúdo
    • histórico de modificações rastreado por atualizações incrementais
  • A mesma função metadata também pode ser usada como método do objeto Doc
>>> doc.metadata()
  • Funções de baixo nível como get_object e update_object permitem acessar e manipular diretamente os objetos internos do documento
  • Também há funções de alto nível como rotate
>>> from pdfsyntax import rotate, writefile
>>> doc180 = rotate(doc, 180)
  • No exemplo de rotação, o objeto original não é alterado; em vez disso, é criado um novo objeto contendo a mudança de orientação em andamento
  • O PDF modificado pode ser gravado em disco com writefile
>>> writefile(doc180, "rotated_doc.pdf")
  • O arquivo resultante tem uma nova seção adicionada após o conteúdo original, e cortar essa seção permite desfazer a alteração

Estado atual e política de contribuições

  • O projeto está em andamento e é um software de qualidade beta
  • A API pode mudar a qualquer momento
  • A lista de próximos trabalhos inclui:
    • recorte e junção de páginas
    • compressão sem perdas
    • mais filtros
    • melhoria na extração de texto
    • reforço da extração de texto com detecção de layout
  • O PDFSyntax usa licença MIT
  • No momento, não aceita contribuições externas
    • É um projeto pessoal com tempo limitado
    • A ideia é primeiro focar na roadmap de novos recursos e refatoração e aceitar contribuições após a estabilização

1 comentários

 
GN⁺ 2025-02-11
Comentários no Hacker News
  • Muito tempo atrás, fiquei encarregado de extrair dados de vários PDFs e criei uma ferramenta para visualizar o posicionamento dos caracteres na página e as caixas delimitadoras de todos os elementos.
    No fim, o projeto foi um fracasso total, e algumas pessoas ficaram irritadas porque ele não entregou o resultado esperado.
    Hoje, eu com certeza teria ido pelo caminho de aproveitar as capacidades dos LLMs para extrair dados de PDFs. Na época, essa opção não existia.

    • Fazer parsing de dados em PDFs arbitrários é quase uma missão amaldiçoada. PDFs podem conter imagens, então é meio parecido com mirar diretamente em JPEGs.
      Dependendo das expectativas, dá para ir bem longe com OCR, mas, pela minha experiência, ele sempre fica um pouco aquém do necessário.
    • LLMs podem ajudar a ordenar os caracteres extraídos de uma página, mas obter o conteúdo real ainda é difícil.
      Já vi várias vezes casos em que as letras do texto eram glifos de fontes customizadas sem um mapeamento tipo ASCII, ou em que, como é especialmente comum em saídas de CAD, os formatos das letras eram desenhados com linhas.
      Nesse caso, não há texto identificável para extrair, então no fim é preciso verificar a página novamente com OCR.
    • Passei por algo parecido em um emprego anterior, e abordagens de parsing baseadas em regras são realmente difíceis de acertar e falham com frequência em casos de borda.
      Na https://runtrellis.com/, estamos criando do zero um pipeline de processamento de PDFs baseado em LLMs e modelos de visão-linguagem, e vimos precisão perto de 100% mesmo em PDFs complicados.
      O ponto central é usar um mecanismo baseado em regras junto com dados de referência para validar os resultados de forma cruzada.
    • Muito tempo atrás, trabalhei na extração de desenhos CAD 2D de PDFs e na conversão deles para 3D completo; foi bem divertido.
    • O pdfjs faz tudo isso e é bem robusto. Usei recentemente para extrair dados de tabelas de 10 anos de extratos bancários.
  • Bem legal. Se isso existisse no meu emprego anterior, acho que eu teria usado bastante.
    O ideal seria algo como https://lapo.it/asn1js/, em que você solta o arquivo e todo o processamento acontece localmente.

  • Graças ao “privilégio” de lidar com código que extrai dados de PDFs, venho usando há algum tempo a versão gratuita do iText RUPS para depurar PDFs.
    A inspeção interna daqui parece um pouco mais poderosa, então deve ser muito boa. Pretendo testar.

  • Lembro de ter visto um projeto parecido no GitHub. Ele permitia visualizar dados binários arbitrários a partir de um schema fornecido, e acho que havia um exemplo de TCP/IP.

    • Talvez seja https://kaitai.io/.
      Parecia ótimo para esse papel, mas no último projeto também precisávamos de serialização, então não usei.
    • O HexFiend também tem uma sintaxe de templates para visualização de dados binários. É baseada em Tcl.
      https://github.com/HexFiend/HexFiend/blob/master/templates/T...
    • Nesse contexto, é bom tomar cuidado com a palavra “arbitrários”.
      Curiosamente, quando testo esses descritores de formatos de arquivo, uso PDF como “Hello World”, porque a especificação de PDF é muito esquisita.
      Se a linguagem de descrição consegue expressar corretamente o layout de um PDF, dá para dizer que ela é, sem dúvida, bem projetada.
      Até agora, não tive muita sorte com nada que não permita sair do modo declarativo e fazer “então execute este código”.
  • Isto parece útil também para forense e para encontrar marcas d’água.

    • Parece interessante. Não entendo muito disso: como isso poderia ser usado para detecção de marcas d’água? Será que assinaturas também poderiam ser detectadas da mesma forma?
  • Parece bom.
    Seria ainda melhor se todos os bytes do PDF fossem exibidos. Parece que endobj e xref não aparecem.

    • Sim, vou corrigir isso em breve.
  • Seria muito bom se isso saísse como uma biblioteca para navegador. Bastaria arrastar e soltar um arquivo para ver o que há dentro. Ainda assim, é impressionante.

    • Você quer dizer uma extensão de navegador? Não quero ser rude, só estou tentando confirmar se entendi direito.
  • Muito bem feito. É uma ferramenta de pré-visualização de segurança muito útil. PDF é uma dor de cabeça.

  • Fiquei curioso se a ferramenta de UI responsável pela visualização é uma biblioteca.
    Gostei muito do formato da UI e também gostaria de usá-la para decompor e depurar fluxos de bytes de vídeo.
    Edit: na verdade, é bem simples. Bom uso de CSS! https://github.com/desgeeko/pdfsyntax/blob/main/docs/simple_...

    • Sim. Valorizo a simplicidade, e a interação oferecida por HTML e CSS básicos é suficiente para meu caso de uso :)
  • Na mesma linha, por que o PDF ainda não foi substituído? Existem XPS, DjVu, XHTML (EPUB), mas todos parecem mirar casos de uso diferentes, como arquivos HTML empacotados.
    O que eu quero é um formato de documento simples que permita incorporar outros arquivos e metadados sem o inchaço da Adobe.
    Ele deveria permitir links dentro da página, evitar que o texto transborde quando o tamanho da fonte muda e imprimir de forma consistente.

    • Não acho que o motivo de o PDF ser um formato “infeliz” para edição, leitura no dispositivo e extração de informação semântica em vez de informação de apresentação seja culpa da Adobe ou do inchaço.
      PDF não é um formato de dados, é um formato de descrição de páginas; todas as decisões vêm da necessidade de permitir imprimir a mesma “página” mesmo usando sistemas operacionais, softwares, impressoras e tamanhos exatos de papel diferentes.
      O principal motivo de o PDF resistir por tanto tempo provavelmente é que muita coisa ainda gira em torno do paradigma de documento, isto é, a ideia de que um “documento” é um “conjunto de folhas de papel”.
      De resumos pós-consulta em hospitais a documentos de registro de automóveis, eles já têm uma representação visual específica escolhida para parecer correta e caber exatamente no papel.
      HTML, por exemplo em um formato autônomo com imagens e CSS em URLs de dados, ou ePub, poderia ser melhor na maioria dos aspectos.
      Mas os objetivos são tão diferentes que, se você fosse tentar convencer hoje quem cria PDFs a migrar para isso, ouviria reclamações de que o conteúdo aparece um pouco diferente em cada dispositivo e que até as quebras de página variam conforme as configurações.
      Algo interessante nesse contexto é que até o Google Docs, embora provavelmente bem menos da metade dos documentos acabe sendo impressa ou convertida para PDF, usa modo de páginas por padrão, e não o modo “sem páginas”.
      O modo “sem páginas” é muito mais útil: como uma página web comum, ele se ajusta à janela e permite rolar indefinidamente por uma única superfície contínua.
    • Os casos de uso são diferentes.
      A exigência de “não deixar o texto transbordar” traz muitos detalhes junto.
      Em PDF, cada letra, caractere e glifo do texto pode ter uma posição x,y exata na página, às vezes até fora dela.
      Assim, o conteúdo pode ser posicionado com precisão, independentemente do que houver ao redor. O aplicativo que usa PDF precisa posicionar os itens corretamente e implementar quebras de linha por caractere ou por palavra.
      O XPS foi o que chegou mais perto de reimplementar o PDF, mas a Microsoft não conseguiu apoio suficiente de outros atores, e ele desapareceu discretamente.
    • Uma coisa interessante sobre PDF que eu não sabia até recentemente é que ele é um subconjunto do PostScript, e isso explica parte do peso.
      O PostScript, embora peculiar, é uma linguagem de programação completa, mas o PDF não é. Ou seja, não é Turing-completo.
      O PDF não oferece suporte a fluxo de controle, então coisas que no PostScript poderiam ser expressas com um loop simples precisam ser expandidas em PDF e armazenadas como uma série de declarações ou expressões simples.
      A vantagem é que renderizar um PDF não exige um interpretador de programas completo.
    • Assim que uma conversa dessas começa, o pessoal do LaTeX aparece, e todos que poderiam contribuir de forma significativa para o padrão ficam travados nessa discussão.
    • Um motivo é que nenhum dos outros formatos, do jeito que são, é adequado para impressão comercial.