Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix compatibility with Certbot < v2.0.0 & Certbot >= 2.1.0 #41

Merged
merged 7 commits into from
Dec 4, 2022

Conversation

HLFH
Copy link
Contributor

@HLFH HLFH commented Nov 24, 2022

You can see other plugins doing the fix for certbot 2.0 compatibility : domeneshop/certbot-dns-domeneshop@bf8e575

Otherwise, when using Certbot >= 2.0, you would get:

An unexpected error occurred:
AttributeError: module 'certbot.interfaces' has no attribute 'IAuthenticator'

It would be great to merge ;)
And release the next 1.4.2 version.

Thanks!

@obynio
Copy link
Owner

obynio commented Nov 25, 2022

I'll take a look asap, feel free to @ me if I forget

@HLFH
Copy link
Contributor Author

HLFH commented Nov 25, 2022

It is being said that my commit would break compatibility with Certbot < 2.0. desec-io/certbot-dns-desec#22.

I honestly think on Arch Linux, we are always up-to-date, so we can skip legacy, but if you want to consider backward compatibility, here is a similar commit: desec-io/certbot-dns-desec@04422d0.
On Arch Linux, I could ask the maintainer of your AUR package that the dependency certbot should be >= to 2.0.0. But again, your choice.

cc @obynio

@obynio
Copy link
Owner

obynio commented Nov 30, 2022

Well I'm a bit hesitant because I know that a lot of people use it on Debian and it might break on them :/

@obynio
Copy link
Owner

obynio commented Nov 30, 2022

What do you think about a very ugly fix like this ?

def try_registration(cls):
    try:
        interfaces.Installer.register(cls)
    except AttributeError:
        pass
    return cls 

@try_registration
@zope.interface.implementer(interfaces.IAuthenticator)
@zope.interface.provider(interfaces.IPluginFactory)
class Authenticator(dns_common.DNSAuthenticator):
[...]

@HLFH
Copy link
Contributor Author

HLFH commented Nov 30, 2022

@obynio See: certbot/certbot#9486

Each method of registering a plugin here will work in every Certbot version, except for v2.0.0, but will work in v2.1.0 and later.

My previous commits were supporting only Certbot v2.0.0 and later.
Your method breaks compatibility with Certbot v2.0.0 but supports Certbot < v2.0.0 and Certbot >= v2.1.0.
Sounds like the consensus is with your method: I have added the commits (I can squash them if necessary).

But we may want to wait for Certbot v2.1.0 to be released before merging.

@HLFH HLFH changed the title Remove zope for certbot 2.0 compatibility Fix compatibility with Certbot < v2.00 & Certbot >= 2.1.0 Nov 30, 2022
@HLFH HLFH changed the title Fix compatibility with Certbot < v2.00 & Certbot >= 2.1.0 Fix compatibility with Certbot < v2.0.0 & Certbot >= 2.1.0 Nov 30, 2022
@obynio
Copy link
Owner

obynio commented Nov 30, 2022

Yes, I would like to wait for certbot 2.1.0 to be released, but if they take too much time we might need to release the breaking change for certbot < 2.0.0 earlier... Let's wait and see for now.

@obynio
Copy link
Owner

obynio commented Nov 30, 2022

What a shame, if only certbot would allow adding dns plugins right into their codebase everything would be much simpler...

@obynio
Copy link
Owner

obynio commented Nov 30, 2022

I agree that Archlinux is important but unfortunately there is much more folks using this plugin on Debian-like system that would be very angry if we were to release a breaking change before they get the chance to upgrade their certbot 😔

@JulienPalard
Copy link
Contributor

Thank you both for taking the time to work on it.

@daveoconnor
Copy link

On Debian Bullseye with packaged certbot/stable,now 1.12.0-2 all [installed] for certbot -v I'm getting:

"An unexpected error occurred:
AttributeError: module 'certbot.interfaces' has no attribute 'IAuthenticator'"

When trying to update that image to use a pip installed certbot 2.0 I get the following when I try to run certbot with a complete cleaned volume for config, certs., etc:

An unexpected error occurred:
AttributeError: module 'certbot.interfaces' has no attribute 'IAuthenticator'

For us on Debian I'm not sure there's any way to win right now either way as things are at the moment.

I've a certificate expiring tomorrow night and then I'm in trouble.

@obynio
Copy link
Owner

obynio commented Dec 4, 2022

Alright, it appears there is nothing that can really fix this certbot mess. Let's merge and see.

@obynio obynio merged commit d5b566e into obynio:master Dec 4, 2022
@obynio
Copy link
Owner

obynio commented Dec 4, 2022

This fix was released in 1.4.2.

@daveoconnor
Copy link

Well, this is a nightmare (for all involved I'm sure).

I tried it again with 1.4.2 and still get the same error, turns out certbot 2 gets pulled in as a pip dependency for 1.4.2, and takes precedence over the apt installed certbot (this confusion is what happens when certbot errors out running certbot -v...

certbot 2.0.0 with certbot-plugin-gandi 1.4.2, no apt certbot:

An unexpected error occurred:
AttributeError: module 'certbot.interfaces' has no attribute 'IAuthenticator'

certbot 2.0.0 with certbot-plugin-gandi==1.4.1:

An unexpected error occurred:
AttributeError: module 'certbot.interfaces' has no attribute 'IAuthenticator'

After running pip uninstall certbot && apt install certbot and then reentering shell to run certbot it at least runs now, but:

$ certbot certonly -a certbot-plugin-gandi:dns --certbot-plugin-gandi:dns-credentials /etc/gandi/gandi.ini --email=$LETSENCRYPT_EMAIL --agree-tos --no-eff-email --force-renewal --dry-run
certbot: error: unrecognized arguments: --certbot-plugin-gandi:dns-credentials /etc/gandi/gandi.ini

Maybe the new syntax? Nope

$ certbot certonly --authenticator dns-gandi --dns-gandi-credentials /etc/gandi/gandi.ini --email=$LETSENCRYPT_EMAIL --agree-tos --no-eff-email --force-renewal --dry-run
...
certbot: error: unrecognized arguments: --dns-gandi-credentials /etc/gandi/gandi.ini

Ok, fine, lets try all of... certbot==[1.32.0 - 1.27.0] and certbot-plugin-gandi==1.4.2, 1.4.1, 1.4.0 (<1.4.0 = Gandi's unsupported API)

Gives:

Traceback (most recent call last):
  File "/usr/local/bin/certbot", line 5, in <module>
    from certbot.main import main
  File "/usr/local/lib/python3.10/site-packages/certbot/main.py", line 6, in <module>
    from certbot._internal import main as internal_main
  File "/usr/local/lib/python3.10/site-packages/certbot/_internal/main.py", line 28, in <module>
    from certbot import crypto_util
  File "/usr/local/lib/python3.10/site-packages/certbot/crypto_util.py", line 42, in <module>
    from certbot import interfaces
  File "/usr/local/lib/python3.10/site-packages/certbot/interfaces.py", line 21, in <module>
    from acme.client import ClientBase
ImportError: cannot import name 'ClientBase' from 'acme.client' (/usr/local/lib/python3.10/site-packages/acme/client.py)

At that point I gave up and decided to just create a cert manually and cross my fingers for 2 months time.

Thanks for all the work you put into this. It must be a pain for you.

@HLFH
Copy link
Contributor Author

HLFH commented Dec 5, 2022

@daveoconnor Certbot 2.1.0 has not been released yet. This PR fixes the compatibility with Certbot < 2.0.0 & Certbot >= 2.1.0, but drops the support for Certbot 2.0.0 because Certbot has decided as well to drop the support for its own version 2.0.0. If you want to use Certbot 2.0.0, you need to use the version 1.4.1 (not 1.4.2) of certbot-plugin-gandi and apply this commit manually probably located at /usr/lib/python3.10/site-packages/certbot_plugin_gandi/main.py:

And we dropped support for the very old syntax since version 1.4.1 as you can see here: #38.
Use the new syntax such as:

certbot certonly --cert-name daveoconnor.com -d daveoconnor.com -d \*.daveoconnor.com --key-type=ecdsa  --authenticator dns-gandi --dns-gandi-credentials /etc/letsencrypt/renewal/credentials/daveoconnor-gandi.ini --dns-gandi-propagation-seconds=60

But if you have an obsolete certbot package such as version 1.12.0 (because of Debian...), you can only use the old syntax and use certbot-plugin-gandi < 1.4.1, so I would recommend certbot-plugin-gandi 1.4.0 in this case.

Furthermore, certificate expiration is a nightmare, therefore, you should automate your renewal.
Such as in /etc/systemd/system/certbot.timer:

[Unit]
Description=Twice daily renewal of Let's Encrypt's certificates

[Timer]
OnCalendar=0/12:00:00
RandomizedDelaySec=1h
Persistent=true

[Install]
WantedBy=timers.target

And in /etc/systemd/system/certbot.service:

[Unit]
Description=Let's Encrypt renewal

[Service]
Type=oneshot
ExecStart=/usr/bin/certbot renew --quiet --agree-tos --deploy-hook "/usr/bin/certbot-ocsp-fetcher -o /etc/nginx/ocsp/"
ExecStartPost=/usr/sbin/systemctl reload nginx postfix dovecot

Don't use the --deploy-hook and -o arguments if you don't use Nginx and OCSP Must-Staple, but you can have a look at: https://github.com/tomwassenberg/certbot-ocsp-fetcher.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants