Skip to content

Commit 556bd7b

Browse files
bytemaintlimoncelli
authored andcommitted
ALIDNS: Implement ALIDNS Provider (#3878)
<!-- Please make sure you've run the following commands from the root directory. bin/generate-all.sh (this runs commands like "go generate", fixes formatting, and so on) Help keep the release changelog clear by pre-naming the proper section in the GitHub pull request title. Some examples: * CICD: Add required GHA permissions for goreleaser * DOCS: Fixed providers with "contributor support" table * ROUTE53: Allow R53_ALIAS records to enable target health evaluation More examples/context can be found in the file .goreleaser.yml under the 'build' > 'changelog' key. !--> #420 Please create the GitHub label 'provider-ALIDNS' --------- Co-authored-by: Tom Limoncelli <[email protected]>
1 parent 12d5a53 commit 556bd7b

File tree

21 files changed

+896
-3
lines changed

21 files changed

+896
-3
lines changed

.github/workflows/pr_integration_tests.yml

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ jobs:
5252
Write-Host "Integration test providers: $Providers"
5353
echo "integration_test_providers=$(ConvertTo-Json -InputObject $Providers -Compress)" >> $env:GITHUB_OUTPUT
5454
env:
55-
PROVIDERS: "['AXFRDDNS', 'AXFRDDNS_DNSSEC', 'AZURE_DNS','BIND','BUNNY_DNS','CLOUDFLAREAPI','CLOUDNS','CNR','DIGITALOCEAN','FORTIGATE','GANDI_V5','GCLOUD','HEDNS','HETZNER_V2','HEXONET','HUAWEICLOUD','INWX','JOKER','MYTHICBEASTS', 'NAMEDOTCOM','NS1','POWERDNS','ROUTE53','SAKURACLOUD','TRANSIP','VERCEL']"
55+
PROVIDERS: "['ALIDNS', 'AXFRDDNS', 'AXFRDDNS_DNSSEC', 'AZURE_DNS','BIND','BUNNY_DNS','CLOUDFLAREAPI','CLOUDNS','CNR','DIGITALOCEAN','FORTIGATE','GANDI_V5','GCLOUD','HEDNS','HETZNER_V2','HEXONET','HUAWEICLOUD','INWX','JOKER','MYTHICBEASTS', 'NAMEDOTCOM','NS1','POWERDNS','ROUTE53','SAKURACLOUD','TRANSIP','VERCEL']"
5656
ENV_CONTEXT: ${{ toJson(env) }}
5757
VARS_CONTEXT: ${{ toJson(vars) }}
5858
SECRETS_CONTEXT: ${{ toJson(secrets) }}
@@ -73,6 +73,7 @@ jobs:
7373
# PROVIDER DOMAIN LIST
7474
# These providers will be tested if the env variable is set.
7575
# Set it to the domain name to use during the test.
76+
ALIDNS_DOMAIN: ${{ vars.ALIDNS_DOMAIN }}
7677
AXFRDDNS_DOMAIN: ${{ vars.AXFRDDNS_DOMAIN }}
7778
AXFRDDNS_DNSSEC_DOMAIN: ${{ vars.AXFRDDNS_DNSSEC_DOMAIN }}
7879
AZURE_DNS_DOMAIN: ${{ vars.AZURE_DNS_DOMAIN }}
@@ -104,6 +105,9 @@ jobs:
104105
# The above providers have additional env variables they
105106
# need for credentials and such.
106107
#
108+
ALIDNS_ACCESS_KEY_ID: ${{ secrets.ALIDNS_ACCESS_KEY_ID }}
109+
ALIDNS_ACCESS_KEY_SECRET: ${{ secrets.ALIDNS_ACCESS_KEY_SECRET }}
110+
#
107111
AXFRDDNS_MASTER: ${{ secrets.AXFRDDNS_MASTER }}
108112
AXFRDDNS_NAMESERVERS: ${{ secrets.AXFRDDNS_NAMESERVERS }}
109113
AXFRDDNS_TRANSFER_KEY: ${{ secrets.AXFRDDNS_TRANSFER_KEY }}

.goreleaser.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ changelog:
3939
regexp: "(?i)^.*(major|new provider|feature)[(\\w)]*:+.*$"
4040
order: 1
4141
- title: 'Provider-specific changes:'
42-
regexp: "(?i)((adguardhome|akamaiedge|autodns|axfrd|azure|azure_private_dns|bind|bunnydns|cloudflare|cloudflareapi_old|cloudns|cnr|cscglobal|desec|digitalocean|dnsimple|dnsmadeeasy|doh|domainnameshop|dynadot|easyname|exoscale|fortigate|gandi|gcloud|gcore|hedns|hetzner|hetznerv2|hexonet|hostingde|huaweicloud|inwx|joker|linode|loopia|luadns|mythicbeasts|namecheap|namedotcom|netcup|netlify|ns1|opensrs|oracle|ovh|packetframe|porkbun|powerdns|realtimeregister|route53|rwth|sakuracloud|softlayer|transip|vercel|vultr).*:)+.*"
42+
regexp: "(?i)((adguardhome|akamaiedge|autodns|axfrd|azure|azure_private_dns|alidns|bind|bunnydns|cloudflare|cloudflareapi_old|cloudns|cnr|cscglobal|desec|digitalocean|dnsimple|dnsmadeeasy|doh|domainnameshop|dynadot|easyname|exoscale|fortigate|gandi|gcloud|gcore|hedns|hetzner|hetznerv2|hexonet|hostingde|huaweicloud|inwx|joker|linode|loopia|luadns|mythicbeasts|namecheap|namedotcom|netcup|netlify|ns1|opensrs|oracle|ovh|packetframe|porkbun|powerdns|realtimeregister|route53|rwth|sakuracloud|softlayer|transip|vercel|vultr).*:)+.*"
4343
order: 2
4444
- title: 'Documentation:'
4545
regexp: "(?i)^.*(docs)[(\\w)]*:+.*$"

OWNERS

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
providers/adguardhome @ishanjain28
22
providers/akamaiedgedns @edglynes
3+
providers/alidns @bytemain
34
providers/autodns @arnoschoon
45
providers/axfrddns @hnrgrgr
56
providers/azuredns @vatsalyagoel

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ Currently supported DNS providers:
1717

1818
- AdGuard Home
1919
- Akamai Edge DNS
20+
- Alibaba Cloud DNS (ALIDNS)
2021
- AutoDNS
2122
- AWS Route 53
2223
- AXFR+DDNS

commands/getZones.go

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -167,6 +167,12 @@ func GetZone(args GetZoneArgs) error {
167167
return fmt.Errorf("failed GetZone CDP: %w", err)
168168
}
169169

170+
// Get the actual provider type name from creds.json or args
171+
providerType := args.ProviderName
172+
if providerType == "" || providerType == "-" {
173+
providerType = providerConfigs[args.CredName][pproviderTypeFieldName]
174+
}
175+
170176
// decide which zones we need to convert
171177
zones := args.ZoneNames
172178
if len(args.ZoneNames) == 1 && args.ZoneNames[0] == "all" {
@@ -253,6 +259,13 @@ func GetZone(args GetZoneArgs) error {
253259
if defaultTTL == 0 {
254260
defaultTTL = prettyzone.MostCommonTTL(recs)
255261
}
262+
// If provider has a registered default TTL and no records exist or MostCommonTTL returns 0,
263+
// use the provider's default TTL
264+
if defaultTTL == 0 || defaultTTL == models.DefaultTTL {
265+
if providerDefaultTTL := providers.GetDefaultTTL(providerType); providerDefaultTTL > 0 {
266+
defaultTTL = providerDefaultTTL
267+
}
268+
}
256269
if defaultTTL != models.DefaultTTL && defaultTTL != 0 {
257270
o = append(o, fmt.Sprintf("DefaultTTL(%d)", defaultTTL))
258271
}

documentation/SUMMARY.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,7 @@
114114
* [Supported providers](provider/index.md)
115115
* [AdGuard Home](provider/adguardhome.md)
116116
* [Akamai Edge DNS](provider/akamaiedgedns.md)
117+
* [Alibaba Cloud DNS (ALIDNS)](provider/alidns.md)
117118
* [Amazon Route 53](provider/route53.md)
118119
* [AutoDNS](provider/autodns.md)
119120
* [AXFR+DDNS](provider/axfrddns.md)

documentation/provider/alidns.md

Lines changed: 126 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,126 @@
1+
## Configuration
2+
3+
This provider is for [Alibaba Cloud DNS](https://www.alibabacloud.com/product/dns) (also known as ALIDNS). To use this provider, add an entry to `creds.json` with `TYPE` set to `ALIDNS` along with your API credentials.
4+
5+
Example:
6+
7+
{% code title="creds.json" %}
8+
```json
9+
{
10+
"alidns": {
11+
"TYPE": "ALIDNS",
12+
"access_key_id": "YOUR_ACCESS_KEY_ID",
13+
"access_key_secret": "YOUR_ACCESS_KEY_SECRET"
14+
}
15+
}
16+
```
17+
{% endcode %}
18+
19+
Optionally, you can specify a `region_id`:
20+
21+
{% code title="creds.json" %}
22+
```json
23+
{
24+
"alidns": {
25+
"TYPE": "ALIDNS",
26+
"access_key_id": "YOUR_ACCESS_KEY_ID",
27+
"access_key_secret": "YOUR_ACCESS_KEY_SECRET",
28+
"region_id": "cn-hangzhou"
29+
}
30+
}
31+
```
32+
{% endcode %}
33+
34+
Note: The `region_id` defaults to `"cn-hangzhou"`. The region value does not affect DNS management (DNS is global), but Alibaba's SDK requires a region to be provided.
35+
36+
## Usage
37+
38+
An example configuration:
39+
40+
{% code title="dnsconfig.js" %}
41+
```javascript
42+
var REG_NONE = NewRegistrar("none");
43+
var DSP_ALIDNS = NewDnsProvider("alidns");
44+
45+
D("example.com", REG_NONE, DnsProvider(DSP_ALIDNS),
46+
A("test", "1.2.3.4"),
47+
CNAME("www", "example.com."),
48+
MX("@", 10, "mail.example.com."),
49+
);
50+
```
51+
{% endcode %}
52+
53+
## Activation
54+
55+
DNSControl depends on an Alibaba Cloud [RAM user](https://www.alibabacloud.com/help/en/ram/user-guide/overview-of-ram-users) with permissions to manage DNS records.
56+
57+
### Creating RAM User and Access Keys
58+
59+
1. Log in to the [RAM console](https://ram.console.aliyun.com/)
60+
2. Create a new RAM user or use an existing one
61+
3. Generate an AccessKey ID and AccessKey Secret for the user
62+
4. Attach the `AliyunDNSFullAccess` policy to the user
63+
64+
The minimum required permissions are:
65+
66+
```json
67+
{
68+
"Version": "1",
69+
"Statement": [
70+
{
71+
"Effect": "Allow",
72+
"Action": [
73+
"alidns:DescribeDomains",
74+
"alidns:DescribeDomainRecords",
75+
"alidns:DescribeDomainInfo",
76+
"alidns:AddDomainRecord",
77+
"alidns:UpdateDomainRecord",
78+
"alidns:DeleteDomainRecord"
79+
],
80+
"Resource": "*"
81+
}
82+
]
83+
}
84+
```
85+
86+
## Important Notes
87+
88+
### TTL Constraints
89+
90+
Alibaba Cloud DNS has different TTL constraints depending on your DNS edition:
91+
92+
- **Enterprise Ultimate Edition**: TTL can be as low as 1 second (1-86400)
93+
- **Personal Edition / Free Edition**: Minimum TTL is 600 seconds (600-86400)
94+
95+
DNSControl will automatically validate TTL values based on your domain's edition. If you attempt to use a TTL below the minimum for your edition, you will receive an error.
96+
97+
### Chinese Domain Name Support
98+
99+
ALIDNS supports Chinese domain names (IDN with Chinese characters). However:
100+
101+
- **Supported**: ASCII characters and Chinese characters (CJK Unified Ideographs)
102+
- **Not supported**: Other Unicode characters (e.g., German umlauts, Arabic script)
103+
104+
DNSControl will automatically convert between punycode and unicode as needed.
105+
106+
### Record Type Support
107+
108+
The following record types are supported:
109+
- A, AAAA, CNAME, MX, TXT, NS
110+
- CAA (requires quoted values: `0 issue "letsencrypt.org"`)
111+
- SRV
112+
113+
### TXT Record Constraints
114+
115+
Alibaba Cloud DNS has specific constraints for TXT records:
116+
- Cannot be empty
117+
- Maximum length: 512 bytes
118+
- Cannot contain unescaped double quotes
119+
- Cannot have trailing spaces
120+
- Cannot have unpaired backslashes (odd number of consecutive backslashes)
121+
122+
DNSControl will audit and reject records that violate these constraints.
123+
124+
## New Domains
125+
126+
If a domain does not exist in your Alibaba Cloud account, you must create it manually through the Alibaba Cloud console. DNSControl does not automatically create new domains for this provider.

documentation/provider/index.md

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ Jump to a table:
2727
| ------------- | ---------------- | ------------ | --------- |
2828
| [`ADGUARDHOME`](adguardhome.md) ||||
2929
| [`AKAMAIEDGEDNS`](akamaiedgedns.md) ||||
30+
| [`ALIDNS`](alidns.md) ||||
3031
| [`AUTODNS`](autodns.md) ||||
3132
| [`AXFRDDNS`](axfrddns.md) ||||
3233
| [`AZURE_DNS`](azure_dns.md) ||||
@@ -90,6 +91,7 @@ Jump to a table:
9091
| ------------- | -------------------------------------------------------------------- | ---------------------------------------------- | -------------- | --------- |
9192
| [`ADGUARDHOME`](adguardhome.md) |||||
9293
| [`AKAMAIEDGEDNS`](akamaiedgedns.md) |||||
94+
| [`ALIDNS`](alidns.md) |||||
9395
| [`AUTODNS`](autodns.md) |||||
9496
| [`AXFRDDNS`](axfrddns.md) |||||
9597
| [`AZURE_DNS`](azure_dns.md) |||||
@@ -152,6 +154,7 @@ Jump to a table:
152154
| ------------- | ---------------------------------------------------------- | ---------------------------------------------------------- | ------------------------------------------------------ | ------------------------------------------------------ | ------------------------------------------------------ |
153155
| [`ADGUARDHOME`](adguardhome.md) ||||||
154156
| [`AKAMAIEDGEDNS`](akamaiedgedns.md) ||||||
157+
| [`ALIDNS`](alidns.md) ||||||
155158
| [`AUTODNS`](autodns.md) ||||||
156159
| [`AXFRDDNS`](axfrddns.md) ||||||
157160
| [`AZURE_DNS`](azure_dns.md) ||||||
@@ -208,6 +211,7 @@ Jump to a table:
208211
| Provider name | [`DHCID`](../language-reference/domain-modifiers/DHCID.md) | [`NAPTR`](../language-reference/domain-modifiers/NAPTR.md) | [`SRV`](../language-reference/domain-modifiers/SRV.md) | [`SVCB`](../language-reference/domain-modifiers/SVCB.md) |
209212
| ------------- | ---------------------------------------------------------- | ---------------------------------------------------------- | ------------------------------------------------------ | -------------------------------------------------------- |
210213
| [`AKAMAIEDGEDNS`](akamaiedgedns.md) |||||
214+
| [`ALIDNS`](alidns.md) |||||
211215
| [`AUTODNS`](autodns.md) |||||
212216
| [`AXFRDDNS`](axfrddns.md) |||||
213217
| [`AZURE_DNS`](azure_dns.md) |||||
@@ -263,6 +267,7 @@ Jump to a table:
263267
| Provider name | [`CAA`](../language-reference/domain-modifiers/CAA.md) | [`HTTPS`](../language-reference/domain-modifiers/HTTPS.md) | [`SMIMEA`](../language-reference/domain-modifiers/SMIMEA.md) | [`SSHFP`](../language-reference/domain-modifiers/SSHFP.md) | [`TLSA`](../language-reference/domain-modifiers/TLSA.md) |
264268
| ------------- | ------------------------------------------------------ | ---------------------------------------------------------- | ------------------------------------------------------------ | ---------------------------------------------------------- | -------------------------------------------------------- |
265269
| [`AKAMAIEDGEDNS`](akamaiedgedns.md) ||||||
270+
| [`ALIDNS`](alidns.md) ||||||
266271
| [`AUTODNS`](autodns.md) ||||||
267272
| [`AXFRDDNS`](axfrddns.md) ||||||
268273
| [`AZURE_DNS`](azure_dns.md) ||||||
@@ -316,6 +321,7 @@ Jump to a table:
316321
| Provider name | [`AUTODNSSEC`](../language-reference/domain-modifiers/AUTODNSSEC_ON.md) | [`DNSKEY`](../language-reference/domain-modifiers/DNSKEY.md) | [`DS`](../language-reference/domain-modifiers/DS.md) |
317322
| ------------- | ----------------------------------------------------------------------- | ------------------------------------------------------------ | ---------------------------------------------------- |
318323
| [`AKAMAIEDGEDNS`](akamaiedgedns.md) ||||
324+
| [`ALIDNS`](alidns.md) ||||
319325
| [`AUTODNS`](autodns.md) ||||
320326
| [`AXFRDDNS`](axfrddns.md) ||||
321327
| [`BIND`](bind.md) ||||
@@ -391,6 +397,7 @@ Providers in this category and their maintainers are:
391397
|Name|Maintainer|
392398
|---|---|
393399
|[`ADGUARDHOME`](adguardhome.md)|@ishanjain28|
400+
|[`ALIDNS`](alidns.md)|@bytemain|
394401
|[`AZURE_PRIVATE_DNS`](azure_private_dns.md)|@matthewmgamble|
395402
|[`AKAMAIEDGEDNS`](akamaiedgedns.md)|@edglynes|
396403
|[`AXFRDDNS`](axfrddns.md)|@hnrgrgr|
@@ -445,7 +452,6 @@ code to support this provider, we'd be glad to help in any way.
445452
*(The list below is sorted alphabetically.)*
446453

447454
* [1984 Hosting](https://github.com/StackExchange/dnscontrol/issues/1251) (#1251)
448-
* [Alibaba Cloud DNS](https://github.com/StackExchange/dnscontrol/issues/420)(#420)
449455
* [BookMyName](https://github.com/StackExchange/dnscontrol/issues/3451) (#3451)
450456
* [Constellix (DNSMadeEasy)](https://github.com/StackExchange/dnscontrol/issues/842) (#842)
451457
* [CoreDNS](https://github.com/StackExchange/dnscontrol/issues/1284) (#1284)

go.mod

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ require (
5959
require (
6060
github.com/Azure/azure-sdk-for-go/sdk/azcore v1.20.0
6161
github.com/G-Core/gcore-dns-sdk-go v0.3.3
62+
github.com/aliyun/alibaba-cloud-sdk-go v1.63.107
6263
github.com/aws/aws-sdk-go-v2/service/sts v1.41.2
6364
github.com/centralnicgroup-opensource/rtldev-middleware-go-sdk/v5 v5.0.18
6465
github.com/failsafe-go/failsafe-go v0.9.2
@@ -127,13 +128,15 @@ require (
127128
github.com/hashicorp/go-hclog v1.6.3 // indirect
128129
github.com/hashicorp/go-retryablehttp v0.7.7 // indirect
129130
github.com/hashicorp/terraform-plugin-log v0.9.0 // indirect
131+
github.com/jmespath/go-jmespath v0.4.0 // indirect
130132
github.com/json-iterator/go v1.1.13-0.20220915233716-71ac16282d12 // indirect
131133
github.com/kolo/xmlrpc v0.0.0-20220921171641-a4b6fa1dd06b // indirect
132134
github.com/mattn/go-colorable v0.1.14 // indirect
133135
github.com/mitchellh/go-homedir v1.1.0 // indirect
134136
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
135137
github.com/modern-go/reflect2 v1.0.2 // indirect
136138
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect
139+
github.com/opentracing/opentracing-go v1.2.1-0.20220228012449-10b1cf09e00b // indirect
137140
github.com/patrickmn/go-cache v2.1.0+incompatible // indirect
138141
github.com/peterhellberg/link v1.2.0 // indirect
139142
github.com/pkg/browser v0.0.0-20240102092130-5ac0b6a4141c // indirect

0 commit comments

Comments
 (0)