2009-07-24 110 views
60

Necesito agregar texto adicional a un PDF existente usando Python, cuál es la mejor manera de hacerlo y qué módulos adicionales necesitaré instalar.Agregar texto a PDF existente usando Python

Nota: Idealmente, me gustaría poder ejecutar esto tanto en Windows como en Linux, pero con un solo empujón Linux solo lo hará.

Gracias de antemano.
Richard.

Editar: pyPDF y ReportLab se ven bien pero ninguno me permite editar un PDF existente, ¿hay alguna otra opción?

Respuesta

63

Sé que esto es un mensaje de más edad, pero pasé mucho tiempo tratando de encontrar una solución. Me encontré con una decente utilizando sólo ReportLab y PyPDF así que pensé que me gustaría compartir:

  1. leído su PDF usando PdfFileReader(), que llamaremos esta entrada
  2. crear un nuevo PDF que contiene su texto para añadir usando ReportLab, guardar esto como un objeto de cadena
  3. leer el objeto de cadena usando PdfFileReader(), que llamaremos este texto
  4. crear un nuevo objeto PDF utilizando PdfFileWriter(), que llamaremos este salida
  5. iterar a través de la entrada y aplicar .mergePage (texto .getPage (0)) para cada página que desea que el texto añadido a, a continuación, utilizar la salida .addPage() para agregar las páginas modificadas a un nuevo documento

Esto funciona bien para las adiciones de texto simples. Vea la muestra de PyPDF para filmar un documento con marca de agua.

Aquí hay un código para responder a la siguiente pregunta:

packet = StringIO.StringIO() 
can = canvas.Canvas(packet, pagesize=letter) 
<do something with canvas> 
can.save() 
packet.seek(0) 
input = PdfFileReader(packet) 

Desde aquí se puede fusionar las páginas del archivo de entrada con otro documento

+1

"cree un nuevo pdf que contenga su texto para agregar usando ReportLab, guárdelo como un objeto de cadena" ¿Cómo lo hace? Es una instancia de lienzo. –

+1

He agregado un código de muestra anterior para responder la pregunta de Lakshman. – dwelch

+1

Esta respuesta es dorada, funciona como un encanto. –

0

Puede tener más suerte rompiendo el problema en la conversión de PDF en un formato editable, escribiendo sus cambios, y luego convirtiéndolo de nuevo en PDF. No conozco una biblioteca que le permita editar PDF directamente, pero hay muchos convertidores entre DOC y PDF, por ejemplo.

+1

problema es que sólo tengo la fuente en PDF (de una tercera parte) y PDF -> DOC -> PDF perderá mucho en la conversión. También necesito que esto se ejecute en Linux para que DOC no sea la mejor opción. – Frozenskys

+0

Creo que Adobe mantiene la capacidad de edición de PDF bastante cerrada y propietaria para que puedan vender licencias para sus mejores versiones de Acrobat. Tal vez pueda encontrar una manera de automatizar el uso de Acrobat Pro para editarlo, utilizando algún tipo de interfaz de macro. – aehlke

+0

Si las partes que desea escribir son campos de formulario, existen interfaces XML para editarlas; de lo contrario, no puedo encontrar nada. – aehlke

-2

¿Has probado pyPdf?

Lo sentimos, no tiene la capacidad de modificar el contenido de una página.

+0

Parece que eso podría funcionar, ¿alguien lo usó? ¿Cómo es el uso de la memoria? – Frozenskys

+0

Tiene la capacidad de agregar una marca de agua de texto y si se formateó correctamente podría funcionar. – Frozenskys

1

Si estás en Windows, esto podría funcionar:

PDF Creator Pilot

También hay un libro blanco de un marco de creación de PDF y la edición en Python. Es un poco anticuado, pero tal vez le puede dar algo de información útil:

Using Python as PDF Editing and Processing Framework

+0

¡El libro blanco se ve bien pero tiene poca luz en el código, y realmente no tengo el recurso para implementar un marco completo de PDF! ;) – Frozenskys

68

Aquí es una respuesta completa que he encontrado en otro lugar [Python 2.7]:

from pyPdf import PdfFileWriter, PdfFileReader 
import StringIO 
from reportlab.pdfgen import canvas 
from reportlab.lib.pagesizes import letter 

packet = StringIO.StringIO() 
# create a new PDF with Reportlab 
can = canvas.Canvas(packet, pagesize=letter) 
can.drawString(10, 100, "Hello world") 
can.save() 

#move to the beginning of the StringIO buffer 
packet.seek(0) 
new_pdf = PdfFileReader(packet) 
# read your existing PDF 
existing_pdf = PdfFileReader(file("original.pdf", "rb")) 
output = PdfFileWriter() 
# add the "watermark" (which is the new pdf) on the existing page 
page = existing_pdf.getPage(0) 
page.mergePage(new_pdf.getPage(0)) 
output.addPage(page) 
# finally, write "output" to a real file 
outputStream = file("destination.pdf", "wb") 
output.write(outputStream) 
outputStream.close() 

Y aquí es una actualización para Python 3.x:


from PyPDF2 import PdfFileWriter, PdfFileReader 
import io 
from reportlab.pdfgen import canvas 
from reportlab.lib.pagesizes import letter 

packet = io.BytesIO() 
# create a new PDF with Reportlab 
can = canvas.Canvas(packet, pagesize=letter) 
can.drawString(10, 100, "Hello world") 
can.save() 

#move to the beginning of the StringIO buffer 
packet.seek(0) 
new_pdf = PdfFileReader(packet) 
# read your existing PDF 
existing_pdf = PdfFileReader(open("original.pdf", "rb")) 
output = PdfFileWriter() 
# add the "watermark" (which is the new pdf) on the existing page 
page = existing_pdf.getPage(0) 
page.mergePage(new_pdf.getPage(0)) 
output.addPage(page) 
# finally, write "output" to a real file 
outputStream = open("destination.pdf", "wb") 
output.write(outputStream) 
outputStream.close() 
+8

Para python3, el paquete debe ser 'io.BytesIO' y use PyPDF2 en lugar de pyPDF (que no se mantiene). ¡Gran respuesta! –

+3

Gracias por compartir. Funciona muy bien. Una nota: creo que es mejor usar 'abrir' en lugar de' archivo'. – mitenka

+0

Creo que esta es una respuesta más aceptable, especialmente porque incluye un ejemplo de trabajo. – Casey

2

cpdf va a hacer el trabajo desde la línea de comandos. No es pitón, aunque (que yo sepa):

cpdf -add-text "Line of text" input.pdf -o output .pdf 
3

pdfrw le permitirá leer en las páginas de un PDF existente y atraerlos a un lienzo reportlab (similar a dibujar una imagen). Hay ejemplos para esto en el subdirectorio pdfrw examples/rl1 en github. Descargo de responsabilidad: soy el autor pdfrw.

+0

Creo que podrías poner un enlace allí – The6thSense

+0

¡Buen punto! No había hecho mucho SO cuando publiqué eso, y estaba preocupado por la "política de texto mínimo más enlace". (Mi representante solo tenía 46 años en ese momento, y IIRC acababa de recibir un -2 en una respuesta, por lo que estaba un poco preocupado por las respuestas nuevas a las preguntas de 5 años :) –

+0

preguntas antiguas tiene más visión :) y atención – The6thSense

3

Aprovechando David Dehghan 's answer anterior, las siguientes obras en Python 2.7.13:

from PyPDF2 import PdfFileWriter, PdfFileReader, PdfFileMerger 

import StringIO 

from reportlab.pdfgen import canvas 
from reportlab.lib.pagesizes import letter 

packet = StringIO.StringIO() 
# create a new PDF with Reportlab 
can = canvas.Canvas(packet, pagesize=letter) 
can.drawString(290, 720, "Hello world") 
can.save() 

#move to the beginning of the StringIO buffer 
packet.seek(0) 
new_pdf = PdfFileReader(packet) 
# read your existing PDF 
existing_pdf = PdfFileReader("original.pdf") 
output = PdfFileWriter() 
# add the "watermark" (which is the new pdf) on the existing page 
page = existing_pdf.getPage(0) 
page.mergePage(new_pdf.getPage(0)) 
output.addPage(page) 
# finally, write "output" to a real file 
outputStream = open("destination.pdf", "wb") 
output.write(outputStream) 
outputStream.close() 
Cuestiones relacionadas