Deleting a private key on macOS Big Sur hangs
Opened this issue · 4 comments
I've encountered an issue where deleting a key would hang forever, using the following code:
GPGME::Key.find(:public, key_id).each { |k| k.delete!(true) }
# or
GPGME::Key.find(:private key_id).each { |k| k.delete!(true) }
�(B�(B�(0lqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqqk�(B�(B�(0x�(B Do you really want to permanently delete the OpenPGP secret key: �(0x�(B�(B�(0x�(B "EnsoTest <test@example.com>"�(0x�(B�(B�(0x�(B 2048-bit RSA key, ID 0FDD92544BA73B80,�(0x�(B�(B�(0x�(B created 2020-08-25.�(0x�(B�(B�(0x�(B ?�(0x�(B�(B�(0x�(B�(B�(0x�(B�(B�(0x�(B �(B<Delete key>�(B
If the key is a public key with no associated private key it works fine. If this is a public key with an associated private key, or if it is a private key itself, it will hang for around 2 minutes.
I have been able to reproduce this every time when running rspec on a Rails 6.0 project; the key was generated once and is re-added to the my test env using:
private_key = IO.read('spec/support/test_gpg')
key_id = GPGME::Key.import(private_key).imports.map(&:fpr)
Maybe there is an additional argument or configuration that is missing to prevent user confirmation via STDIN ?
@dvkch were you able to find any workaround to input the user confirmation?
@errfanwadia Unfortunately not. There might be a way in Ruby to connect to STDIN and STDOUT to know when the lib asks for confirmation and write it to STDOUT programmatically from another thread, but I haven't had the chance to test it though
The current gem is not supporting this for now but the gpg/gpgme
has an additional function gpgme_op_delete_ext
where we can put the flags for the force delete:
/* Flags for the key delete functions. */
#define GPGME_DELETE_ALLOW_SECRET (1 << 0) /* Also delete secret key. */
#define GPGME_DELETE_FORCE (1 << 1) /* Do not ask user to confirm. */
see:
@errfanwadia Unfortunately not. There might be a way in Ruby to connect to STDIN and STDOUT to know when the lib asks for confirmation and write it to STDOUT programmatically from another thread, but I haven't had the chance to test it though
you can definitely do this, but it is kind of painful obviously. All 3 are predefined as IO objects named STDOUT
, STDIN
, and STDERR
. Instead tho, you might consider just marking the key untrusted. It will still be there, but not get used normally.