From e53bff904318e57ffded14c66aa71e96e1579b96 Mon Sep 17 00:00:00 2001 From: Matt Palmer <9059517+56KBs@users.noreply.github.com> Date: Mon, 8 Nov 2021 14:45:45 +0000 Subject: [PATCH] plugin/route53: Configurable AWS Endpoint (#4963) Provide the ability to configure the AWS endpoint Signed-off-by: Matthew Palmer --- plugin/route53/README.md | 14 ++++++++++++++ plugin/route53/setup.go | 13 ++++++++++--- plugin/route53/setup_test.go | 8 +++++++- 3 files changed, 31 insertions(+), 4 deletions(-) diff --git a/plugin/route53/README.md b/plugin/route53/README.md index b859d56ce..9dd6f49a1 100644 --- a/plugin/route53/README.md +++ b/plugin/route53/README.md @@ -16,6 +16,7 @@ The route53 plugin can be used when coredns is deployed on AWS or elsewhere. ~~~ txt route53 [ZONE:HOSTED_ZONE_ID...] { aws_access_key [AWS_ACCESS_KEY_ID AWS_SECRET_ACCESS_KEY] + aws_endpoint ENDPOINT credentials PROFILE [FILENAME] fallthrough [ZONES...] refresh DURATION @@ -34,6 +35,9 @@ route53 [ZONE:HOSTED_ZONE_ID...] { AWS credentials the same way as AWS CLI, e.g., environmental variables, AWS credentials file, instance profile credentials, etc. +* `aws_endpoint` can be used to control the endpoint to use when querying AWS (optional). **ENDPOINT** is the + URL of the endpoint to use. If this is not provided the default AWS endpoint resolution will occur. + * `credentials` is used for reading the credential **FILENAME** and setting the **PROFILE** name for a given zone. **PROFILE** is the AWS account profile name. Defaults to `default`. **FILENAME** is the AWS credentials filename, defaults to `~/.aws/credentials`. @@ -75,6 +79,16 @@ example.org { } ~~~ +Enable route53 with an explicit AWS endpoint: + +~~~ txt +example.org { + route53 example.org.:Z1Z2Z3Z4DZ5Z6Z7 { + aws_endpoint https://test.us-west-2.amazonaws.com + } +} +~~~ + Enable route53 with fallthrough: ~~~ txt diff --git a/plugin/route53/setup.go b/plugin/route53/setup.go index 6fd3db18e..ec775680c 100644 --- a/plugin/route53/setup.go +++ b/plugin/route53/setup.go @@ -26,8 +26,8 @@ var log = clog.NewWithPlugin("route53") func init() { plugin.Register("route53", setup) } // exposed for testing -var f = func(credential *credentials.Credentials) route53iface.Route53API { - return route53.New(session.Must(session.NewSession(&aws.Config{Credentials: credential}))) +var f = func(credential *credentials.Credentials, endpoint *string) route53iface.Route53API { + return route53.New(session.Must(session.NewSession(&aws.Config{Credentials: credential, Endpoint: endpoint}))) } func setup(c *caddy.Controller) error { @@ -44,6 +44,7 @@ func setup(c *caddy.Controller) error { sharedProvider := &credentials.SharedCredentialsProvider{} var providers []credentials.Provider var fall fall.F + var endpoint string refresh := time.Duration(1) * time.Minute // default update frequency to 1 minute @@ -79,6 +80,12 @@ func setup(c *caddy.Controller) error { SecretAccessKey: v[1], }, }) + case "aws_endpoint": + if c.NextArg() { + endpoint = c.Val() + } else { + return plugin.Error("route53", c.ArgErr()) + } case "upstream": c.RemainingArgs() // eats args case "credentials": @@ -120,7 +127,7 @@ func setup(c *caddy.Controller) error { } providers = append(providers, &credentials.EnvProvider{}, sharedProvider, defaults.RemoteCredProvider(*session.Config, session.Handlers)) - client := f(credentials.NewChainCredentials(providers)) + client := f(credentials.NewChainCredentials(providers), &endpoint) ctx, cancel := context.WithCancel(context.Background()) h, err := New(ctx, client, keys, refresh) if err != nil { diff --git a/plugin/route53/setup_test.go b/plugin/route53/setup_test.go index e521091f6..98e7caa8d 100644 --- a/plugin/route53/setup_test.go +++ b/plugin/route53/setup_test.go @@ -10,7 +10,7 @@ import ( ) func TestSetupRoute53(t *testing.T) { - f = func(credential *credentials.Credentials) route53iface.Route53API { + f = func(credential *credentials.Credentials, endpoint *string) route53iface.Route53API { return fakeRoute53{} } @@ -70,6 +70,12 @@ func TestSetupRoute53(t *testing.T) { {`route53 example.org { }`, true}, + {`route53 example.org:12345678 { + aws_endpoint +}`, true}, + {`route53 example.org:12345678 { + aws_endpoint https://localhost +}`, false}, } for _, test := range tests {