Quantcast

Pdf - Incremental Updates

classic Classic list List threaded Threaded
10 messages Options
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Pdf - Incremental Updates

linuxunil
Using: iText v 5.4.3 - Jdk 1.7_u25 32bit

I wonder how do I save pdf files with incremental updates.

Reading the PDF format specification v1.7, section 3.4.5 page 98
http://www.adobe.com/content/dam/Adobe/en/devnet/acrobat/pdfs/pdf_reference_1-7.pdf
Talks about "Incremental Updates." Read this section for more info.

At the moment, I get a pdf template from server, fill in a few fields, and sign.

Then reopen the document, and use the method:
pdfStamperInstance.getAcroFields (). extractRevision ("SignatureFieldNameHere");

That gives me an InputStream. According to the documentation of iText, this inputStream is the revision of pdf document associated with the signature.

I transfer this revision to the server. On the server, i want to add this revision in the same template and save.

The class PdfStamper already has a constructor that seems pretty close to what I need:

//From the iText API
PdfStamper (PdfReader reader, OutputStream them, pdfVersion char, boolean append)
Starts the process of adding extra content to an existing PDF document, possibly as a new revision.

So i trying:
  - I create an instance of the PdfReader reading the pdf template
  - I create an instance of the above PdfStamper using the constructor:
    //outputFileFos is a FileOutputStream
     new PdfStamper (reader, outputFileFos, '\ 0', true);

How i do append the revision on the stamper instance?
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

linuxunil
This post was updated on .
And for some reason the method pdfStamperInstance.getAcroFields ().extractRevision() is returning an empty inputStream (avaible () = 0).

When i run the method I get an object that contains the following:
- RASInputStream
   - Position: 0
   - Source: WindowRandomAcessSource
     - Length: 564167 / / <--- actual size of the revision
     - Offset: 0
     - Source: IndependentRandomAcessSource
        - Source: IndependentRandomAcessSource
           - Source: ArrayRandomAcessSource
             - array
                (0 ... 564167) / / <---- byte[] of same size

But when trying to execute read() on this object, the method returns nothing (byte[0]).
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

info-2
On 9/2/2013 11:00 PM, linuxunil wrote:
> And for some reason the method pdfStamper.extractRevision() is returning an
> empty inputStream (avaible () = 0).
Extract revision is about extracting signed revision.
If you don't have any signatures in your file, you won't be able to
extract revisions.

------------------------------------------------------------------------------
Learn the latest--Visual Studio 2012, SharePoint 2013, SQL 2012, more!
Discover the easy way to master current and previous Microsoft technologies
and advance your career. Get an incredible 1,500+ hours of step-by-step
tutorial videos with LearnDevNow. Subscribe today and save!
http://pubads.g.doubleclick.net/gampad/clk?id=58040911&iu=/4140/ostg.clktrk
_______________________________________________
iText-questions mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/itext-questions

iText(R) is a registered trademark of 1T3XT BVBA.
Many questions posted to this list can (and will) be answered with a reference to the iText book: http://www.itextpdf.com/book/
Please check the keywords list before you ask for examples: http://itextpdf.com/themes/keywords.php
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

info-2
In reply to this post by linuxunil
On 9/2/2013 10:01 PM, linuxunil wrote:
> How i do append the revision on the stamper instance?
You're creating a PDF that is incrementally updated.
Are you signing that update? If not, all you have is an incrementally
updated PDF, not a signed revision.

------------------------------------------------------------------------------
Learn the latest--Visual Studio 2012, SharePoint 2013, SQL 2012, more!
Discover the easy way to master current and previous Microsoft technologies
and advance your career. Get an incredible 1,500+ hours of step-by-step
tutorial videos with LearnDevNow. Subscribe today and save!
http://pubads.g.doubleclick.net/gampad/clk?id=58040911&iu=/4140/ostg.clktrk
_______________________________________________
iText-questions mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/itext-questions

iText(R) is a registered trademark of 1T3XT BVBA.
Many questions posted to this list can (and will) be answered with a reference to the iText book: http://www.itextpdf.com/book/
Please check the keywords list before you ask for examples: http://itextpdf.com/themes/keywords.php
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

linuxunil
This post was updated on .
1 - I get the template from the server
2 - I open, fill some fields AND SIGN.
3 - I REOPEN the file (2) and execute the code: pdfStamperInstance.getAcroFields ().extractRevision("signatureFieldNameHere")
4 - The inputStream return an empty inputStream (avaible() = 0).

After i get an valid inputStream, i want to send it back to the server and append the revision on the template again.
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

info-2
Op 3/09/2013 19:17, linuxunil schreef:
> 3 - I*REOPEN*  the file (2) and execute the code:
> pdfStamper.extractRevision("signatureFieldNameHere")
If "signatureFieldNameHere" is the name of the signature field used in
2, then what's the point of extracting the revision? The revision is the
whole file. I really don't understand the question, and I doubt it
anyone else does.

------------------------------------------------------------------------------
Learn the latest--Visual Studio 2012, SharePoint 2013, SQL 2012, more!
Discover the easy way to master current and previous Microsoft technologies
and advance your career. Get an incredible 1,500+ hours of step-by-step
tutorial videos with LearnDevNow. Subscribe today and save!
http://pubads.g.doubleclick.net/gampad/clk?id=58040911&iu=/4140/ostg.clktrk
_______________________________________________
iText-questions mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/itext-questions

iText(R) is a registered trademark of 1T3XT BVBA.
Many questions posted to this list can (and will) be answered with a reference to the iText book: http://www.itextpdf.com/book/
Please check the keywords list before you ask for examples: http://itextpdf.com/themes/keywords.php
mkl
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

mkl
In reply to this post by linuxunil
linuxunil,
linuxunil wrote
1 - I get the template from the server
2 - I open, fill some fields AND SIGN.
3 - I REOPEN the file (2) and execute the code: pdfStamper.extractRevision("signatureFieldNameHere")
The iText class PdfStamper does not have a method extractRevision. Unless your pdfStamper is an instance of something entirely else, your code execution stops no later than here.

Furthermore, if you re-open the file, I would expect you to use a PdfReader.

Thus, your description somehow does not make sense. It might help, therefore, if you provided a SSCCE illustrating your issue.

This all being said,
4 - The inputStream return an empty inputStream (avaible() = 0).
No, the InputStream is not empty, your interpretation of the available() method is wrong.

available() "Returns an estimate of the number of bytes that can be read (or skipped over) from this input stream without blocking" (cf the InputStream JavaDocs). So it is a) only an estimate of b) bytes readable without blocking, not bytes overall. Thus, it doesn't say anything about the bytes that can actually be read.

In the case at hand, the InputStream returned is a com.itextpdf.text.io.RASInputStream which does not override the default implementation of that method which always returns 0.

You can simply read the revision from that stream.

Regards,   Michael
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

linuxunil
This post was updated on .
In reply to this post by info-2
Using: iText v 5.4.3 - Jdk 1.7_u25 32bit

First, read the PDF format specification v1.7, section 3.4.5 page 98
http://www.adobe.com/content/dam/Adobe/en/devnet/acrobat/pdfs/pdf_reference_1-7.pdf
Talks about "Incremental Updates." Read this section for more info of what I'm talking here.

Second, in my previous posts when I referred to pdfStamper.extractRevision () I was actually referring to me pdfStamperInstance.getAcroFields().extractRevision();

I edited my previous posts to make it clear.

Third, let it clear what I'm trying to do:
I have files that are signed multiple times. The first time the file is requested flow is as follows:

1 - I get a template server.
2 - I open this file fill some fields and sign. Saved and closed the file.
3 - We reopen this file and try to extract the file revision.
4 - Mando InputStream to the revision to the server.
5 - The server receives the inputStream and must make a revision in the append template.

If is the second (or later) that file is requested, the file to be sent to the client will be the last appended update.

Below the code:

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.security.GeneralSecurityException;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.pdf.AcroFields;
import com.itextpdf.text.pdf.PdfReader;
import com.itextpdf.text.pdf.PdfStamper;

public class ItextIncrementalUpdater {

        public static void main(String[] args)
                throws IOException, DocumentException, GeneralSecurityException {
                //-------------------------------------------------
                // Filling and signing pdf
                //Here we simulate a server sending the template and
                //the client filling the fields and sign
                //-------------------------------------------------
                System.out.println("#> FILLING PDF");
               
                File pdfTemplate = new File("template.pdf");
                FileInputStream pdfTemplateFis = new FileInputStream(pdfTemplate);
                byte[] pdfTemplateFisBuffer = new byte[pdfTemplateFis.available()];
                pdfTemplateFis.read(pdfTemplateFisBuffer);
                pdfTemplateFis.close();
               
                File outputFilled1Pdf = new File("filled1.pdf");
                FileOutputStream outputFilled1PdfFos = new FileOutputStream(outputFilled1Pdf);
               
                PdfReader reader = new PdfReader(pdfTemplateFisBuffer);
                PdfStamper stamper = new PdfStamper(reader, outputFilled1PdfFos);
               
                AcroFields fields = stamper.getAcroFields();
                fields.setField("FIELD1", "VALUE_FOR_FIELD_1");
               
                stamper.close();
                reader.close();
                outputFilled1PdfFos.flush();
                outputFilled1PdfFos.close();
               
                System.out.println("#> SIGNING PDF");
                File outputSignedPdf = new File("outputSig1.pdf");
               
                //ItextSmartCardPdfSigner is my signer class
                ItextSmartCardPdfSigner signer = new ItextSmartCardPdfSigner("smartCardPasswordHere".toCharArray());
                signer.sign(outputFilled1Pdf, outputSignedPdf, "reason", "local", "contact", 0, 1, "SignatureFieldNameHere");
               
                System.out.println("#> PDF SIGNED");
               
                //-------------------------------------------------
                // Extracting Revision
                //Here we intend to extract the revison on the
                //client side to send only the revision back to server
                //-------------------------------------------------
                System.out.println("#> LOADING SIGNED FILE");
                FileInputStream pdfSignedFis = new FileInputStream(outputSignedPdf);
                byte[] pdfSignedBuffer = new byte[pdfSignedFis.available()];
                pdfSignedFis.read(pdfSignedBuffer);
                pdfSignedFis.close();
               
                File revisionFile = new File("revision.pdf");
                FileOutputStream revisionFos = new FileOutputStream(revisionFile);
               
                PdfReader reader2 = new PdfReader(pdfSignedBuffer);
                PdfStamper stamper2 = new PdfStamper(reader2, revisionFos);
               
                System.out.println("#> EXTRACTING REVISION");
                AcroFields revisionFields = stamper2.getAcroFields();
                InputStream revisionIs = revisionFields.extractRevision("Sig1"); //<-- revision is supposed to be here
               
                System.out.println("#> INPUTSTREAM AVAIBLE COUNT : " + revisionIs.available());
               
                byte[] revisionBuffer = new byte[revisionIs.available()];
                revisionIs.read(revisionBuffer);
                revisionIs.close();
                System.out.println("##> REVISION SIZE " + revisionBuffer.length);
               
                String revisionStr = new String(revisionBuffer);
                System.out.println(revisionStr);
               
                stamper2.close();
                reader2.close();
                revisionFos.flush();
                revisionFos.close();
                System.out.println("#> END OF REVISION EXTRACT");
                //-------------------------------------------------
                // Incremental Update (!i want to know how to do this part!)
                //Here we simulate the server received the revision
                //and is trying to append the revision on the template
                //-------------------------------------------------
                System.out.println("#> STARTING THE INCREMENTAL UPDATE");
               
                FileInputStream templateFis = new FileInputStream(pdfTemplate);
                byte[] templateFisBuffer = new byte[templateFis.available()];
                templateFis.read(templateFisBuffer);
                templateFis.close();
               
                File outputFile = new File("out.pdf");
                FileOutputStream fos = new FileOutputStream(outputFile);
               
                fos.write(templateFisBuffer);
                fos.flush();
               
                fos.write(revisionBuffer);
                fos.flush();
               
                fos.close();
               
                System.out.println("#> END OF THE INCREMENTAL UPDATE");
        }
       
}
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

info-2
On 9/4/2013 8:18 PM, linuxunil wrote:
> First, read the PDF format specification v1.7, section 3.4.5 page 98
> http://www.adobe.com/content/dam/Adobe/en/devnet/acrobat/pdfs/pdf_reference_1-7.pdf
> Talks about "Incremental Updates." Read this section for more info of what
> I'm talking here.

We know ISO-32000-1 inside-out, we know what incremental updates are.

> Second, in my previous posts when I referred to pdfStamper.extractRevision
> () I was actually referring to me
> pdfStamperInstance.getAcroFields().extractRevision();

Incremental updates is a means to create a signed revision, however, not
every incremental update is a revision.
Are you mixing the concepts of incremental updates and signed revisions?

> 1 - I get a template server.

The concept of a "template server" is unknown. You probably mean: I get
a template from a server.

> 2 - I open this file fill some fields and sign. Saved and closed the file.

 From your code, it's impossible to detect whether or not you sign in
append mode.
To fill out the form, you use: PdfStamper stamper = new
PdfStamper(reader, outputFilled1PdfFos);
This means you are NOT creating an incremental update.
To sign the form, you use:
ItextSmartCardPdfSigner signer = new
ItextSmartCardPdfSigner("smartCardPasswordHere".toCharArray());
signer.sign(outputFilled1Pdf, outputSignedPdf, "reason", "local",
"contact", 0, 1, "SignatureFieldNameHere";
We can't GUESS if you're creating an incremental update, and you're not
telling us.

> 3 - We reopen this file and try to extract the file revision.

???
This requirement is absurd. You don't have a revision.
There's only one signature!

> 4 - Mando InputStream to the revision to the server.

What is "Mando"?

> 5 - The server receives the inputStream and must make a revision in the
> append template.

What is this requirement about? I don't understand what you mean.
Let's take a look at the code:

> //-------------------------------------------------
> // Incremental Update (!i want to know how to do this part!)
> //Here we simulate the server received the revision
> //and is trying to append the revision on the template
> //-------------------------------------------------

Do you want to append something to the UNSIGNED filled out form?
Do you want to append something to the SIGNID filled out form?
What are you trying to append to what?
Why would you need the template? You've already filled it out?

> System.out.println("#> STARTING THE INCREMENTAL UPDATE");
>
> FileInputStream templateFis = new FileInputStream(pdfTemplate);
> byte[] templateFisBuffer = new byte[templateFis.available()];
> templateFis.read(templateFisBuffer);
> templateFis.close();

This is your original template.

>
> File outputFile = new File("out.pdf");
> FileOutputStream fos = new FileOutputStream(outputFile);
>
> fos.write(templateFisBuffer);
> fos.flush();
>
> fos.write(revisionBuffer);
> fos.flush();
>
> fos.close();
>
> System.out.println("#> END OF THE INCREMENTAL UPDATE");
> }
>
> }

Ouch... you're doing something completely wrong!

You have a file that starts with %PDF-1.7 and ends with %%EOF.
If you fill out that form in append mode (incremental update, something
you DON'T do), then you add extra stuff after the last %%EOF and you add
an extra %%EOF.
If you sign that form in append mode, you add extra stuff after that
%%EOF and you add another %%EOF.

The COMPLETE file is a single revision. Only when you add another
signature in append mode, you create another revision. That COMPLETE
file is the second revision.

You are making the following false assumptions:
1. you think you are filling out the form in append mode, but you don't.
2. you assume that a revision is the part that is added after the
original %%EOF, but it isn't.

In short: you think something isn't working in iText based on the wrong
interpretation of the concepts incremental update and revision. iText
can extract revisions, but iText doesn't have any functionality to
return different stages in an incremental update. Why would iText need
such functionality? Getting the different updates is only a matter of
finding one of the previous %%EOF markers and removing all the bytes
that follow it.

------------------------------------------------------------------------------
Learn the latest--Visual Studio 2012, SharePoint 2013, SQL 2012, more!
Discover the easy way to master current and previous Microsoft technologies
and advance your career. Get an incredible 1,500+ hours of step-by-step
tutorial videos with LearnDevNow. Subscribe today and save!
http://pubads.g.doubleclick.net/gampad/clk?id=58041391&iu=/4140/ostg.clktrk
_______________________________________________
iText-questions mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/itext-questions

iText(R) is a registered trademark of 1T3XT BVBA.
Many questions posted to this list can (and will) be answered with a reference to the iText book: http://www.itextpdf.com/book/
Please check the keywords list before you ask for examples: http://itextpdf.com/themes/keywords.php
mkl
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Pdf - Incremental Updates

mkl
In reply to this post by linuxunil
linuxunil,
linuxunil wrote
First, read the PDF format specification v1.7, section 3.4.5 page 98
http://www.adobe.com/content/dam/Adobe/en/devnet/acrobat/pdfs/pdf_reference_1-7.pdf
Talks about "Incremental Updates." Read this section for more info of what I'm talking here.
Please use the ISO PDF specification (which also is publicly available on the Adobe site: http://www.adobe.com/content/dam/Adobe/en/devnet/acrobat/pdfs/PDF32000_2008.pdf); by using RFC style lingo, some details are more accurate in the ISO spec than in the Adobe spec. Furthermore it is the (current) standard concerning the PDF format.
I edited my previous posts to make it clear.
Editing your posts is futile for mailing lists mirrored on nabble as the edits aren't forwarded to the mailing list. nabble does show a banner "Your changes will not be sent to the mailing list. If you want others in the mailing list to know of your changes, please compose a new message or reply to your original message." when you edit your posts which is quite to the point.
    InputStream revisionIs = revisionFields.extractRevision("Sig1"); //<-- revision is supposed to be here

    System.out.println("#> INPUTSTREAM AVAIBLE COUNT : " + revisionIs.available());

    byte[] revisionBuffer = new byte[revisionIs.available()];
    revisionIs.read(revisionBuffer);
    revisionIs.close();
    System.out.println("##> REVISION SIZE " + revisionBuffer.length);
What makes you think this could work at all? InputStream.available() only in very special InputStream implementations returns the length of the complete data to retrieve from the stream, FileInputStreams coming to my mind. Generally it's merely "an *estimate* of the number of bytes that can be read (or skipped over) from this input stream *without blocking*" (cf the InputStream JavaDocs).
If is the second (or later) that file is requested, the file to be sent to the client will be the last appended update.
Even if you correctly read the revision input stream, that would not be what you want as it is not merely the data added during the associated incremental update but all data up to and including that incremental update, excluding anything newer. You actually merely want an end piece of that. As you know the size of the data you had before, you know how long a head piece you have to skip.

Regards,   Michael
Loading...