commit f61a8f2ce8c5195e597437c73099ef4cdc4d410c Author: Konstantin Ryabitsev mricon@kernel.org Date: Tue Jan 24 14:03:57 2012 -0500
Add support for gpg-signing the email.
Caveats: 1. Signed+encrypted emails seem to break evolution 2. Must specify signer, because gpgme seems to think that all keys are capable of can_sign.
etc/epylog.conf.in | 9 ++++-- man/epylog.conf.5 | 34 +++++++++++++++++++-------- py/epylog/publishers.py | 59 +++++++++++++++++++++++++++++++++++------------ 3 files changed, 74 insertions(+), 28 deletions(-) --- diff --git a/etc/epylog.conf.in b/etc/epylog.conf.in index 323737d..0495214 100644 --- a/etc/epylog.conf.in +++ b/etc/epylog.conf.in @@ -24,12 +24,15 @@ rawlogs_limit = 200 # GPG encryption requires pygpgme installed # gpg_encrypt = no -# If gpg_keyring is omitted, we'll use the default ~/.gnupg for the +# If gpg_keyringdir is omitted, we'll use the default ~/.gnupg for the # user running epylog (/root/.gnupg, usually). -#gpg_keyring = %%pkgconfdir%%/pubring.gpg +#gpg_keyringdir = %%pkgconfdir%%/gpg/ # List key ids, can be emails or fingerprints. If omitted, we'll -# encrypt to all keys found in the keyring. +# encrypt to all keys found in the pubring. #gpg_recipients = admin1@example.com, admin2@example.com +# List key ids that we should use to sign the report. +# If omitted, the report will not be signed, only encrypted. +#gpg_signers = epylog@logserv.example.com
[file] method = file diff --git a/man/epylog.conf.5 b/man/epylog.conf.5 index 9582481..5ab6d07 100644 --- a/man/epylog.conf.5 +++ b/man/epylog.conf.5 @@ -118,20 +118,34 @@ designated administrators. Set to "yes" to enable gpg-encryption of the mail report. You will need to install mygpgme (installed by default on all yum-managed systems). .TP -.B gpg_keyring -This is the gpg keyring containing the public keys of recipients. You can -generate it using the following command: +.B gpg_keyringdir +If you don't want to use the default keyring (usually /root/.gnupg), you +can set up a separate keyring directory for epylog's use. E.g.: .br -> gpg --no-default-keyring --keyring=./epylog.gpg --search KEYID -.br -This will query the keyserver and display all matching keys, which you can -then import into epylog's pubring. You can repeat this operation multiple -times if you need to encrypt to several recipients. +> mkdir -m 0700 /etc/epylog/gpg .TP .B gpg_recipients List of PGP key id's to use when encrypting the report. The keys must be in -the keyring specified in gpg_keyring. If this option is omitted, epylog will -encrypt to all keys found in the keyring. +the pubring specified in gpg_keyringdir. If this option is omitted, epylog +will encrypt to all keys found in the pubring. To add a public key to a +keyring, you can use the following command. +.br +> gpg [--homedir=/etc/epylog/gpg] --import pubkey.gpg +.br +You can generate the pubkey.gpg file by running "gpg --export KEYID" on your +workstation, or you can use "gpg --search" to import the public keys from +the keyserver. +.TP +.B gpg_signers +To use the signing option, you will first need to generate a private key: +.br +> gpg [--homedir=/etc/epylog/gpg] --gen-key +.br +Create a \fBsign-only RSA key\fR and leave the passphrase empty. You can then +use "gpg --export" to export the key you have generated and import it on the +workstation where you read mail. +.br +If gpg_signers is not set, the report will not be signed.
.SH "File Publisher" .TP diff --git a/py/epylog/publishers.py b/py/epylog/publishers.py index 2e6dbc3..6901ede 100644 --- a/py/epylog/publishers.py +++ b/py/epylog/publishers.py @@ -207,26 +207,33 @@ class MailPublisher: self.gpg_encrypt = config.getboolean(self.section, 'gpg_encrypt')
try: - # Copy the keyring specified into tmpprefix - gpg_keyring = config.get(self.section, 'gpg_keyring') - logger.put(5, 'Copying %s into %s' % (gpg_keyring, self.tmpprefix)) - shutil.copyfile(gpg_keyring, os.path.join(self.tmpprefix, 'pubring.gpg')) - self.gpg_keyringdir = self.tmpprefix + self.gpg_keyringdir = config.get(self.section, 'gpg_keyringdir') except: self.gpg_keyringdir = None
try: gpg_recipients = config.get(self.section, 'gpg_recipients') - addrs = gpg_recipients.split(',') + keyids = gpg_recipients.split(',') self.gpg_recipients = [] - for addr in addrs: - addr = addr.strip() - logger.put(5, 'adding gpg_recipient=%s' % addr) - self.gpg_recipients.append(addr) + for keyid in keyids: + keyid = keyid.strip() + logger.put(5, 'adding gpg_recipient=%s' % keyid) + self.gpg_recipients.append(keyid) except: # Will use all recipients found in the keyring self.gpg_recipients = None
+ try: + gpg_signers = config.get(self.section, 'gpg_signers') + keyids = gpg_signers.split(',') + self.gpg_signers = [] + for keyid in keyids: + keyid = keyid.strip() + logger.put(5, 'adding gpg_signer=%s' % keyid) + self.gpg_signers.append(keyid) + except: + self.gpg_signers = None + except: self.gpg_encrypt = 0
@@ -356,24 +363,43 @@ class MailPublisher: ctx.armor = True
recipients = [] + signers = [] logger.put(5, 'self.gpg_recipients = %s' % self.gpg_recipients) + logger.put(5, 'self.gpg_signers = %s' % self.gpg_signers)
if self.gpg_recipients is not None: for recipient in self.gpg_recipients: - logger.puthang(5, 'Looking for a key for %s' % recipient) + logger.puthang(5, 'Looking for an encryption key for %s' % recipient) recipients.append(ctx.get_key(recipient)) logger.endhang(5) else: - logger.put(5, 'Looking for all keys in the keyring') for key in ctx.keylist(): for subkey in key.subkeys: if subkey.can_encrypt: - logger.put(5, 'Found key=%s' % subkey.keyid) + logger.put(5, 'Found can_encrypt key=%s' % subkey.keyid) recipients.append(key) break
- ctx.encrypt(recipients, gpgme.ENCRYPT_ALWAYS_TRUST, - cleartext, ciphertext) + if self.gpg_signers is not None: + for signer in self.gpg_signers: + logger.puthang(5, 'Looking for a signing key for %s' % signer) + signers.append(ctx.get_key(signer)) + logger.endhang(5) + + if len(signers) > 0: + logger.puthang(3, 'Encrypting and signing the report') + ctx.signers = signers + ctx.encrypt_sign(recipients, gpgme.ENCRYPT_ALWAYS_TRUST, + cleartext, ciphertext) + logger.endhang(3) + + else: + logger.puthang(3, 'Encrypting the report') + ctx.encrypt(recipients, gpgme.ENCRYPT_ALWAYS_TRUST, + cleartext, ciphertext) + logger.endhang(3) + + logger.puthang(5, 'Creating the MIME envelope for PGP')
gpg_envelope_part = MIMEMultipart('encrypted') gpg_envelope_part.set_param('protocol', 'application/pgp-encrypted', @@ -396,8 +422,11 @@ class MailPublisher: gpg_envelope_part.attach(gpg_mime_version_part) gpg_envelope_part.attach(gpg_payload_part)
+ # envelope becomes the new root part root_part = gpg_envelope_part
+ logger.endhang(5) + except ImportError: logger.endhang(3) logger.put(0, 'Install pygpgme for GPG encryption support.')