/// <summary> /// Create Xades <QualifyingProperties> from the <SignatureProperties> and <DataObjectProperties> elements /// </summary> /// <param name="signedXml"></param> /// <param name="document"></param> /// <param name="certificate"></param> private void CreateXadesQualifyingProperties(XadesSignedXml signedXml, XmlDocument document, X509Certificate2 certificate) { string signatureRootId = CreateId(XadesSignatureRootId); string signedPropertiesId = CreateId(XadesSignedPropertiesId); // build xades XML XmlElement qualifyingProperties = document.CreateElement("QualifyingProperties", XadesNamespaceUrl); qualifyingProperties.SetAttribute("Target", $"#{signatureRootId}"); XmlElement signedProperties = qualifyingProperties.CreateChild("SignedProperties", XadesNamespaceUrl); signedProperties.SetAttribute("Id", signedPropertiesId); XmlElement signatureProperties = SignatureProperties.CreateXadesSignatureProperties(document, certificate, SignatureType); signedProperties.AppendChild(signatureProperties); XmlElement dataObjectProperties = CreateXadesDataObjectProperties(document); if (dataObjectProperties.ChildNodes.Count > 0) { signedProperties.AppendChild(dataObjectProperties); } // add reference to xades XML signedXml.AddXadesObject(new DataObject(null, null, null, qualifyingProperties)); Reference signedPropertiesReference = new Reference($"#{signedPropertiesId}") { TransformChain = XadesTransformChain, DigestMethod = XadesDigestMethod, Type = XadesReferenceType }; signedXml.AddReference(signedPropertiesReference); signedXml.Signature.Id = signatureRootId; }
/// <summary> /// Create Xades signature of the included files /// </summary> /// <param name="certificate"></param> /// <param name="resolver"></param> /// <returns></returns> public XmlElement Sign(X509Certificate2 certificate) { XmlDocument document = _document ?? new XmlDocument(); _documentIds = new HashSet <string>(document.SelectNodes("//@id | //@Id").OfType <XmlAttribute>().Select(x => x.Value)); // reserve or generate item ids CheckItemIds(); //SignedXml signedXml = _signatureParent != null ? new SignedXml(_signatureParent) : new SignedXml(document); XadesSignedXml signedXml = _signatureParent != null ? new XadesSignedXml(_signatureParent) : new XadesSignedXml(document); signedXml.SignedInfo.CanonicalizationMethod = CanonicalizationMethod; signedXml.SignedInfo.SignatureMethod = SignatureMethod; // if Xades, add object, qualifyingproperties and signedproperties if (SignatureType != SignatureType.XmlDSig) { CreateXadesQualifyingProperties(signedXml, document, certificate); } // add reference for each file foreach (XadesReference item in References) { if (item.Fragment != null) { signedXml.AddXadesObject(new DataObject(item.Id, null, null, (XmlElement)document.ImportNode(item.Fragment, true))); } signedXml.AddReference(item.GetReference(UriResolver)); } // set key KeyInfo keyInfo = new KeyInfo(); keyInfo.AddClause(new KeyInfoX509Data(certificate, X509IncludeOption.WholeChain)); signedXml.SigningKey = certificate.GetRSAPrivateKey(); signedXml.KeyInfo = keyInfo; // calculate signature signedXml.ComputeSignature(); XmlElement root = signedXml.GetXml(); return(root); }