Я суслик, поэтому в этой статье будут перечислены все сценарии обработки pdf, с которыми я столкнулся, с точки зрения суслика, например:
pdf渲染
pdf校验
pdf加水印
pdf获取页数
pdf合并
pdf拆分
修复受损pdf
pdf转png
识别pdf中的字体
pdf解密
...
Большая часть этой статьи представляет собой список проблем сцены, вы можете извлечь интересующие вас части в соответствии с заголовком для просмотра.
Я не особенно профессионален во многих вопросах PDF.Если у вас есть какие-либо вопросы или вопросы, пожалуйста, не стесняйтесь общаться со мной.
1. Отрисовка HTML-страницы в формате PDF
Чтобы отобразить pdf на основе html-страницы, я использовал следующие две схемы:
- wkhtmltopdf
- chromedp
1. Рендерим pdf с помощью wkhtmltopdf
wkhtmltopdfИнструмент командной строки для рендеринга HTML-страниц в PDF, основанный на движке рендеринга Qt WebKit.
Использование относительно простое:
## 将一个静态html页面打印成pdf
$ wkhtmltopdf input.html output.pdf
## 将一个网页打印成pdf
$ wkhtmltopdf https://www.google.com output.pdf
Параметры wkhtmltopdf очень богаты, например:
Поддерживает отправку HTTP-запросов, подходит для рендеринга специально разработанных веб-страниц в файлы PDF:
$ wkhtmltopdf --help
...
--post <name> <value> Add an additional post field (repeatable)
...
Поддержка сценариев javascript для изменения html перед рендерингом pdf:
$ wkhtmltopdf --run-script "javascript:(function(){document.getElementsByClassName('dom_class_name')[0].style.display = 'none'}())" page input.html output.pdf
Более подробные параметры см.Официальная документация сайта
Если вы используете язык Go, есть также сторонний пакет, который включает использование wkhtmltopdf:go-wkhtmltopdf
2. Используйте chromedp для рендеринга PDF
chromedp— это пакет в Go, который обеспечивает более быстрый и простой способ управления браузерами, поддерживающими протокол Chrome DevTools, без внешних зависимостей (таких как Selenium или PhantomJS).
Как пользоваться:
package main
import (
"context"
"io/ioutil"
"github.com/chromedp/cdproto/page"
"github.com/chromedp/chromedp"
"errors"
)
func main(){
err := ChromedpPrintPdf("https://www.google.com", "/path/to/file.pdf")
if err != nil {
fmt.Println(err)
return
}
}
func ChromedpPrintPdf(url string, to string) error {
ctx, cancel := chromedp.NewContext(context.Background())
defer cancel()
var buf []byte
err := chromedp.Run(ctx, chromedp.Tasks{
chromedp.Navigate(url),
chromedp.WaitReady("body"),
chromedp.ActionFunc(func(ctx context.Context) error {
var err error
buf, _, err = page.PrintToPDF().
Do(ctx)
return err
}),
})
if err != nil {
return fmt.Errorf("chromedp Run failed,err:%+v", err)
}
if err := ioutil.WriteFile(to, buf, 0644); err != nil {
return fmt.Errorf("write to file failed,err:%+v", err)
}
return nil
}
2. Водяные знаки PDF
Инструменты, которые я изучил, которые поддерживают водяные знаки PDF:
- unidoc/unipdf
- pdfcpu
1.unidoc/unipdf
unidocплатформа разработанаunipdfЭто библиотека PDF, написанная на языке Go, которая предоставляет режимы использования API и CLI и поддерживает следующие функции:
$ unipdf -h
...
Available Commands:
decrypt Decrypt PDF files
encrypt Encrypt PDF files
explode Explodes the input file into separate single page PDF files
extract Extract PDF resources
form PDF form operations
grayscale Convert PDF to grayscale
help Help about any command
info Output PDF information
merge Merge PDF files
optimize Optimize PDF files
passwd Change PDF passwords
rotate Rotate PDF file pages
search Search text in PDF files
split Split PDF files
version Output version information and exit
watermark Add watermark to PDF files
...
Добавить водяной знак в режиме CLI
$ unipdf watermark in.pdf watermark.png -o out.pdf
Watermark successfully applied to in.pdf
Output file saved to out.pdf
Используйте API для добавления водяного знака, вы можете обратиться напрямуюunipdf github example
Примечание: за лицензию на использование продуктов unidoc необходимо заплатить.
2.pdfcpu
pdfcpuЭто библиотека обработки PDF, написанная на языке Go, предоставляющая API и режим CLI для использования.
Поддерживаются следующие функции:
$ pdfcpu help
...
The commands are:
attachments list, add, remove, extract embedded file attachments
changeopw change owner password
changeupw change user password
decrypt remove password protection
encrypt set password protection
extract extract images, fonts, content, pages, metadata
fonts install, list supported fonts
grid rearrange pages or images for enhanced browsing experience
import import/convert images to PDF
info print file info
merge concatenate 2 or more PDFs
nup rearrange pages or images for reduced number of pages
optimize optimize PDF by getting rid of redundant page resources
pages insert, remove selected pages
paper print list of supported paper sizes
permissions list, set user access permissions
rotate rotate pages
split split multi-page PDF into several PDFs according to split span
stamp add, remove, update text, image or PDF stamps for selected pages
trim create trimmed version of selected pages
validate validate PDF against PDF 32000-1:2008 (PDF 1.7)
version print version
watermark add, remove, update text, image or PDF watermarks for selected pages
...
Добавьте водяной знак на изображение с помощью инструмента CLI:
$ pdfcpu watermark add -mode image 'voucher_watermark.png' 's:1 abs, rot:0' in.pdf out.pdf
вызовите API, чтобы добавить водяной знак
package main
import (
"github.com/pdfcpu/pdfcpu/pkg/api"
"github.com/pdfcpu/pdfcpu/pkg/pdfcpu"
)
func main() {
onTop := false
wm, _ := pdfcpu.ParseImageWatermarkDetails("watermark.png", "s:1 abs, rot:0", onTop)
api.AddWatermarksFile("in.pdf", "out.pdf", nil, wm, nil)
}
3. Слияние PDF
- cpdf
- unipdfc
- pdfcpu
1. Объединить pdf с помощью cpdf
cpdfЭто бесплатная библиотека инструментов командной строки PDF с открытым исходным кодом с богатыми функциями, такими как:
- Merge PDF files together, or split them apart
- Encrypt and decrypt
- Scale, crop and rotate pages
- Read and set document info and metadata
- Copy, add or remove bookmarks
- Stamp logos, text, dates, page numbers
- Add or remove attachments
- Losslessly compress PDF files
Объединить PDF-файлы:
$ cpdf -merge input1.pdf input2.pdf -o output.pdf
2. Объединить pdf с помощью unipdf
$ unipdf merge output.pdf input1.pdf input2.pdf
Используйте API для слияния PDF, ссылкаunpdf github example
3. Объединить pdf с помощью pdfcpu
$ pdfcpu merge output.pdf input1.pdf input2.pdf
Примечание. pdfcpu поддерживает только файлы PDF с версиями ниже PDF V1.7.
4. Разделить PDF
- cpdf
- unipdf
- pdfcpu
1. Разделить pdf с помощью cpdf
## 逐页拆分成单个pdf
$ cpdf -split in.pdf 1 even -chunk 1 -o ./out%%%.pdf
2. Разделить pdf с помощью unipdf
## 将第一页拆分出来
$ unipdf split input.pdf out.pdf 1-1
Разделить pdf с помощью API, ссылкаunipdf github examples
3. Разделить PDF с помощью pdfcpu
$ pdfcpu split in.pdf .
5. Преобразование PDF в изображение
- mupdf
- xpdf
1. Используйте mupdf для работы с pdf в изображение
MuPDF is a lightweight PDF, XPS, and E-book viewer.
MuPDF consists of a software library, command line tools, and viewers for various platforms.
После загрузки mupdf вы получаете некоторые инструменты, такие как:
mupdf
pdfdraw
pdfinfo
pdfclean
pdfextract
pdfshow
xpsdraw
вpdfdraw
Может использоваться для преобразования изображений
$ pdfdraw -o out%d.png in.pdf
2. Используйте xpdf для работы с pdf в изображение
xpdfЭто бесплатный PDF Toolkit, включая анализ текста, преобразование изображения, преобразование HTML и т. Д.
Скачав пакет, вы можете получить ряд инструментов:
pdfdetach
pdffonts
pdfimages
pdfinfo
pdftohtml
pdftopng
pdftoppm
pdftops
pdftotext
Из названия можно примерно понять полезность каждого инструмента.
## 使用pdftopng将pdf转换成png
$ pdftopng in.pdf out-prefix
Шесть, расшифровка PDF
Я часто сталкиваюсь со сценарием, когда при чтении pdf-файла сообщается об ошибке: файл зашифрован
Но как это решить без пароля?
- расшифровать с помощью qpdf
использоватьqpdfВыполните принудительную расшифровку.В некоторых случаях расшифровка может быть успешной, но в некоторых случаях расшифровка может быть неудачной.
qpdf — это инструмент для работы с PDF, поддерживающий командную строку.
$ qpdf --decrypt in.pdf out.pdf
- расшифровать с помощью pdfcpu
$ pdfcpu decrypt encrypted.pdf output.pdf
Когда есть пароль, его можно расшифровать с помощью пароля:
- расшифровать pdf с помощью unipdf
$ unipdf decrypt -p pass -o output.pdf input.pdf
Семь, распознавание PDF
Я часто сталкиваюсь с некоторыми сценариями, такими как распознавание того, является ли файл файлом pdf, распознавание текста в pdf, распознавание изображений в pdf и т. д.
1. Распознать текст в PDF
Как используется здесь, pdf xpdf анализирует текст, а затем использует некоторые манипуляции со строками регулярных выражений или бизнес-анализ.
- использовать
xpdf/pdftotext
Разобрать текст в pdf
$ pdftotext input.pdf output.txt
- использовать
unipdf
Разобрать текст в pdf
$ unipdf extract text input.pdf
Разобрать текст в формате pdf с помощью API, ссылкаunipdf github examples
- Разбор данных PDF с использованием информации координаты
Вышеупомянутое состоит в том, чтобы сначала проанализировать текст pdf, а затем обработать его в соответствии с бизнес-процессами.
Другой способ состоит в том, чтобы проанализировать PDF-файл в соответствии с положением координат, что является более гибким и общим, с использованиемpdflib/tet
## 输入一组坐标,即可按照坐标解析pdf中的数据
$ tet --pageopt "includebox={{38 707.93 243.91 716.93}}" input.pdf
Координаты могут использовать tet для анализа pdf, чтобы получить файл tetml, который содержит информацию о координатах:
$ tet --tetml input.pdf
Конечно, вы также можете использовать некоторые другие методы для получения информации о координатах данных в pdf, такие как nodejs и т. д.
Уведомление:
pdflib/tet
Это платное программное обеспечение, но согласно официальной документации, tet предоставляет базовые функции, и вам не нужно приобретать лицензию для обработки pdf-файлов объемом не более 10 страниц или менее 1M.
pdflib/tet
Он предоставляет инструменты командной строки и поддержку языков SDK, таких какC/C++/Java/.NET/Perl/PHP/Python/Ruby/Swift
Но язык Go пока не поддерживается, поэтому на данный момент есть только два варианта gopher: CLI ИЛИ CGO
8. Восстановить поврежденные PDF-файлы
Есть некоторые PDF-файлы, которые выглядят нормально при открытии на компьютере, но являются ненормальными при обнаружении кодом, например при попытке использовать стороннюю библиотеку для анализа (поврежденного) PDF-файла в Go:
import (
"fmt"
"github.com/rsc.io/pdf"
)
func main() {
filePath := "path/to/your/broken.pdf"
_, err := pdf.Open(filePath)
if err != nil {
fmt.Println("open pdf failed,err:", err.Error())
return
}
}
После запуска вы получите такой результат:
open pdf failed,err: malformed PDF: cross-reference table not found: {5 0 obj}<</Contents 6 0 R /Group <</CS /DeviceRGB /S /Transparency /Type /Group>> /MediaBox [0 0 595.27600098 841.89001465] /Parent 3 0 R /Type /Page>>
Компьютер включается нормально, но программа читает ошибку!
В это время, если вы попытаетесь открыть pdf-файл на компьютере, затем сохраните его как новый pdf-файл, а затем используете код для его обнаружения, вы обнаружите, что он был восстановлен!
Отлично, проблема решена!
И так, если у меня 1000 pdf файлов, вы же не хотите открывать по одному и сохранять как? Как вы можете быть в состоянии?Так что, если есть функция пакетного восстановления просто отлично
После долгих поисков в интернете я нашел примерно три решения:
- Используя Acrobat SDK, вызовите SDK всохранить как функцию, можно реализовать эффект открытия сохранения как на компе
- восстановление pdf с помощью ghostscript
- использоватьmupdfсделать ремонт пдф
Здесь я только проверил, что третий способ выполним, здесь я используюmupdf-0.9-linux-amd64
Проверить эту версию
После загрузки пакета я получил один из исполняемых файлов:pdfclean
$ pdfclean broken.pdf repaired.pdf
+ pdf/pdf_xref.c:160: pdf_read_trailer(): cannot recognize xref format: '%'
| pdf/pdf_xref.c:481: pdf_load_xref(): cannot read trailer
\ pdf/pdf_xref.c:537: pdf_open_xref_with_stream(): trying to repair
Судя по выводу, mupdf попробовал процесс восстановления
После получения нового файла PDF попробуйте открыть его с помощью предыдущего кода Go, это нормально.
Осталось написать bash-скрипт, пакетно фиксить и цель достигнута!
Девять, информация об идентификации шрифта файла PDF
Иногда необходимо поддерживать согласованность нескольких текстовых шрифтов PDF, чтобы не анализировать, какие шрифты используются в PDF, в настоящее время вы можете использовать
xpdf/pdffonts
Выполнить анализ шрифта
$ pdffonts input.pdf
name type encoding emb sub uni object ID
------------------------------------ ----------------- ---------------- --- --- --- ---------
NimbusSanL-Regu CID TrueType Identity-H yes no yes 10 0
NimbusSanL-Bold CID TrueType Identity-H yes no yes 20 0
Другое введение Libiray
Это библиотека с открытым исходным кодом C++, которая поддерживает создание PDF-файлов, объединение PDF-файлов, манипулирование текстом водяных знаков изображения и т. д.
Для gopher, чтобы использовать эту библиотеку, вам нужно инкапсулировать слой кода CGO.
Это библиотека PDF, реализованная на языке Go, которую можно использовать для чтения информации в формате PDF, такой как чтение содержимого PDF/номера страниц/шрифта и т. д. Для получения подробной информации см.Документация
Представляя так много сторонних библиотек, он просто разнообразен, каждая проявляет свои магические силы. Некоторые функции повторяются в большинстве библиотек, и какие проблемы могут возникнуть при конкретном использовании, зависит от реальной ситуации.
Надеюсь, что эти резюме будут полезны читателям
Ссылаться на: