Posted in

Как читать данные с pdf через python 3 (PyPDF2)

Как извлечь данные pdf с помощью python3
Как извлечь данные pdf с помощью python3

Мониторил недавно запросы заказчиков на бирже и наткнулся на интересную задачу. Нужно было из сотни .pdf-файлов извлечь емейлы. И мне стало интересно как это сделать с python 3. Нашел для этого модуль PyPDF2. С его помощью и будем читать данные с пдф-файлов.

Как установить PyPDF2

Модуль ставится без проблем через pip. И на виндовс в том числе. Через командную строку выполните код:

pip install pypdf2

Спустя несколько секунд модуль установится.

Как открыть pdf-файл на питоне

Импортируем модуль PyPDF2, открываем файл через open в байтовом режиме.

import PyPDF2
pl = open('d:/bdseo.pdf', 'rb')

Обратите внимание – PyPDF2 нужно писать именно так: большие буквы, кроме ‘y’, иначе будет ошибка импорта библиотеки. И файл открывать в режиме ‘rb‘, не ‘r’.

Как прочитать pdf-файл на python 3

Для чтения содержимого файла pdf используется класс PdfFileReader. Код будет выглядеть вот так:

import PyPDF2
pl = open('d:/bdseo.pdf', 'rb')
plread = PyPDF2.PdfFileReader(pl)

Сначала импорт модуля, потом открываем файл. После этого читаем файл через PyPDF2.PdfFileReader.

Чтобы вывести количество страниц pdf-файла используйте такой код:

print(plread.numPages)

Как извлечь текст с pdf-файла с python 3

Сразу код, обьясню позже:

import PyPDF2
pl = open('d:/bdseo.pdf', 'rb')
plread = PyPDF2.PdfFileReader(pl)
getpage37 = plread.getPage(37)
text37 = getpage37.extractText()

Первые три строки мы уже знаем: импорт, открыть файл, прочитать его. Дальше мы берем 37 страниц (getPage(37)). И извлекаем оттуда текст – extractText().
Если нужно использовать кодировку, то при выводе (или записи в файл) используйте .encode:

print(text37.encode('utf-8'))

или

with open('c:/bdseoru_pdf.txt', 'w', encoding='utf-8') as fg:
    fg.write(text37)

Этот код записывает данные в файл bdseoru_pdf.txt.

Как извлечь данные с pdf-файла (емейл, телефоны и т.п.)

Как прочитать данные с pdf я уже написал. Емейлы и телефоны можно извлекать как с обычного текста – например, с помощью стандартного модуля RE, и масок регулярных выражений. Если кому интересно – спрашивайте.

10 thoughts on “Как читать данные с pdf через python 3 (PyPDF2)

  1. А если мне надо найти информацию по контексту в нескольких сот пдф файлов архив. И чтоб на выходе он мне выдавал что мол в таких и таких журналах есть ваша инфа. Я могу использовать ваш код в этом случае?

    1. Часть кода. Как я вижу решение задачи:
      1) в цикле for проходимся по файлам
      2) открываем пдф и ищем нет ли там подходящего текста
      3) если есть – выводим название файла

  2. Пытаюсь воспроизвести ваш код указав свой путь для файла.пидиэф

    pl = open(‘/home/prog/pyProject/devops.pdf’, ‘rb’)
    plread = PyPDF2.PdfFileReader(pl)

    Выдает ошибку:

    Traceback (most recent call last):
    File “search_pdf.py”, line 48, in <module>
    plread = PyPDF2.PdfFileReader(pl)
    File “/usr/lib/python3.7/site-packages/PyPDF2/pdf.py”, line 1084, in __init__
    self.read(stream)
    File “/usr/lib/python3.7/site-packages/PyPDF2/pdf.py”, line 1689, in read
    stream.seek(-1, 2)
    OSError: [Errno 22] Invalid argument

    Не подскажете, в чем может быть причина?

     

     

     

    1. Точно не подскажу, в сети пишут что есть такая проблема в некоторых пдф файлах. Попробуйте на другом, проверьте кавычки в пути, заэкранируйте слэши (r”/home/prog.pdf”).
      Может почитайте о PdfFileMerger (сам не пользовался, в сети нашел).

  3. Сделал как вы посоветовали плюс еще исправил одну ошибкую. Код работает вроде бы, колво строк в документе считает, но файл не открывается и ошибок не выдает:

    import PyPDF2
    pl = open(r'/home/py/technews.pdf', 'rb')
    plread = PyPDF2.PdfFileReader(pl, False)
    print(plread.numPages)
    

    Так должно быть? Логично что должен открыться редактор “пидиэф” и сам файл!?

    Далее добавляю следующий кусок вашего кода:

    getpage228 = plread.getPage(228)
    text228 = getpage365.extractText()

    и получаю ошибку:

    Traceback (most recent call last):
      File "search_pdf2.py", line 5, in <module>
        getpage228 = plread.getPage(228)
      File "/usr/lib/python3.7/site-packages/PyPDF2/pdf.py", line 1177, in getPage
        return self.flattenedPages[pageNumber]
    IndexError: list index out of range
    

    Видимо где то что то я пропустил? Подскажите пожалуйста, где.

    1. начну с конца. по поводу ошибки – он не видит 228 страницу, их меньше получается. Кроме того, Вы пишите getpage228, а в след.строке хотите вытянуть текст – с *365.
      вначале открываться ничего не должно, т.к. Вы написали только “вывести кол-во страниц” (print). 🙂

  4. Здравствуйте

    Вот моя программа

    import PyPDF2with open(‘2019_3_phys_r1.pdf’, ‘rb’) as vsesib:
    vsesib_read = PyPDF2.PdfFileReader(vsesib)
    print(vsesib_read.numPages)
    getpage = vsesib_read.getPage(0)
    text = getpage.extractText()
    with open(‘vsesib.txt’, ‘w’) as fout:
    fout.write(text)

    в vsesib.txt выводятся только цифры без слов. Проблема с кодировкой теста в пдф файле?

    1. Файл на каком языке?
      Попробуйте указать кодировку при сохранении:
      with open(‘vsesib.txt’, ‘w’, encoding='utf-8') as fout:
      Или какая подходит.

  5. Здравствуйте!
    Можете подсказать как вытащить из пдф только абзацы с текстом? То есть без заголовков и т.д. Есть ли какие-то маски для этого?

    1. Здравствуйте. Нужно смотреть конкретный файл. Есть ли в этом файле “заголовок”. Как “сказать компьютеру” что это заголовок или просто текст.

Leave a Reply

Your email address will not be published. Required fields are marked *