2016-04-20 220 views
1

所以我遇到了一个有趣的问题。所以我知道在itext/itextsharp签名时,您可以在PdfSignatureAppearance上设置一个设置CertificationLevel的设置,并且按预期工作,但是最近我遇到了问题,我签署了一个文档,其中第一个签名文档用PdfSignatureAppearance.CERTIFIED_FORM_FILLING签名,因此允许我使用(PdfSignatureAppearance.NOT_CERTIFIED)作为批准签名向后添加/签名签名。PDF设置不允许在签署后更改

所以我问这个问题的原因是我遇到了一个问题,我有一个文档与文档中的现有签名字段,我签署了第一个签名与PdfSignatureAppearance.CERTIFIED_FORM_FILLING和签名后与PdfSignatureAppearance.NOT_CERTIFIED ,但是当我签署第二个签名字段时,第一个签名字段变得无效。

我正在使用的这个文档是使用FoxitPro创建的,但是如果我在Adobe DC Pro中执行完全相同的操作,它将按预期工作。

任何意见,将不胜感激。

这里是我用于签署pdf文档的代码,它只有签名者类,所以其他对象和对这个类的引用将会丢失。

 public byte[] Sign(SignRequest request) 
    { 
     request.Document = SaveDocumentChanges(new SaveRequest 
     { 
      Document = request.Document, 
      FormFields = request.FormFields, 
      SigningBlocks = request.SigningBlocks 
     }, request.Information); 

     return SignDocument(request.Certificate, request.Information, request.SigningBlocks, request.SignatureImages, request.Document, request.IsFinalSignature); 
    } 

    private byte[] AddFormFields(List<FormField> formFields, byte[] document) 
    { 
     for (int i = 0; i < formFields.Count; i++) 
     { 
      using (MemoryStream outputStream = new MemoryStream()) 
      { 
       using (PdfReader reader = new PdfReader(document)) 
       { 
        using (PdfStamper stamper = CreatePdfStamper(reader, outputStream, false)) 
        { 
         if (!DoesFormFieldExist(reader, formFields[i].Name)) 
         { 
          CreateFormField(reader, stamper, formFields[i]); 
         } 
         else 
         { 
          UpdateFormField(stamper, formFields[i]); 
         } 
        } 
       } 

       document = outputStream.ToArray(); 
      } 
     } 

     return document; 
    } 

    private byte[] AddMetaData(SigningInformation information, byte[] document) 
    { 
     if (information.CustomProperties != null && information.CustomProperties.Any()) 
     { 
      using (MemoryStream outputStream = new MemoryStream()) 
      { 
       using (PdfReader reader = new PdfReader(document)) 
       { 
        using (PdfStamper stamper = CreatePdfStamper(reader, outputStream, false)) 
        { 
         Dictionary<string, string> currentProperties = reader.Info; 
         foreach (string key in information.CustomProperties.Keys) 
         { 
          AddMetaDataAddDictionaryValue(currentProperties, key, information.CustomProperties[key]); 
         } 

         AddMetaDataAddDictionaryValue(currentProperties, "Producer", "Signisure"); 
         AddMetaDataAddDictionaryValue(currentProperties, "Creator", "Signisure"); 
         AddMetaDataAddDictionaryValue(currentProperties, "Author", "Signisure"); 
         stamper.MoreInfo = currentProperties; 
        } 
       } 

       return outputStream.ToArray(); 
      } 
     } 

     return document; 
    } 

    private void AddMetaDataAddDictionaryValue(Dictionary<string, string> dictionary, string key, string value) 
    { 
     if (dictionary.ContainsKey(key)) 
     { 
      dictionary[key] = value; 
     } 
     else 
     { 
      dictionary.Add(key, value); 
     } 
    } 

    private void AddMetaDataAddDictionaryValue(PdfDictionary dictionary, PdfName key, PdfObject value) 
    { 
     if (!dictionary.Keys.Contains(key)) 
     { 
      dictionary.Put(key, value); 
     } 
    } 

    private byte[] AddSignatureFields(List<SigningBlock> signingBlocks, byte[] document) 
    { 
     for (int i = 0; i < signingBlocks.Count; i++) 
     { 
      using (MemoryStream outputStream = new MemoryStream()) 
      { 
       using (PdfReader reader = new PdfReader(document)) 
       { 
        using (PdfStamper stamper = CreatePdfStamper(reader, outputStream, false)) 
        { 
         if (!DoesSignatureFieldExist(reader, signingBlocks[i].Name)) 
         { 
          CreateSignatureField(stamper, signingBlocks[i]); 
         } 
        } 
       } 

       document = outputStream.ToArray(); 
      } 
     } 

     return document; 
    } 

    private void CreateFormField(PdfReader reader, PdfStamper stamper, FormField formField) 
    { 
     TextField field = new TextField(stamper.Writer, new Rectangle(formField.X, formField.Y, formField.X + formField.Width, formField.Y + formField.Height), formField.Name); 
     field.Text = formField.Value; 
     field.Font = BaseFont.CreateFont(BaseFont.TIMES_ROMAN, BaseFont.CP1252, BaseFont.EMBEDDED); 
     field.FontSize = 12; 
     field.Options = TextField.READ_ONLY; 

     stamper.AddAnnotation(field.GetTextField(), formField.Page); 
    } 

    private PdfSignatureAppearance CreatePdfAppearance(PdfStamper stamper, SigningInformation information, string location, bool certify) 
    { 
     PdfSignatureAppearance appearance = stamper.SignatureAppearance; 
     appearance.SignatureRenderingMode = PdfSignatureAppearance.RenderingMode.DESCRIPTION; 
     CreatePdfAppearanceCertifyDocument(appearance, certify); 

     if (information != null) 
     { 
      appearance.Location = location != String.Empty ? String.Format("{0} ({1})", location, information.IPAddress) : information.IPAddress; 
      appearance.Reason = information.SignatoryReason; 
      appearance.Contact = String.Format("{0} ({1})", information.Signatory, information.SignatoryEmail); 
     } 

     return appearance; 
    } 

    private void CreatePdfAppearanceCertifyDocument(PdfSignatureAppearance appearance, bool certify) 
    { 
     if (certify) 
     { 
      appearance.CertificationLevel = PdfSignatureAppearance.CERTIFIED_FORM_FILLING_AND_ANNOTATIONS; 
     } 
     else 
     { 
      appearance.CertificationLevel = PdfSignatureAppearance.NOT_CERTIFIED; 
     } 
    } 

    private PdfStamper CreatePdfStamper(PdfReader reader, MemoryStream outputStream, bool isSignature) 
    { 
     if (CreatePdfStamperIsPDFADocument(reader)) 
     { 
      if (isSignature) 
      { 
       return PdfAStamper.CreateSignature(reader, outputStream, _pdfVersion, null, true, PdfAConformanceLevel.PDF_A_1A); 
      } 
      else 
      { 
       return new PdfAStamper(reader, outputStream, _pdfVersion, true, PdfAConformanceLevel.PDF_A_1A); 
      } 
     } 
     else 
     { 
      if (isSignature) 
      { 
       return PdfStamper.CreateSignature(reader, outputStream, _pdfVersion, null, true); 
      } 
      else 
      { 
       return new PdfStamper(reader, outputStream, _pdfVersion, true); 
      } 
     } 
    } 

    private bool CreatePdfStamperIsPDFADocument(PdfReader reader) 
    { 
     if (reader.Metadata != null && reader.Metadata.Length > 0) 
     { 
      IXmpMeta xmpMeta = XmpMetaParser.Parse(reader.Metadata, null); 
      IXmpProperty pdfaidConformance = xmpMeta.GetProperty(XmpConst.NS_PDFA_ID, "pdfaid:conformance"); 
      IXmpProperty pdfaidPart = xmpMeta.GetProperty(XmpConst.NS_PDFA_ID, "pdfaid:part"); 

      if (pdfaidConformance == null || pdfaidPart == null) 
      { 
       return false; 
      } 

      return true; 
     } 

     return false; 
    } 

    private void CreateSignatureField(PdfStamper stamper, SigningBlock signingBlock) 
    { 
     if (signingBlock == null) 
     { 
      return; 
     } 

     PdfFormField signatureField = PdfFormField.CreateSignature(stamper.Writer); 
     signatureField.SetWidget(new Rectangle(signingBlock.X, signingBlock.Y, signingBlock.X + signingBlock.Width, signingBlock.Y + signingBlock.Height), null); 
     signatureField.Flags = PdfAnnotation.FLAGS_PRINT; 
     signatureField.FieldName = signingBlock.Name; 
     signatureField.Page = signingBlock.Page; 

     signatureField.Put(PdfName.CONTENTS, new PdfString(String.Empty)); 
     CreateSignatureFieldAddLockProperties(signatureField, signingBlock, stamper); 

     stamper.AddAnnotation(signatureField, signingBlock.Page); 
    } 

    private void CreateSignatureFieldAddLockProperties(PdfFormField signatureField, SigningBlock signingBlock, PdfStamper stamper) 
    { 
     if (signingBlock.LinkedFormFields != null && signingBlock.LinkedFormFields.Count > 0) 
     { 
      PdfSigLockDictionary lockDictionary = new PdfSigLockDictionary(PdfSigLockDictionary.LockAction.INCLUDE, signingBlock.LinkedFormFields.ToArray()); 
      signatureField.Put(PdfName.LOCK, stamper.Writer.AddToBody(lockDictionary).IndirectReference); 
     } 
    } 

    private bool DoesFormFieldExist(PdfReader reader, string formFieldName) 
    { 
     if (String.IsNullOrWhiteSpace(formFieldName)) 
     { 
      return false; 
     } 

     return reader.AcroFields.Fields.Where(vp => vp.Key == formFieldName).Any(); 
    } 

    private bool DoesSignatureFieldExist(PdfReader reader, string signatureFieldName) 
    { 
     if (String.IsNullOrWhiteSpace(signatureFieldName)) 
     { 
      return false; 
     } 

     return reader.AcroFields.DoesSignatureFieldExist(signatureFieldName); 
    } 

    private AcroFields.FieldPosition GetAcroFieldByName(PdfStamper stamper, string signatureBlockName) 
    { 
     return stamper.AcroFields.GetFieldPositions(signatureBlockName).FirstOrDefault(); 
    } 

    private List<string> GetAllSignatureFieldNames(PdfReader reader) 
    { 
     List<string> signatureFields = new List<string>(); 
     signatureFields.AddRange(reader.AcroFields.GetBlankSignatureNames()); 
     signatureFields.AddRange(reader.AcroFields.GetSignatureNames()); 

     return signatureFields; 
    } 

    private void GetDocumentFormFieldsBuildFormFields(List<FormField> formFields, PdfReader reader, PdfStamper stamper) 
    { 
     List<string> signatureFields = GetAllSignatureFieldNames(reader); 
     foreach (KeyValuePair<string, AcroFields.Item> field in reader.AcroFields.Fields) 
     { 
      string fieldName = field.Key.ToString(); 
      if (!signatureFields.Where(signatureFieldName => signatureFieldName == fieldName).Any()) 
      { 
       string fieldValue = reader.AcroFields.GetField(field.Key.ToString()); 
       AcroFields.FieldPosition formFieldPosition = GetAcroFieldByName(stamper, fieldName); 

       formFields.Add(GetDocumentFormFieldsBuildFormFieldsCreateField(formFieldPosition, fieldName, fieldValue)); 
      } 
     } 
    } 

    private FormField GetDocumentFormFieldsBuildFormFieldsCreateField(AcroFields.FieldPosition formFieldPosition, string fieldName, string fieldValue) 
    { 
     return new FormField 
     { 
      Height = (int)formFieldPosition.position.Height, 
      Name = fieldName, 
      Page = formFieldPosition.page, 
      Width = (int)formFieldPosition.position.Width, 
      X = (int)formFieldPosition.position.Left, 
      Y = (int)formFieldPosition.position.Top, 
      Value = fieldValue 
     }; 
    } 

    private void GetDocumentSignatureBlocksBuildSignatureBlocks(List<SigningBlock> signatureBlocks, List<string> signatureBlockNames, PdfReader reader, PdfStamper stamper, bool isSigned) 
    { 
     foreach (string signatureBlockName in signatureBlockNames) 
     { 
      AcroFields.FieldPosition signatureFieldPosition = GetAcroFieldByName(stamper, signatureBlockName); 
      signatureBlocks.Add(GetDocumentSignatureBlocksBuildSignatureBlocksCreateBlock(signatureFieldPosition, signatureBlockName, isSigned)); 
     } 
    } 

    private SigningBlock GetDocumentSignatureBlocksBuildSignatureBlocksCreateBlock(AcroFields.FieldPosition signatureFieldPosition, string fieldName, bool isSigned) 
    { 
     return new SigningBlock 
     { 
      Height = (int)signatureFieldPosition.position.Height, 
      Name = fieldName, 
      Page = signatureFieldPosition.page, 
      Width = (int)signatureFieldPosition.position.Width, 
      X = (int)signatureFieldPosition.position.Left, 
      Y = (int)signatureFieldPosition.position.Top, 
      IsSigned = isSigned 
     }; 
    } 

    private string GetFormFieldValueForName(PdfStamper stamper, string formFieldName) 
    { 
     AcroFields formFields = stamper.AcroFields; 
     return formFields.GetField(formFieldName); 
    } 

    private byte[] GetSignatureImage(List<MemberItemSignature> signatureImages, string signingBlockName) 
    { 
     MemberItemSignature signature = signingBlockName.Contains("Initial") ? signatureImages.Where(image => image.Use == SignatureUses.Initial).FirstOrDefault() : signatureImages.Where(image => image.Use == SignatureUses.Signature).FirstOrDefault(); 
     if (signature != null) 
     { 
      return signature.Image; 
     } 

     return null; 
    } 

    private byte[] SaveDocumentChanges(SaveRequest request, SigningInformation information) 
    { 
     request.Document = AddMetaData(information, request.Document); 
     request.Document = AddFormFields(request.FormFields, request.Document); 
     request.Document = AddSignatureFields(request.SigningBlocks, request.Document); 

     return request.Document; 
    } 

    private byte[] SignDocument(Certificate certificate, SigningInformation information, List<SigningBlock> signingBlocks, List<MemberItemSignature> signatureImages, byte[] document, bool isFinalSignature) 
    { 
     for (int i = 0; i < signingBlocks.Count; i++) 
     { 
      document = SignDocumentSignSignatureField(certificate, information, signingBlocks[i], signatureImages, document, true); 
     } 

     if (isFinalSignature) 
     { 
      return SignDocumentLTVVerification(certificate, document); 
     } 

     return document; 
    } 

    private byte[] SignDocumentLTVVerification(Certificate certificate, byte[] document) 
    { 
     using (MemoryStream outputStream = new MemoryStream()) 
     { 
      using (PdfReader reader = new PdfReader(document)) 
      { 
       using (PdfStamper stamper = PdfStamper.CreateSignature(reader, outputStream, '\0', null, true)) 
       { 
        SignDocumentSigningBlockAddLTVVerification(stamper, certificate); 
       } 
      } 

      return outputStream.ToArray(); 
     } 
    } 

    private void SignDocumentSigningBlock(SigningComponents components, SigningInformation information, SigningBlock block, PdfSignatureAppearance appearance, PdfStamper stamper, byte[] signatureImage) 
    { 
     appearance.SetVisibleSignature(block.Name); 
     SignDocumentSigningBlockWithImage(signatureImage, appearance); 
     SignDocumentSigningBlockWithText(appearance, information, appearance.SignDate); 

     if (components.Certificate != null) 
     { 
      using (RSACryptoServiceProvider rsa = (RSACryptoServiceProvider)components.Certificate.PrivateKey) 
      { 
       PrivateKeySignature privateKeySignature = SignDocumentSigningBlockBuildDigestSigningMethod(information, rsa) as PrivateKeySignature; 
       SignatureHelper.Sign(appearance, privateKeySignature, components.CertificateChain, new List<ICrlClient> { components.CrlClient }, components.OcspClient, components.TimeStampingAuthority, Int32.Parse(_settingManager["DocumentSigningEstimatedDigestSize"]), CryptoStandard.CMS, SignDocumentSigningBlockCreateMetaData(information)); 
      } 
     } 
     else 
     { 
      HSMExternalSignature hsmExternalSignature = SignDocumentSigningBlockBuildDigestSigningMethod(information, null) as HSMExternalSignature; 
      SignatureHelper.Sign(appearance, hsmExternalSignature, components.TimeStampingAuthority, Int32.Parse(_settingManager["DocumentSigningEstimatedDigestSize"]), CryptoStandard.CMS, SignDocumentSigningBlockCreateMetaData(information)); 
     } 
    } 

    private void SignDocumentSigningBlockAddLTVVerification(PdfStamper stamper, Certificate certificate) 
    { 
     SigningComponents components = new SigningComponents(_settingManager, certificate); 
     LtvVerification ltvVerification = stamper.LtvVerification; 
     List<string> signatureFieldNames = stamper.AcroFields.GetSignatureNames(); 

     PdfPKCS7 pkcs7 = stamper.AcroFields.VerifySignature(signatureFieldNames.Last()); 
     if (pkcs7.IsTsp) 
     { 
      bool validationAddedSuccessfully = ltvVerification.AddVerification(signatureFieldNames.Last(), components.OcspClient, components.CrlClient, LtvVerification.CertificateOption.SIGNING_CERTIFICATE, LtvVerification.Level.OCSP_CRL, LtvVerification.CertificateInclusion.YES); 
     } 
     else 
     { 
      foreach (string name in stamper.AcroFields.GetSignatureNames()) 
      { 
       bool validationAddedSuccessfully = ltvVerification.AddVerification(name, components.OcspClient, components.CrlClient, LtvVerification.CertificateOption.WHOLE_CHAIN, LtvVerification.Level.OCSP_CRL, LtvVerification.CertificateInclusion.YES); 
      } 
     } 
     ltvVerification.Merge(); 

     PdfSignatureAppearance appearance = stamper.SignatureAppearance; 
     LtvTimestamp.Timestamp(appearance, components.TimeStampingAuthority, null); 
    } 

    private IExternalSignature SignDocumentSigningBlockBuildDigestSigningMethod(SigningInformation information, RSACryptoServiceProvider rsaCryptoProvider) 
    { 
     if (information.CertificateUse == CertificateUse.SignisureCertificate || rsaCryptoProvider == null) 
     { 
      return new HSMExternalSignature(_hsmService, _settingManager["DocumentSigningEncryptionHashAlgorithm"]); 
     } 
     else 
     { 
      return new PrivateKeySignature(DotNetUtilities.GetRsaKeyPair(rsaCryptoProvider).Private, _settingManager["DocumentSigningEncryptionHashAlgorithm"]); 
     } 
    } 

    private PdfDictionary SignDocumentSigningBlockCreateMetaData(SigningInformation information) 
    { 
     PdfDictionary signatureDictionary = new PdfDictionary(); 
     if (!String.IsNullOrWhiteSpace(information.IdentificationInformation)) 
     { 
      AddMetaDataAddDictionaryValue(signatureDictionary, new PdfName(".Signisure.IdentificationInformation"), new PdfString(information.IdentificationInformation)); 
     } 
     if (!String.IsNullOrWhiteSpace(information.JuristicEntity)) 
     { 
      AddMetaDataAddDictionaryValue(signatureDictionary, new PdfName(".Signisure.JuristicEntity"), new PdfString(information.JuristicEntity)); 
     } 
     if (!String.IsNullOrWhiteSpace(information.Capacity)) 
     { 
      AddMetaDataAddDictionaryValue(signatureDictionary, new PdfName(".Signisure.Capacity"), new PdfString(information.Capacity)); 
     } 

     return signatureDictionary; 
    } 

    private void SignDocumentSigningBlockWithImage(byte[] signatureImage, PdfSignatureAppearance appearance) 
    { 
     if (signatureImage != null && signatureImage.Length > 0) 
     { 
      Image signatureImageInstance = Image.GetInstance(ImageHelper.FlattenImage(signatureImage)); 

      appearance.Image = signatureImageInstance; 
      appearance.SignatureGraphic = signatureImageInstance; 
     } 
    } 

    private void SignDocumentSigningBlockWithText(PdfSignatureAppearance appearance, SigningInformation information, DateTime timestampDateTime) 
    { 
     BaseFont verdana = BaseFont.CreateFont(AssemblyDirectory + "\\Content\\Fonts\\Verdana\\Verdana.ttf", BaseFont.CP1252, BaseFont.EMBEDDED); 
     BaseFont helvetica = BaseFont.CreateFont(AssemblyDirectory + "\\Content\\Fonts\\Helvetica\\Helvetica.ttf", BaseFont.CP1252, BaseFont.EMBEDDED); 
     BaseFont comicSans = BaseFont.CreateFont(AssemblyDirectory + "\\Content\\Fonts\\ComicSans\\ComicSans.ttf", BaseFont.CP1252, BaseFont.EMBEDDED); 

     appearance.Layer2Text = SignDocumentSigningBlockWithTextBuildText(appearance, information, timestampDateTime); 
     appearance.Layer2Font = new Font(verdana); 
    } 

    private string SignDocumentSigningBlockWithTextBuildText(PdfSignatureAppearance appearance, SigningInformation information, DateTime timestampDateTime) 
    { 
     return String.Format("Signee: {0}\nSign date: {1}\nLocation: {2}\nReason: {3}", information.Signatory, timestampDateTime.ToLocalTime().ToString("yyyy-MM-dd HH:mm:ss zzz"), appearance.Location, appearance.Reason); 
    } 

    private byte[] SignDocumentSignSignatureField(Certificate certificate, SigningInformation information, SigningBlock signingBlock, List<MemberItemSignature> signatureImages, byte[] document, bool isVisible) 
    { 
     SigningComponents components = new SigningComponents(_settingManager, certificate); 
     using (MemoryStream outputStream = new MemoryStream()) 
     { 
      using (PdfReader reader = new PdfReader(document)) 
      { 
       using (PdfStamper stamper = CreatePdfStamper(reader, outputStream, true)) 
       { 
        PdfSignatureAppearance appearance = CreatePdfAppearance(stamper, information, SignDocumentSignSignatureFieldBuildLocation(stamper, signingBlock), false); 
        SignDocumentSigningBlock(components, information, signingBlock, appearance, stamper, GetSignatureImage(signatureImages, signingBlock.Name)); 
       } 
      } 

      return outputStream.ToArray(); 
     } 
    } 

    private string SignDocumentSignSignatureFieldBuildLocation(PdfStamper stamper, SigningBlock signingBlock) 
    { 
     StringBuilder builder = new StringBuilder(); 
     for (int index = 0; index < signingBlock.LinkedFormFields.Count; index++) 
     { 
      builder.Append(GetFormFieldValueForName(stamper, signingBlock.LinkedFormFields[index])); 
      if (index + 1 < signingBlock.LinkedFormFields.Count) 
      { 
       builder.Append(", "); 
      } 
     } 

     return builder.ToString(); 
    } 

    private void UpdateFormField(PdfStamper stamper, FormField formField) 
    { 
     AcroFields formFields = stamper.AcroFields; 
     if (formField.Value != null && GetFormFieldValueForName(stamper, formField.Name) != formField.Value) 
     { 
      formFields.SetField(formField.Name, formField.Value); 
      formFields.SetFieldProperty(formField.Name, "setfflags", PdfFormField.FF_READ_ONLY, null); 
     } 
    } 
} 

}

+0

请删除您的问题中的矛盾。你问*是否有另一个文档级别的设置,只要你尝试签名后续签名,就会强制签名无效?*对于不是专家的人,似乎你在问题前的段落中提供了答案:*我正在尝试使用PdfSignatureAppearance.CERTIFIED_FORM_FILLING签署一份文件...这使我后续的签名无效* –

+0

您好布鲁诺,对不起,我想指出的是,是否有其他设置我不知道。我会尽量使问题更清楚。感谢您的回复 – Johandre

+0

当人们不显示他们的代码时,他们总是挫败可以帮助他们的人。我从来没有明白,如果你期待他们的帮助,你为什么要挫败他人。原始签名被破坏的一个可能的原因可能是您忘记在* append模式下使用'PdfStamper'。请理解,您不应该玩*猜谜游戏*。 –

回答

2

简短的回答:

如果你签订与PdfSignatureAppearance.CERTIFIED_FORM_FILLING级认证签名的文件,那么你可以添加你想要的额外审批签名不破坏原(或之前)签名。

较长的答案:

没有人会相信你,如果你写:

我试图签署PdfSignatureAppearance.CERTIFIED_FORM_FILLING第一个文件,这应该让我增加更多的签名域,编辑表单字段或签名其他签名字段,但相反,它会使我的后续签名签名失效。

你在这里说的是错误的。

但是,也许你没有正确签署PDF。请允许我重复我的答案很简单:

如果你签订了认证签名PdfSignatureAppearance.CERTIFIED_FORM_FILLING级别的文档,那么您可以根据需要添加尽可能多的额外审批签名没有打破原有的(或之前)的签名。

我强调了两个概念。 PDF可以具有最多一个认证签名(又名作者签名),并且该签名应该是文档中的第一签名。 PDF可以有多个批准签名(aka收件人签名)。

也许你正在使用认证签名签署文件(我认为这是真的,因为你谈论认证级别)。也许你正试图添加第二个认证签名。显然,这会破坏PDF中的签名,因为PDF规范只允许一个认证签名。

也许你的问题是通过添加批准签名而不是认证签名来解决的。

+0

您好布鲁诺,感谢您的回应,我认为在我原来的解释中,我没有正确解释自己,所以我很抱歉,所以我所做的是第一个签名用PdfSignatureAppearance.CERTIFIED_FORM_FILLING签名签名签名后签名的签名使用PdfSignatureAppearance.NOT_CERTIFIED签名,即这些将是我的批准签名。 我希望这样做更好理解,还是我误解了一些东西? – Johandre

+0

我已经更新了这个问题,我希望现在更清楚,对于矛盾和困惑感到抱歉。亲切的问候 – Johandre

+0

如果您使用'NOT_CERTIFIED',那么原始签名不应该被打破。当然:只有你签字正确。你没有显示你的代码,那么我们如何知道你是否在* append模式下使用'PdfStamper'? –