Not much time has passed since I last wrote about my progress on the PGPainless library. However, I feel like its time for an update.
Since the big 0.2.0 release, 4 further releases, 0.2.1 through 0.2.4 have been published. Taken together, the changes are quite substantial, so let me summarize.
Modular SOP Implementation
The (in my opinion) most exciting change is that there now is an experimental module of java interfaces that model the Stateless OpenPGP Protocol (SOP). This module named sop-java is completely independent from PGPainless and has no external dependencies whatsoever. Its basically a port of Sequoia-PGP’s sop crate (which in term is based around the Stateless OpenPGP Command Line Interface specification) to Java.
Applications that want to execute basic OpenPGP operations can depend on this interface and decide on the concrete implementation later without locking themselves in with one fixed implementation. Remember:
The Database Is a Detail. […] The Web Is a Detail. […] Frameworks Are Details.
Uncle Bob – Clean Architecture
The module sop-java-picocli contains a CLI frontend for sop-java
. It uses the picocli library to closely model the Stateless OpenPGP Command Line Interface (SOP-CLI) specification (version 1 for now).
The exciting part is that this module too is independent from PGPainless, but it can be used by any library that implements sop-java
.
Next up, the contents of pgpainless-sop drastically changed. While up until recently it contained a fully fledged SOP-CLI application which used pgpainless-core
directly, it now no longer contains command line application code, but instead an implementation of sop-java
using pgpainless-core
. Therefore pgpainless-sop
can be used as a drop-in for sop-java
, making it the first java-based SOP implementation (to my knowledge).
Lastly, pgpainless-cli brings sop-java-picocli
and pgpainless-sop
together. The code does little more than to plug pgpainless-sop
as SOP backend into the command line application, resulting in a fully functional OpenPGP command line application (basically what pgpainless-sop
was up until release 0.2.3, just better :P).
$ ./pgpainless-cli help Usage: pgpainless-cli [COMMAND] Commands: help Displays help information about the specified command armor Add ASCII Armor to standard input dearmor Remove ASCII Armor from standard input decrypt Decrypt a message from standard input encrypt Encrypt a message from standard input extract-cert Extract a public key certificate from a secret key from standard input generate-key Generate a secret key sign Create a detached signature on the data from standard input verify Verify a detached signature over the data from standard input version Display version information about the tool
The exciting part about this modular design is that if YOU are working on an OpenPGP library for Java, you don’t need to re-implement a CLI frontend on your own. Instead, you can implement the sop-java
interface and benefit from the CLI provided by sop-java-picocli
for free.
If you are a library consumer, depending on sop-java
instead of pgpainless-core
would allow you to swap out PGPainless for another library, should any emerge in the future. It also means that porting your application to other platforms and languages might become easier, thanks to the more or less fixed API provided by the SOP protocol.
Further Changes
There are some more exciting changes worth mentioning.
The whole PGPainless suite can now be built reproducibly!
$ gradle --quiet clean build &> /dev/null && md5sum {.,pgpainless-core,pgpainless-sop,pgpainless-cli,sop-java,sop-java-picocli}/build/libs/*.jar e7e9f45eb9d74540092920528bb0abf0 ./build/libs/PGPainless-0.2.4.jar 8ab68285202c8a303692c7332d15c2b2 pgpainless-core/build/libs/pgpainless-core-0.2.4.jar a9c1d7b4a47d5ec66fc65131c14f4848 pgpainless-sop/build/libs/pgpainless-sop-0.2.4.jar 08cfb620a69015190e45d66548b8ea0f pgpainless-cli/build/libs/pgpainless-cli-0.2.4.jar e309d5a8d3a9439c6fae1c56150d9d07 sop-java/build/libs/sop-java-0.2.4.jar 9901849535f57f04b615afb06216ae5c sop-java-picocli/build/libs/sop-java-picocli-0.2.4.jar
It actually was not hard at all to achieve reproducibility. The command line application has a version command, which extracted the current application version by accessing a version.properties
file which would be written during the Gradle build.
Unfortunately, Java’s implementation of the Properties
class includes a timestamp when writing out the object into a PrintStream
. Therefore the result was not reproducible. The fix was to write the file manually, without using a Properties
object.
Furthermore, the APIs for decryption/verification were further simplified, following the example of the encryption API. Instead of chained builder subclasses, there now is a single builder class which is used to receive decryption keys and public key certificates etc.
If you need more details about what changed in PGPainless, there now is a changelog file.
3 responses to “Progress on PGPainless Development”
@vanitasvitae great work!
[…] Progress on PGPainless Development […]
@vanitasvitae Hi it says here https://keys.openpgp.org/about/news#2019-11-12-celebrating-100k you celebrated 100k verified addresses in Nov 2019. I guess they must be a lot more now. Congratulations and thank you SO MUCH for such a massive good job. It has made using pgp easier. Thank you #openpgp #encryption #pgpainless