Merge branch 'main' into feature/image-appearance
This commit is contained in:
8
go.mod
8
go.mod
@@ -1,12 +1,14 @@
|
|||||||
module github.com/digitorus/pdfsign
|
module github.com/digitorus/pdfsign
|
||||||
|
|
||||||
go 1.22
|
go 1.23.0
|
||||||
|
|
||||||
|
toolchain go1.23.6
|
||||||
|
|
||||||
require (
|
require (
|
||||||
github.com/digitorus/pdf v0.1.2
|
github.com/digitorus/pdf v0.1.2
|
||||||
github.com/digitorus/pkcs7 v0.0.0-20230818184609-3a137a874352
|
github.com/digitorus/pkcs7 v0.0.0-20230818184609-3a137a874352
|
||||||
github.com/digitorus/timestamp v0.0.0-20231217203849-220c5c2851b7
|
github.com/digitorus/timestamp v0.0.0-20231217203849-220c5c2851b7
|
||||||
github.com/mattetti/filebuffer v1.0.1
|
github.com/mattetti/filebuffer v1.0.1
|
||||||
golang.org/x/crypto v0.33.0
|
golang.org/x/crypto v0.35.0
|
||||||
golang.org/x/text v0.22.0
|
golang.org/x/text v0.25.0
|
||||||
)
|
)
|
||||||
|
8
go.sum
8
go.sum
@@ -7,7 +7,7 @@ github.com/digitorus/timestamp v0.0.0-20231217203849-220c5c2851b7 h1:lxmTCgmHE1G
|
|||||||
github.com/digitorus/timestamp v0.0.0-20231217203849-220c5c2851b7/go.mod h1:GvWntX9qiTlOud0WkQ6ewFm0LPy5JUR1Xo0Ngbd1w6Y=
|
github.com/digitorus/timestamp v0.0.0-20231217203849-220c5c2851b7/go.mod h1:GvWntX9qiTlOud0WkQ6ewFm0LPy5JUR1Xo0Ngbd1w6Y=
|
||||||
github.com/mattetti/filebuffer v1.0.1 h1:gG7pyfnSIZCxdoKq+cPa8T0hhYtD9NxCdI4D7PTjRLM=
|
github.com/mattetti/filebuffer v1.0.1 h1:gG7pyfnSIZCxdoKq+cPa8T0hhYtD9NxCdI4D7PTjRLM=
|
||||||
github.com/mattetti/filebuffer v1.0.1/go.mod h1:YdMURNDOttIiruleeVr6f56OrMc+MydEnTcXwtkxNVs=
|
github.com/mattetti/filebuffer v1.0.1/go.mod h1:YdMURNDOttIiruleeVr6f56OrMc+MydEnTcXwtkxNVs=
|
||||||
golang.org/x/crypto v0.33.0 h1:IOBPskki6Lysi0lo9qQvbxiQ+FvsCC/YWOecCHAixus=
|
golang.org/x/crypto v0.35.0 h1:b15kiHdrGCHrP6LvwaQ3c03kgNhhiMgvlhxHQhmg2Xs=
|
||||||
golang.org/x/crypto v0.33.0/go.mod h1:bVdXmD7IV/4GdElGPozy6U7lWdRXA4qyRVGJV57uQ5M=
|
golang.org/x/crypto v0.35.0/go.mod h1:dy7dXNW32cAb/6/PRuTNsix8T+vJAqvuIy5Bli/x0YQ=
|
||||||
golang.org/x/text v0.22.0 h1:bofq7m3/HAFvbF51jz3Q9wLg3jkvSPuiZu/pD1XwgtM=
|
golang.org/x/text v0.25.0 h1:qVyWApTSYLk/drJRO5mDlNYskwQznZmkpV2c8q9zls4=
|
||||||
golang.org/x/text v0.22.0/go.mod h1:YRoo4H8PVmsu+E3Ou7cqLVH8oXWIHVoX0jqUWALQhfY=
|
golang.org/x/text v0.25.0/go.mod h1:WEdwpYrmk1qmdHvhkSTNPm3app7v4rsT8F2UD6+VHIA=
|
||||||
|
@@ -28,9 +28,10 @@ func (context *SignContext) createCatalog() ([]byte, error) {
|
|||||||
// written in the PDF file (for example, /1.4).
|
// written in the PDF file (for example, /1.4).
|
||||||
//
|
//
|
||||||
// If an incremental upgrade requires a version that is higher than specified by the document.
|
// If an incremental upgrade requires a version that is higher than specified by the document.
|
||||||
// if context.PDFReader.PDFVersion < "2.0" {
|
// Ensure PDF version is at least 1.5 to support SigFlags in acroFormDict (1.4) and UF in the fileSpecDict (1.5)
|
||||||
// catalog_buffer.WriteString(" /Version /2.0")
|
if v, err := strconv.ParseFloat(context.PDFReader.PDFVersion, 64); err == nil && v < 1.5 {
|
||||||
// }
|
catalog_buffer.WriteString(" /Version /1.5\n")
|
||||||
|
}
|
||||||
|
|
||||||
// Retrieve the root, its pointer and set the root string
|
// Retrieve the root, its pointer and set the root string
|
||||||
root := context.PDFReader.Trailer().Key("Root")
|
root := context.PDFReader.Trailer().Key("Root")
|
||||||
|
@@ -21,11 +21,11 @@ var testFiles = []struct {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
file: "../testfiles/testfile21.pdf",
|
file: "../testfiles/testfile12.pdf",
|
||||||
expectedCatalogs: map[CertType]string{
|
expectedCatalogs: map[CertType]string{
|
||||||
CertificationSignature: "<<\n /Type /Catalog\n /Metadata 8 0 R\n /Names 6 0 R\n /Pages 9 0 R\n /AcroForm <<\n /Fields [16 0 R]\n /SigFlags 3\n >>\n>>\n",
|
CertificationSignature: "<<\n /Type /Catalog\n /Version /1.5\n /Outlines 2 0 R\n /Pages 3 0 R\n /AcroForm <<\n /Fields [16 0 R]\n /SigFlags 3\n >>\n>>\n",
|
||||||
UsageRightsSignature: "<<\n /Type /Catalog\n /Metadata 8 0 R\n /Names 6 0 R\n /Pages 9 0 R\n /AcroForm <<\n /Fields [16 0 R]\n /SigFlags 1\n >>\n>>\n",
|
UsageRightsSignature: "<<\n /Type /Catalog\n /Version /1.5\n /Outlines 2 0 R\n /Pages 3 0 R\n /AcroForm <<\n /Fields [16 0 R]\n /SigFlags 1\n >>\n>>\n",
|
||||||
ApprovalSignature: "<<\n /Type /Catalog\n /Metadata 8 0 R\n /Names 6 0 R\n /Pages 9 0 R\n /AcroForm <<\n /Fields [16 0 R]\n /SigFlags 3\n >>\n>>\n",
|
ApprovalSignature: "<<\n /Type /Catalog\n /Version /1.5\n /Outlines 2 0 R\n /Pages 3 0 R\n /AcroForm <<\n /Fields [16 0 R]\n /SigFlags 3\n >>\n>>\n",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
@@ -43,7 +43,7 @@ func (context *SignContext) writeTrailer() error {
|
|||||||
lines[i] = " " + strings.TrimSpace(line)
|
lines[i] = " " + strings.TrimSpace(line)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
trailer_string = strings.Join(lines, "\n")
|
trailer_string = strings.Join(lines, "\n") + "\n"
|
||||||
|
|
||||||
// Write the new trailer.
|
// Write the new trailer.
|
||||||
if _, err := context.OutputBuffer.Write([]byte(trailer_string)); err != nil {
|
if _, err := context.OutputBuffer.Write([]byte(trailer_string)); err != nil {
|
||||||
@@ -54,7 +54,6 @@ func (context *SignContext) writeTrailer() error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Write the new xref start position.
|
// Write the new xref start position.
|
||||||
if _, err := context.OutputBuffer.Write([]byte(strconv.FormatInt(context.NewXrefStart, 10) + "\n")); err != nil {
|
if _, err := context.OutputBuffer.Write([]byte(strconv.FormatInt(context.NewXrefStart, 10) + "\n")); err != nil {
|
||||||
return err
|
return err
|
||||||
|
@@ -128,9 +128,25 @@ func (context *SignContext) createIncPageUpdate(pageNumber, annot uint32) ([]byt
|
|||||||
// TODO: Update digitorus/pdf to get raw values without resolving pointers
|
// TODO: Update digitorus/pdf to get raw values without resolving pointers
|
||||||
for _, key := range page.Keys() {
|
for _, key := range page.Keys() {
|
||||||
switch key {
|
switch key {
|
||||||
case "Contents", "Parent":
|
case "Parent":
|
||||||
ptr := page.Key(key).GetPtr()
|
ptr := page.Key(key).GetPtr()
|
||||||
page_buffer.WriteString(fmt.Sprintf(" /%s %d 0 R\n", key, ptr.GetID()))
|
page_buffer.WriteString(fmt.Sprintf(" /%s %d 0 R\n", key, ptr.GetID()))
|
||||||
|
case "Contents":
|
||||||
|
// Special handling for Contents - must preserve stream structure
|
||||||
|
contentsValue := page.Key(key)
|
||||||
|
if contentsValue.Kind() == pdf.Array {
|
||||||
|
// If Contents is an array, keep it as an array reference
|
||||||
|
page_buffer.WriteString(" /Contents [")
|
||||||
|
for i := 0; i < contentsValue.Len(); i++ {
|
||||||
|
ptr := contentsValue.Index(i).GetPtr()
|
||||||
|
page_buffer.WriteString(fmt.Sprintf(" %d 0 R", ptr.GetID()))
|
||||||
|
}
|
||||||
|
page_buffer.WriteString(" ]\n")
|
||||||
|
} else {
|
||||||
|
// If Contents is a single reference, keep it as a single reference
|
||||||
|
ptr := contentsValue.GetPtr()
|
||||||
|
page_buffer.WriteString(fmt.Sprintf(" /%s %d 0 R\n", key, ptr.GetID()))
|
||||||
|
}
|
||||||
case "Annots":
|
case "Annots":
|
||||||
page_buffer.WriteString(" /Annots [\n")
|
page_buffer.WriteString(" /Annots [\n")
|
||||||
for i := 0; i < page.Key("Annots").Len(); i++ {
|
for i := 0; i < page.Key("Annots").Len(); i++ {
|
||||||
|
@@ -20,7 +20,6 @@ func TestGetLastObjectIDFromXref(t *testing.T) {
|
|||||||
{"testfile16.pdf", 567},
|
{"testfile16.pdf", 567},
|
||||||
{"testfile17.pdf", 20},
|
{"testfile17.pdf", 20},
|
||||||
{"testfile20.pdf", 10},
|
{"testfile20.pdf", 10},
|
||||||
{"testfile21.pdf", 16},
|
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, tc := range testCases {
|
for _, tc := range testCases {
|
||||||
|
Binary file not shown.
Reference in New Issue
Block a user