Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Multiple signatures support #11

Open
michaltrzcinka opened this issue Apr 24, 2017 · 11 comments
Open

Multiple signatures support #11

michaltrzcinka opened this issue Apr 24, 2017 · 11 comments
Labels

Comments

@michaltrzcinka
Copy link

I'm wondering if Origami currently supports creating multiple signatures in one document? I'm trying to attempt that, but when I open the file in Acrobat Reader, I see an error under first revision: SigDict/Contents illegal data.
The second revision looks fine.

Here's how I do it:

pdf = PDF.read(file)
pdf.sign(...)
pdf.save(file)
pdf = PDF.read(file)
pdf.sign(...)
pdf.save(file)
@gdelugre
Copy link
Owner

I confirm this is currently not supported.

The current problem is that Origami will parse the document and maintain an internal representation of all the objects for every revision. When the PDF#save method is called, an entire new document is regenerated which breaks the existing signatures since the data is not exactly the same.

I am still unsure about how to implement this. Maybe it could be done through an "append only" mode which would be passed as a flag to open or automatically set for a signed document.

@michaltrzcinka
Copy link
Author

Hmm is there any open library in another language that I could take a look at to port this feature to Origami? I know Java iText has it, but I think it's closed source.

@gdelugre
Copy link
Owner

Not that I know of. I wrote this feature based on the PDF specifications and by comparing with signed documents generated by the Adobe products. There may be more libraries supporting this feature now though.

@ekzobrain
Copy link

Hi, @michaltrzcinka, did you manage to get it working some way?

@ekzobrain
Copy link

Hi.

We are currently working on this and made some progress, but need yor help, @gdelugre
This ability should be implemented via revisions. When creating a second signature, we need to make a new revision, a new page and add that page/annotation/digsig/etc objects to that new revision, so when saving a document they will be appended after existing data, not mixed with it.

Please, take a look at these example documents, they contains two signatures and were created with Adobe acrobat and this programm: http://soft.rubypdf.com/software/pdf-digital-signe

single_page2_two_signatures.pdf
sign.rake3.pdf

@marcomd
Copy link

marcomd commented Mar 29, 2019

@netcitylife Thanks for your work, how is it progressing?

@colinpetruno
Copy link

I was able to get this working without too many changes to the gem. I'll try to get it cleaned up for others to check out but it might be a few weeks before I have time to do so.

The biggest change is in the output method. Currently the gem loops over all of the revisions. Instead you need to take the original content and then loop over and generate the new subsequent revisions while skipping the original ones. Just make sure the trailer gets set correctly on the first new revision and the rest works itself out.

@ekzobrain
Copy link

Hi, @colinpetruno, that's really great, I am very much awaiting for your solution! @marcomd, unfortunatelly I was unable so solve it myself because of my poor knowledge of PDF spec, and @gdelugre also did not yet have time to implement it. @colinpetruno, may be you could push your current code to a fork to let us look at it? That's not a problem if it not polished for now... I could run some tests in my usecases and provide a feedback. Thanks.

@colinpetruno
Copy link

@netcitylife Here are some links for you... This sort of resolves both issues you were pursuing (#32 in addition to this one)

Commit (details in the commit message):
colinpetruno@dc1e328

Diff:
cdc1557...colinpetruno:cp-publishable-code

I implemented a sign_with_hsm method where the HSM was the external device doing the signing. There is still some noise in the commit.

  • PNG Implementation. I pulled over code from wicked PDF to get this to work. I was getting close but the processor power required to do it all in ruby made it a bit too time consuming to finish for now.
  • Random comments and such as I was digging into origami.
  • Spacing.. I'm a 2 space person and this repo was 4 so sorry for errors there

Next steps

Clean up initialization

Initially a parser reads the documents and returns the pdf class losing reference to the parser. I don't remember exactly why this was annoying but I didn't really have access to the original doc much after parsing which made some parts like determining if it was originally signed and getting the original content of the file pretty difficult. Thus this couples the parser and the pdf classes probably more than @gdelugre intended.

parser_class.new(options).parse(path)

Try to unify the bitesize sequences

For some reason the offset was always a little different on the second revisions so I had to reimplement logic to clean this up. This works based on my implementation but probably would not under all scenarios.

QA with all combos

I am unsure how this would affect the other features of the gem like encryption and such. That would need to get looked at as well.

Missing pieces

My sign_with_hsm method sort of reimplements the problems in #32. Depending on how you plan to sign you may or may not need help here to implement it. I kept it out of this commit since it is somewhat specific to our app and most people will need different code. In our case I used an HSM to store the private key.

@ekzobrain
Copy link

Hi, @colinpetruno

Thank you very much for your work! I will review your changes by the end of the week and will try to merge them with the current upstream code in my fork, because your fork is much outdated. My fork also contains a solution for your HSM signing feature, see #57 pull request. But it is not yet accepted by @gdelugre , because he advised some changes for new signature formats support. Your decision to append new revision to the original source content is right, because origami's output will often differ from original file contents (because of formatting rules), so prior signatures may become invalid, but that leads to the problems that you faced with not being able to correctly calculate byte offsets. To solve it a bit different offset calculation mecanism should be implemented - parser should remember original offsets when parsing initial document, but not calculate offsets based on it's own output (than might differ a little).
I also do not fully understand your note about PNG support - is it finished or not?

@jotolo
Copy link

jotolo commented Nov 16, 2021

@gdelugre @netcitylife Any progress about this feature?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

6 participants