I just found this API ridiculously confusing to use, and maybe I just suck, but I don't want to figure it out again, so I'm writing it down here
Optional, but if you have an established gpg home dir that you want to use or you don't want it chosen for you
GPGME::Engine.home_dir = "/some/dir" # e.g. env['GNUPG_HOME']
Note If you already have keys imported in that home dir, you can skip this part:
Only need to do once for each key, but repeated imports are ok too.
A very basic explanation of keys in case you're not familiar:
- Private keys
- You need to import at least 1 private key to decrypt anything asymmetrically encrypted
- You also need the private key in order to cryptographically "sign" something
- When you use a private key for one of these operations you'll usually need to provide a password or a password callback function (hook, agent etc) in order to get access to the private key
- Public keys
- You'll need 1 public key for each person or account for which you want to encrypt
- You'll also need these keys to verify they have cryptographically "signed" something
- If you aren't using some sort of chain of trust (web of trust) and/or the keys aren't signed by anyone you already trust, you'll need to specify always_trust :true
### The keys are "saved" in your GPGME::Engine.home_dir which is why they don't really persist in ruby land
File.open("keyfile", 'rb') do |key_file|
GPGME::Key.import(
key_file,
{armor: true, keylist_mode: GPGME::KEYLIST_MODE_LOCAL}
)
end
It will inherit the keys assuming you don't change home_dir again) Note You can specify options now and/or when you call additional methods or both
additional ctx options available
crypto = GPGME::Crypto.new({always_trust: true})
Note Most of the GPGME methods return a GPGME::Data object which can be read just like a typical IO object, but remember to seek(0) to return to the beginning if nec.
cipher_text = crypto.encrypt(
"test text",
{recipients: '[email protected]'}
# or recipients: ['[email protected]', '[email protected]']
)
# recipients: could have been specified w/the crypto object or when calling encrypt
# same goes for always_trust:
clear_text = crypto.decrypt(
cipher_text,
{keylist_mode: GPGME::KEYLIST_MODE_LOCAL, password: 'blah'}
)
Note If you previously called cipher_text.read etc you'll need to first call cipher_text.seek 0
clear_text.read
clear_text.see(0) # optional