public ActionResult SignCodComplete(SignatureCompleteModel model) { byte[] signatureContent; try { var signer = new XmlElementSigner(); // Set the document to be signed and the policy, exactly like in the SignCod method signer.SetXml(Storage.GetSampleCodEnvelope()); signer.SetPolicy(getSignaturePolicy()); // Set the signature computed on the client-side, along with the "transfer data" signer.SetPrecomputedSignature(model.Signature, model.TransferData); // It is not necessary to set the signing certificate nor the element ID to be signed, both are contained in the "transfer data" // Call ComputeSignature(), which validates the signature of the "to-sign-hash" and finishes the signature process signer.ComputeSignature(); // Get the signed XML as an array of bytes signatureContent = signer.GetSignedXml(); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate is revoked. ModelState.AddModelError("", ex.ValidationResults.ToString()); return(View()); } // Store the signature file on the folder "App_Data/" and redirect to the SignCodResult action with the filename. var filename = Storage.StoreFile(signatureContent, ".xml"); return(RedirectToAction("SignCodResult", new SignatureInfoModel() { Filename = filename })); }
public ActionResult SignCodeh(string id, SignatureStartModel model) { // Recover XML envelope with signed COD element from "storage" based on its ID byte[] content; string extension; if (!Storage.TryGetFile(id, out content, out extension)) { return(HttpNotFound()); } byte[] toSignHash, transferData; SignatureAlgorithm signatureAlg; try { // Instantiate a CadesSigner class var signer = new XmlElementSigner(); // Set the XML to sign signer.SetXml(content); // Set the ID of the CODEH element signer.SetToSignElementId("CODEH"); // Decode the user's certificate and set as the signer certificate signer.SetSigningCertificate(PKCertificate.Decode(model.CertContent)); // Set the signature policy signer.SetPolicy(getSignaturePolicy()); // Generate the "to-sign-hash". This method also yields the signature algorithm that must // be used on the client-side, based on the signature policy. toSignHash = signer.GenerateToSignHash(out signatureAlg, out transferData); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate // encoding cannot be read or if the certificate is expired. ModelState.AddModelError("", ex.ValidationResults.ToString()); return(View()); } // On the next step (SignCodehComplete action), we'll need once again some information: // - The thumpprint of the selected certificate // - The "to-sign-hash" // - The OID of the digest algorithm to be used during the signature operation // - The "transfer data" TempData["SignatureCompleteModel"] = new SignatureCompleteModel() { CertThumb = model.CertThumb, ToSignHash = toSignHash, DigestAlgorithmOid = signatureAlg.DigestAlgorithm.Oid, TransferData = transferData }; return(RedirectToAction("SignCodehComplete", new { id })); }
public ActionResult SignCodehComplete(string id, SignatureCompleteModel model) { // Recover XML envelope with signed COD element from "storage" based on its ID byte[] content; if (!StorageMock.TryGetFile(id, out content)) { return(HttpNotFound()); } byte[] signatureContent; try { // Recover the "transfer data" content stored in a temporary file. byte[] transferDataContent; if (!StorageMock.TryGetFile(model.TransferDataFileId, out transferDataContent)) { return(HttpNotFound()); } // Get an instance of the XmlElementSigner class. var signer = new XmlElementSigner(); // Set the document to be signed and the policy, exactly like in the SignCodeh method signer.SetXml(content); signer.SetPolicy(getSignaturePolicy()); // Set the signature computed on the client-side, along with the "transfer data" signer.SetPrecomputedSignature(model.Signature, transferDataContent); // Call ComputeSignature(), which validates the signature of the "to-sign-hash" and finishes the signature process signer.ComputeSignature(); // Get the signed XML as an array of bytes signatureContent = signer.GetSignedXml(); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate is revoked. ModelState.AddModelError("", ex.ValidationResults.ToString()); return(View()); } // On the next step (SignatureInfo action), we'll render the following information: // - The filename to be available to download in next action. // We'll store these values on TempData, which is a dictionary shared between actions. TempData["SignatureInfoModel"] = new SignatureInfoModel() { // Store the signature file on the folder "App_Data/" and redirect to the SignCodehResult action with the filename. File = StorageMock.Store(signatureContent, ".xml") }; return(RedirectToAction("SignCodehSignatureInfo")); }
public ActionResult Index(SignatureStartModel model) { byte[] toSignHash, transferData; SignatureAlgorithm signatureAlg; try { // Instantiate a XmlElementSigner class var signer = new XmlElementSigner(); // Set the data to sign, which in the case of this example is a fixed sample document signer.SetXml(Storage.GetSampleNFeContent()); // static Id from node <infNFe> from SampleNFe.xml document signer.SetToSignElementId("NFe35141214314050000662550010001084271182362300"); // Decode the user's certificate and set as the signer certificate signer.SetSigningCertificate(PKCertificate.Decode(model.CertContent)); // Set the signature policy signer.SetPolicy(getSignaturePolicy()); // Generate the "to-sign-hash". This method also yields the signature algorithm that must // be used on the client-side, based on the signature policy. toSignHash = signer.GenerateToSignHash(out signatureAlg, out transferData); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate // encoding cannot be read or if the certificate is expired. ModelState.AddModelError("", ex.ValidationResults.ToString()); return(View()); } // On the next step (Complete action), we'll need once again some information: // - The content of the selected certificate only used to render the user's certificate information // after the signature is completed. It is no longer needed for the signature process. // - The thumpprint of the selected certificate. // - The "transfer data" used to validate the signature in complete action. // - The "to-sign-hash" to be signed. (see signature-complete-form.js) // - The OID of the digest algorithm to be used during the signature operation. // We'll store this value on TempData, that will store in dictionary shared between actions. TempData["SignatureCompleteModel"] = new SignatureCompleteModel() { CertContent = model.CertContent, CertThumb = model.CertThumb, TransferData = transferData, ToSignHash = toSignHash, DigestAlgorithmOid = signatureAlg.DigestAlgorithm.Oid }; return(RedirectToAction("Complete")); }
public IHttpActionResult Start(SignatureStartRequest request) { byte[] toSignHash, transferData; SignatureAlgorithm signatureAlg; try { // Decode the user's certificate var cert = PKCertificate.Decode(request.Certificate); // Instantiate a XmlElementSigner class var signer = new XmlElementSigner(); // Set the data to sign, which in the case of this example is a fixed sample document signer.SetXml(Storage.GetSampleNFeContent()); // static Id from node <infNFe> from SampleNFe.xml document signer.SetToSignElementId("NFe35141214314050000662550010001084271182362300"); // Set the signer certificate decoded signer.SetSigningCertificate(cert); // Set the signature policy signer.SetPolicy(getSignaturePolicy()); // Generate the "to-sign-hash". This method also yields the signature algorithm that must // be used on the client-side, based on the signature policy. As well as the "transfer data", // a byte-array that will be needed on the next step. toSignHash = signer.GenerateToSignHash(out signatureAlg, out transferData); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate // encoding cannot be read or if the certificate is expired. return(new ResponseMessageResult(Request.CreateResponse(HttpStatusCode.BadRequest, new ValidationErrorModel(ex.ValidationResults)))); } // Create response with some informations that we'll use on Complete action and on client-side. var response = new SignatureStartResponse() { // The "transfer data" for Xml signatyures are not so big. Therefore, we can easily send it as one of // response fields. TransferData = transferData, // Send to the javascript the "to sign hash" of the document and the digest algorithm that must // be used on the signature algorithm computation ToSignHash = toSignHash, DigestAlgorithmOid = signatureAlg.DigestAlgorithm.Oid }; return(Ok(response)); }
public ActionResult Index(SignatureStartModel model) { byte[] toSignHash, transferData; SignatureAlgorithm signatureAlg; try { // Instantiate a CadesSigner class var signer = new XmlElementSigner(); // Set the data to sign, which in the case of this example is a fixed sample "COD envelope" signer.SetXml(StorageMock.GetSampleCodEnvelopeContent()); // Set the ID of the COD element signer.SetToSignElementId("COD"); // Decode the user's certificate and set as the signer certificate signer.SetSigningCertificate(PKCertificate.Decode(model.CertContent)); // Set the signature policy signer.SetPolicy(getSignaturePolicy()); // Generate the "to-sign-hash". This method also yields the signature algorithm that must // be used on the client-side, based on the signature policy. toSignHash = signer.GenerateToSignHash(out signatureAlg, out transferData); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate // encoding cannot be read or if the certificate is expired. ModelState.AddModelError("", ex.ValidationResults.ToString()); return(View()); } // On the next step (SignCodComplete action), we'll need once again some information: // - The thumpprint of the selected certificate // - The "to-sign-hash" // - The OID of the digest algorithm to be used during the signature operation // - The "transfer data" used to validate the signature in complete action.Its content is stored in // a temporary file (with extension .bin) to be shared with the Complete action. TempData["SignatureCompleteModel"] = new SignatureCompleteModel() { CertThumb = model.CertThumb, ToSignHash = toSignHash, DigestAlgorithmOid = signatureAlg.DigestAlgorithm.Oid, TransferDataFileId = StorageMock.Store(transferData, ".bin"), }; return(RedirectToAction("Complete")); }
public ActionResult Complete(SignatureCompleteModel model) { byte[] signatureContent; try { // Recover the "transfer data" content stored in a temporary file. byte[] transferDataContent; if (!StorageMock.TryGetFile(model.TransferDataFileId, out transferDataContent)) { return(HttpNotFound()); } // Instantiate a XmlElementSigner class var signer = new XmlElementSigner(); // Set the document to be signed and the policy, exactly like in the Start method signer.SetXml(StorageMock.GetSampleNFeContent()); signer.SetPolicy(getSignaturePolicy()); // Set the signature computed on the client-side, along with the "transfer data" (rendered in a hidden field, see the view) signer.SetPrecomputedSignature(model.Signature, transferDataContent); // Call ComputeSignature(), which does all the work, including validation of the signer's certificate and of the resulting signature signer.ComputeSignature(); // Get the signed XML as an array of bytes signatureContent = signer.GetSignedXml(); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate is revoked. ModelState.AddModelError("", ex.ValidationResults.ToString()); return(View()); } // On the next step (SignatureInfo action), we'll render the following information:] // - The filename to be available to download in next action. // - The signer's certificate information to be rendered. // We'll store these values on TempData, which is a dictionary shared between actions. TempData["SignatureInfoModel"] = new SignatureInfoModel() { // Store the signature file on the folder "App_Data/" and redirects to the SignatureInfo action with the filename. // With this filename, it can show a link to download the signature file. File = StorageMock.Store(signatureContent, ".xml") }; return(RedirectToAction("SignatureInfo")); }
protected void SubmitCertificateButton_Click(object sender, EventArgs e) { byte[] toSignHash, transferData; SignatureAlgorithm signatureAlg; try { // Decode the user's certificate. var cert = PKCertificate.Decode(Convert.FromBase64String(CertificateField.Value)); // Instantiate a XmlElementSigner class. var signer = new XmlElementSigner(); // Set the data to sign, which in the case of this example is a fixed sample document. signer.SetXml(Storage.GetSampleNFeContent()); // static Id from node <infNFe> from SampleNFe.xml document. signer.SetToSignElementId("NFe35141214314050000662550010001084271182362300"); // Set as the signer certificate. signer.SetSigningCertificate(cert); // Set the signature policy. signer.SetPolicy(getSignaturePolicy()); // Generate the "to-sign-hash". This method also yields the signature algorithm that must // be used on the client-side, based on the signature policy. as well as the "transfer data", // a byte-array that will be needed on the next step. toSignHash = signer.GenerateToSignHash(out signatureAlg, out transferData); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate // encoding cannot be read or if the certificate is expired. ex.ValidationResults.Errors.ForEach(ve => ModelState.AddModelError("", ve.ToString())); return; } // The "transfer data" for Xml signatures are not so big. Therefore, we can easily store it in a // hidden field. TransferDataField.Value = Convert.ToBase64String(transferData); // Send to the javascript the "to sign hash" of the document and the digest algorithm that must // be used on the signature algorithm computation. ToSignHashField.Value = Convert.ToBase64String(toSignHash); DigestAlgorithmField.Value = signatureAlg.DigestAlgorithm.Oid; }
protected void SubmitSignatureButton_Click(object sender, EventArgs e) { byte[] signatureContent; try { // Instantiate a XmlElementSigner class. var signer = new XmlElementSigner(); // Set the document to be signed and the policy, exactly like in the previous event // (SubmitCertificateButton_Click). signer.SetXml(Storage.GetSampleNFeContent()); signer.SetPolicy(getSignaturePolicy()); // Set the signature computed on the client-side, along with the "transfer data". signer.SetPrecomputedSignature(Convert.FromBase64String(SignatureField.Value), Convert.FromBase64String(TransferDataField.Value)); // Call ComputeSignature(), which does all the work, including validation of the signer's // certificate and of the resulting signature. signer.ComputeSignature(); // Get the signed XML as an array of bytes signatureContent = signer.GetSignedXml(); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate // is revoked. ex.ValidationResults.Errors.ForEach(ve => ModelState.AddModelError("", ve.ToString())); CertificateField.Value = ""; ToSignHashField.Value = ""; return; } // Pass the following fields to be used on XmlElementSignatureInfo page: // - The signature file will be stored on the folder "App_Data/". Its name will be passed by // SignatureFile field. // - The user's certificate this.SignatureFile = Storage.StoreFile(signatureContent, ".xml"); this.Certificate = PKCertificate.Decode(Convert.FromBase64String(CertificateField.Value)); Server.Transfer("XmlElementSignatureInfo.aspx"); }
public IHttpActionResult Complete(SignatureCompleteRequest request) { byte[] signatureContent; try { // Instantiate a XmlElementSigner class var signer = new XmlElementSigner(); // Set the document to be signed and the policy, exactly like in the Start action signer.SetXml(Storage.GetSampleNFeContent()); signer.SetPolicy(getSignaturePolicy()); // Set the signature computed on the client-side, along with the "transfer data" signer.SetPrecomputedSignature(request.Signature, request.TransferData); // Call ComputeSignature(), which does all the work, including validation of the signer's certificate and of the resulting signature signer.ComputeSignature(); // Get the signed XML as an array of bytes signatureContent = signer.GetSignedXml(); } catch (ValidationException ex) { // Some of the operations above may throw a ValidationException, for instance if the certificate is revoked. return(new ResponseMessageResult(Request.CreateResponse(HttpStatusCode.BadRequest, new ValidationErrorModel(ex.ValidationResults)))); } // Pass the following fields to be used on signature-results template: // - The signature file will be stored on the folder "App_Data/". Its name will be passed by Filename field. // - The user's certificate var response = new SignatureCompleteResponse() { Filename = Storage.StoreFile(signatureContent, ".xml"), Certificate = new CertificateModel(PKCertificate.Decode(request.Certificate)) }; return(Ok(response)); }