Hello guys! It’s been a while since my last post about GroupDocs.Signature for Java. So, our Java community might have been waiting for something new regarding our e-signature API. Well, we have recently released version 19.7 of GroupDocs.Signature for Java and today, I shall give you an overview of something interesting that we have introduced in our latest release.
In the last couple of months, we introduced a quite valuable feature in the .NET variant related to the metadata signatures - signing documents with custom metadata. We have now introduced this feature in the Java API as well. So now, you can define and use the custom objects as metadata signatures using GroupDocs.Signature for Java.
Signing document with custom metadata objects becomes useful when you want to embed the metadata signatures containing the information/data of your own choice. For example, you may want to embed the information to the document about who did sign the document, the date when the document was signed and so on. In that case, you can not use the built-in metadata properties of the documents. This is where you can use the custom objects in metadata signatures.
For this, the following classes are extended with new public method AddSignature.
- WordsMetadataSignature - for Word documents
- SlidesMetadataSignature - for Presentations
- CellsMetadataSignature - for Spreadsheets
- PdfMetadataSignature - for PDF documents
This method creates new metadata signature with passed arguments (name and value), adds the signature to list of metadata signatures and returns the newly created object as a result.
Let’s now check out how to add the custom object in the metadata signature. I am assuming that we have to sign the Word document, therefore, I’ll be using the classes that work with the Word documents.
The following is the custom class containing the data members that I want to embed as the metadata signature in the document.
// For complete examples and data files, please go to https://github.com/groupdocs-signature/GroupDocs.Signature-for-Java | |
public static class DocumentSignature | |
{ | |
public String getVersion(){ return Version; } | |
public void setVersion(String value){ Version = value; } | |
// specify SkipSerialization attribute to skip this field on serialization | |
@SkipSerializationAttribute() | |
public String Version; | |
public boolean isProcessed(){ return IsProcessed; } | |
public void setProcessed(boolean value){ IsProcessed = value; } | |
// specify SkipSerialization attribute to skip this field on serialization | |
@SkipSerializationAttribute() | |
public boolean IsProcessed; | |
public String getID(){ return ID; } | |
public void setID(String value){ ID = value; } | |
@FormatAttribute(propertyName = "SignatureID") | |
public String ID; | |
public String getAuthor(){ return Author; } | |
public void setAuthor(String value){ Author = value; } | |
@FormatAttribute (propertyName = "Author") | |
public String Author; | |
public java.util.Date getSigned() { return Signed; } | |
public void setSigned(java.util.Date value) { Signed = value; } | |
@FormatAttribute (propertyName = "SignatureDate",propertyFormat = "yyyy-MM-dd") | |
public java.util.Date Signed = new java.util.Date(); | |
public java.math.BigDecimal getDataFactor() { return DataFactor; } | |
public void setDataFactor(java.math.BigDecimal value) { DataFactor = value; } | |
@FormatAttribute (propertyName = "Factor", propertyFormat = "N2") | |
public java.math.BigDecimal DataFactor = new java.math.BigDecimal(0.01); | |
} |
And this is how we would create the object of the custom class and then add that object to the metadata signature collection of the input document.
// For complete examples and data files, please go to https://github.com/groupdocs-signature/GroupDocs.Signature-for-Java | |
// setup key and passphrase | |
String key = "1234567890"; | |
String salt = "1234567890"; | |
// create data encryption | |
IDataEncryption encryption = new SymmetricEncryption(SymmetricAlgorithmType.Rijndael, key, salt); | |
// setup Signature configuration | |
SignatureConfig signConfig = new SignatureConfig(); | |
signConfig.setStoragePath(BaseTestData.getTestDataPath() +"\\Storage"); | |
signConfig.setOutputPath(BaseTestData.getTestDataPath() +"\\Output"); | |
// instantiate the signature handler | |
SignatureHandler<String> handler = new SignatureHandler<String>(signConfig); | |
// setup signature options | |
WordsMetadataSignOptions signOptions = new WordsMetadataSignOptions(); | |
// create custom object | |
DocumentSignature signature = new DocumentSignature(); | |
signature.setID(Guid.newGuid().toString()); | |
signature.setAuthor(System.getenv("USERNAME")); | |
signature.setSigned(new java.util.Date()); | |
signature.setDataFactor(new java.math.BigDecimal("11.22")); | |
// add custom object to sigature collection | |
WordsMetadataSignature mdDocument = signOptions.addSignature("DocumentSignature", signature); | |
// set encryption | |
mdDocument.setDataEncryption(encryption); | |
SaveOptions so = new SaveOptions(); | |
so.setOutputType(OutputType.String); | |
so.setOutputFileName("SignedMedataDataEncrypted.docx"); | |
// sign document | |
String signedPath = handler.<String>sign("test.docx", signOptions, so); | |
System.out.print("Signed file path is: " + signedPath); |
Did you notice that I have done something extra in the code before signing the document? Yes, after adding the object to the signature collection, I have encrypted it to make it secure. So you can avoid the custom metadata signatures to be captured by the unauthorized persons by applying the encryption.
That is not the end yet! You can also search your custom objects within the metadata signature collection of the documents using SignatureHandler.search method. The following code snippet shows how to search the encrypted object that we have added before.
// For complete examples and data files, please go to https://github.com/groupdocs-signature/GroupDocs.Signature-for-Java | |
// setup key and pasphrase | |
String key = "1234567890"; | |
String salt = "1234567890"; | |
// create data encryption | |
IDataEncryption encryption = new SymmetricEncryption(SymmetricAlgorithmType.Rijndael, key, salt); | |
// setup Signature configuration | |
SignatureConfig signConfig = new SignatureConfig(); | |
signConfig.setStoragePath(BaseTestData.getTestDataPath() +"\\Storage"); | |
signConfig.setOutputPath(BaseTestData.getTestDataPath() +"\\Output"); | |
// instantiate the signature handler | |
SignatureHandler handler = new SignatureHandler(signConfig); | |
// setup search options | |
WordsSearchMetadataOptions searchOptions = new WordsSearchMetadataOptions(); | |
// search document | |
SearchResult result = handler.search("SignedMedataDataEncrypted.docx", searchOptions); | |
// output signatures | |
java.util.List<WordsMetadataSignature> signatures = result.toList(WordsMetadataSignature.class); | |
Iterator tmp0 = ( signatures).iterator(); | |
while (tmp0.hasNext()){ | |
WordsMetadataSignature signature = (WordsMetadataSignature)tmp0.next(); | |
if (signature != null && signature.getName().equals("DocumentSignature")){ | |
DocumentSignature docSignature = signature.<DocumentSignature>getData(DocumentSignature.class, encryption); | |
if (docSignature != null){ | |
System.out.print("Found DocumentSignature signature: #"+docSignature.getID()+". Author "+docSignature.getAuthor()+" from "+docSignature.getDataFactor()+". Factor: " +docSignature.getDataFactor() ); | |
} | |
} | |
} |
For adding and searching encrypted custom objects in other document formats, please visit the documentation.
In addition to the above-mentioned features, we have also added some improvements regarding .djvu file format as well as three bug fixes. For details, please have a look at the release notes.
If you are interested in using the newly arrived features in your e-signing application, just download and integrate the latest release. For working code samples, download or clone our examples project from GitHub repository.
In case you would have any questions or suggestions, just create a topic on our forum and we would love to have a conversation with you.