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

GoDaddy API Limitations #2269

Closed
3 tasks done
kanwhoa opened this issue Sep 10, 2024 · 18 comments · Fixed by #2270
Closed
3 tasks done

GoDaddy API Limitations #2269

kanwhoa opened this issue Sep 10, 2024 · 18 comments · Fixed by #2270

Comments

@kanwhoa
Copy link

kanwhoa commented Sep 10, 2024

Welcome

  • Yes, I'm using a binary release within 2 latest releases.
  • Yes, I've searched similar issues on GitHub and didn't find any.
  • Yes, I've included all information below (version, config, etc).

What did you expect to see?

The GoDaddy DNS provider cleans up old record of type TXT with name _acme-challenge.

Note that I understand this is not a lego fault, it's a change with the API access allowed by GoDaddy. However, after some playing, I found that the APIs which could be used for ACME are still open.

For example, the following request is allowed to delete:

curl --verbose \
  -X DELETE \
  -H "Authorization: sso-key x:y" \
  -d "" \
  "https://api.godaddy.com/v1/domains/domain.tld/records/TXT/_acme-challenge.infra"

So, there's likely some API used which is disallowed by the new policies put in place by GoDaddy. However, there seems to be some workarounds. Btw, the TXT record creation works without an issue.

What did you see instead?

The command line reported

failed to get all TXT records: unexpected status code: [status code: 403] body: {"code":"ACCESS_DENIED","message":"Authenticated user is not allowed access"

How do you use lego?

Binary

Reproduction steps

  1. Issue the command
GODADDY_API_KEY=x GODADDY_API_SECRET=y lego \
  --domains "subdomain.domain.tld" \
  --accept-tos --email "certificates@domain.tld" \
  --dns godaddy \
  --dns.resolvers "ns17.domaincontrol.com,ns18.domaincontrol.com" \
  --dns-timeout 600 \
  run

Version of lego

lego version 4.18.0 darwin/arm64

Logs

2024/09/10 14:19:22 [INFO] [subdomain.domain.tld] acme: Obtaining bundled SAN certificate
2024/09/10 14:19:23 [INFO] [subdomain.domain.tld] AuthURL: https://acme-v02.api.letsencrypt.org/acme/authz-v3/XXXXXXXXXXXXX
2024/09/10 14:19:23 [INFO] [subdomain.domain.tld] acme: Could not find solver for: tls-alpn-01
2024/09/10 14:19:23 [INFO] [subdomain.domain.tld] acme: Could not find solver for: http-01
2024/09/10 14:19:23 [INFO] [subdomain.domain.tld] acme: use dns-01 solver
2024/09/10 14:19:23 [INFO] [subdomain.domain.tld] acme: Preparing to solve DNS-01
2024/09/10 14:19:25 [INFO] [subdomain.domain.tld] acme: Trying to solve DNS-01
2024/09/10 14:19:25 [INFO] [subdomain.domain.tld] acme: Checking DNS record propagation. [nameservers=ns17.domaincontrol.com:53,ns18.domaincontrol.com:53]
2024/09/10 14:19:27 [INFO] Wait for propagation [timeout: 2m0s, interval: 2s]
2024/09/10 14:19:27 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:30 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:32 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:34 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:36 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:39 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:41 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:43 [INFO] [subdomain.domain.tld] acme: Waiting for DNS record propagation.
2024/09/10 14:19:50 [INFO] [subdomain.domain.tld] acme: Cleaning DNS-01 challenge
2024/09/10 14:19:51 [WARN] [subdomain.domain.tld] acme: cleaning up failed: godaddy: failed to get all TXT records: unexpected status code: [status code: 403] body: {"code":"ACCESS_DENIED","message":"Authenticated user is not allowed access"}
2024/09/10 14:19:51 [INFO] Deactivating auth: https://acme-v02.api.letsencrypt.org/acme/authz-v3/XXXXXXXXXXXXX
2024/09/10 14:19:51 Could not obtain certificates:
        error: one or more domains had a problem:

Go environment (if applicable)

$ go version && go env
# paste output here
@kanwhoa kanwhoa added the bug label Sep 10, 2024
@ldez
Copy link
Member

ldez commented Sep 10, 2024

https://go-acme.github.io/lego/dns/godaddy/index.html#additional-configuration

GoDaddy has recently (2024-04) updated the account requirements to access parts of their production Domains API:

Availability API: Limited to accounts with 50 or more domains.
Management and DNS APIs: Limited to accounts with 10 or more domains and/or an active Discount Domain Club plan.

https://community.letsencrypt.org/t/getting-unauthorized-url-error-while-trying-to-get-cert-for-subdomains/217329/12

Related to #2182

@ldez

This comment was marked as outdated.

@ldez ldez added question and removed bug labels Sep 10, 2024
@ldez
Copy link
Member

ldez commented Sep 10, 2024

You should consider replacing GoDaddy with a DNS provider with a better policy.

If you already own a domain in another DNS provider, you can use the CNAME approach, like that you will be able to still use your GoDaddy domain.

Sadly I have no other solution, the GoDaddy API policies are extremely bad.

@ldez ldez closed this as completed Sep 10, 2024
@kanwhoa
Copy link
Author

kanwhoa commented Sep 10, 2024

Hi,

I should have noted in my original, that the GET URL also appears to work without restriction:

curl --verbose \
  -X GET \
  -H "Authorization: sso-key x:y" \
  -d "" \
  "https://api.godaddy.com/v1/domains/domain.tld/records/TXT/_acme-challenge.infra"

This should allow getting all TXT record for a domain or subdomain. I'm not sure where the "Authenticated user is not allowed access" message is being generated from, the log line just before indicate that it is cleaning up. I'm not sure of the particular API being called at this point though.

2024/09/10 19:19:15 [INFO] [*.subdomain.domain.tld] acme: Cleaning DNS-01 challenge
2024/09/10 19:19:15 [WARN] [*.subdomain.domain.tld] acme: cleaning up failed: godaddy: failed to get all TXT records: unexpected status code: [status code: 403] body: {"code":"ACCESS_DENIED","message":"Authenticated user is not allowed access"}

@ldez
Copy link
Member

ldez commented Sep 10, 2024

Sorry, I mixed the 2 endpoints in my head but the problem is the same:

lego uses:

  • GET https://api.godaddy.com/v1/domains/example.com/records/TXT/_acme-challenge to get all the TXT records.
  • PUT https://api.godaddy.com/v1/domains/example.com/records/TXT/_acme-challenge to add/delete TXT records.

As there are no alternatives to add a TXT record then there is no solution.

@ldez
Copy link
Member

ldez commented Sep 10, 2024

After re-checking the doc, there is another endpoint https://developer.godaddy.com/doc/endpoint/domains#/v1/recordAdd

But I guess the limitations are the same as the PUT endpoint.

@ldez
Copy link
Member

ldez commented Sep 10, 2024

Also, it seems (from a post on a forum) like the API limitations are not the same for the apex (example.com/_acme-challenge.example.com) or a subdomain (foo.example.com/_acme-challenge.foo.example.com)

But I think this doesn't really change the possibilities.

@kanwhoa
Copy link
Author

kanwhoa commented Sep 10, 2024

let me re-clarify here:

Command Using LEGO Using curl
Add TXT record Working, no issue. Working, no issue.
Get TXT record ? Working, no issue.
Delete TXT record Not working - API limitation issue Working, no issue

I do get the issue with GoDaddy, and would encourage every user to make a formal complaint for a basic API access. However, it will be a commercial decision and so unlikely to change. That said, there appears to be a route to allow the Lego provider to work, but it seems like one particular API is being called which triggers the issue.

If there's a way to get HTTP trace logging out of Lego, I'm more than happy to debug, and locate the specific API being called that causes the issue.

@ldez
Copy link
Member

ldez commented Sep 10, 2024

The lego implementation for GoDaddy is basic:

It's the same call to add and "delete".

So nothing special.

failed to get all TXT records: unexpected status code: [status code: 403] body: {"code":"ACCESS_DENIED","message":"Authenticated user is not allowed access"

The error message is clear: it fails during the clean up when lego gets all domains.

The workflow is this one:

  • "present"
    • get all records
    • add the new record
  • "cleanup"
    • get all records
    • remove the new record

@ldez
Copy link
Member

ldez commented Sep 10, 2024

GoDaddy limitations are extreme: one call can work but 2 calls in a row are not working.

Clearly, you should go away from this DNS provider or use the CNAME approach with another DNS provider.

@kanwhoa
Copy link
Author

kanwhoa commented Sep 10, 2024

Found the issue.

The error in question is generated from the godaddy.go:177. The final argument to this call is a blank string. I presume at some point, this meant all records of type. This is passed to client.go:40 where it is placed into the request.

Replicating the call in curl gets the same API error:

curl \
  -X GET \
  -H "Authorization: sso-key x:y" \
  "https://api.godaddy.com/v1/domains/domain.tld/records/TXT/"
{"code":"ACCESS_DENIED","message":"Authenticated user is not allowed access"}

However, placing "_acme-challenge." in the final argument works correctly. 100% of the time.

e.g.

curl \
  -X GET \
  -H "Authorization: sso-key x:y" \
  "https://api.godaddy.com/v1/domains/domain.tld/records/TXT/_acme-challenge.subdomain"
[...]

The "subdomain" part should be the domain(s) between the root of the owned domain in the GoDaddy console and the record. For example requesting "a.b.c.example.com" and "example.com" is the owned domain, then the last part of the request should be "_acme-challenge.a.b.c"

@ldez

This comment was marked as outdated.

@ldez

This comment was marked as outdated.

@ldez
Copy link
Member

ldez commented Sep 10, 2024

oh I see

@ldez
Copy link
Member

ldez commented Sep 10, 2024

Can you try #2270 ?

@ldez ldez added the bug label Sep 10, 2024
@ldez
Copy link
Member

ldez commented Sep 10, 2024

In fact, there are some API changes because this implementation has been used since 2020 without problems.

Good catch 👍

I modified the implementation to follow your findings and also implemented the DELETE.

I will wait for your feedback about #2270.

@kanwhoa
Copy link
Author

kanwhoa commented Sep 10, 2024

Tested. There were some latent issues with the API. I've fixed and attached a diff. Sorry, was having trouble updating the PR.
godaddyfix.diff.patch

@ldez
Copy link
Member

ldez commented Sep 10, 2024

Most of your patch was already inside the PR, so I just kept the effective diff.

d424d2d

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

Successfully merging a pull request may close this issue.

2 participants