Skip to content

Commit

Permalink
poc resource-level default tags support; vpc and subnet resources
Browse files Browse the repository at this point in the history
  • Loading branch information
anGie44 committed Mar 8, 2021
1 parent 50f17fd commit 7d85dac
Show file tree
Hide file tree
Showing 14 changed files with 1,672 additions and 96 deletions.
11 changes: 11 additions & 0 deletions .changelog/17974.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
```release-note:note
provider: New `default_tags` argument as a public preview for applying tags across all resources under a provider. Support for the functionality must be added to individual resources in the codebase and is only implemented for the `aws_subnet` and `aws_vpc` resources at this time. Until a general availability announcement, no compatibility promises are made with these provider arguments and their functionality.
```

```release-note:enhancement
aws_subnet: Support provider-wide default tags (in public preview, see note above)
```

```release-note:enhancement
aws_vpc: Support provider-wide default tags (in public preview, see note above)
```
9 changes: 6 additions & 3 deletions aws/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -191,9 +191,10 @@ type Config struct {
AllowedAccountIds []string
ForbiddenAccountIds []string

Endpoints map[string]string
IgnoreTagsConfig *keyvaluetags.IgnoreConfig
Insecure bool
DefaultTagsConfig *keyvaluetags.DefaultConfig
Endpoints map[string]string
IgnoreTagsConfig *keyvaluetags.IgnoreConfig
Insecure bool

SkipCredsValidation bool
SkipGetEC2Platforms bool
Expand Down Expand Up @@ -249,6 +250,7 @@ type AWSClient struct {
datapipelineconn *datapipeline.DataPipeline
datasyncconn *datasync.DataSync
daxconn *dax.DAX
DefaultTagsConfig *keyvaluetags.DefaultConfig
devicefarmconn *devicefarm.DeviceFarm
dlmconn *dlm.DLM
dmsconn *databasemigrationservice.DatabaseMigrationService
Expand Down Expand Up @@ -492,6 +494,7 @@ func (c *Config) Client() (interface{}, error) {
datapipelineconn: datapipeline.New(sess.Copy(&aws.Config{Endpoint: aws.String(c.Endpoints["datapipeline"])})),
datasyncconn: datasync.New(sess.Copy(&aws.Config{Endpoint: aws.String(c.Endpoints["datasync"])})),
daxconn: dax.New(sess.Copy(&aws.Config{Endpoint: aws.String(c.Endpoints["dax"])})),
DefaultTagsConfig: c.DefaultTagsConfig,
devicefarmconn: devicefarm.New(sess.Copy(&aws.Config{Endpoint: aws.String(c.Endpoints["devicefarm"])})),
dlmconn: dlm.New(sess.Copy(&aws.Config{Endpoint: aws.String(c.Endpoints["dlm"])})),
dmsconn: databasemigrationservice.New(sess.Copy(&aws.Config{Endpoint: aws.String(c.Endpoints["dms"])})),
Expand Down
76 changes: 76 additions & 0 deletions aws/internal/keyvaluetags/key_value_tags.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,11 @@ const (
ServerlessApplicationRepositoryTagKeyPrefix = `serverlessrepo:`
)

// DefaultConfig contains tags to default across all resources.
type DefaultConfig struct {
Tags KeyValueTags
}

// IgnoreConfig contains various options for removing resource tags.
type IgnoreConfig struct {
Keys KeyValueTags
Expand All @@ -50,6 +55,32 @@ func (tags KeyValueTags) IgnoreAws() KeyValueTags {
return result
}

// Merge calls keyvaluetags.Merge() on the given DefaultConfig.Tags, if any,
// with KeyValueTags provided as an argument, overriding the value
// of any tag with a matching key.
func (config *DefaultConfig) Merge(tags KeyValueTags) KeyValueTags {
if len(config.Tags) == 0 {
return tags
}

return config.Tags.Merge(tags)
}

// TagsEqual returns true if the given configuration's Tags
// are equal to those passed in as an argument;
// otherwise returns false
func (config *DefaultConfig) TagsEqual(tags KeyValueTags) bool {
if len(config.Tags) == 0 {
return len(tags) == 0
}

if len(tags) == 0 {
return false
}

return config.Tags.ContainsAll(tags)
}

// IgnoreConfig returns any tags not removed by a given configuration.
func (tags KeyValueTags) IgnoreConfig(config *IgnoreConfig) KeyValueTags {
if config == nil {
Expand Down Expand Up @@ -401,6 +432,27 @@ func (tags KeyValueTags) Hash() int {
return hash
}

// RemoveDefaultConfig returns tags not present in a DefaultConfig object
// in addition to tags with key/value pairs that override those in a DefaultConfig;
// however, if all tags present in the DefaultConfig object are equivalent to those
// in the given KeyValueTags, then the KeyValueTags are returned, effectively
// bypassing the need to remove differing tags.
func (tags KeyValueTags) RemoveDefaultConfig(config *DefaultConfig) KeyValueTags {
if config == nil || len(config.Tags) == 0 {
return tags
}

result := make(KeyValueTags)

for k, v := range tags {
if defaultVal, ok := config.Tags[k]; !ok || !v.Equal(defaultVal) {
result[k] = v
}
}

return result
}

// String returns the default string representation of the KeyValueTags.
func (tags KeyValueTags) String() string {
var builder strings.Builder
Expand Down Expand Up @@ -435,6 +487,30 @@ func (tags KeyValueTags) UrlEncode() string {
return values.Encode()
}

// MergeConfigTags creates KeyValueTags by merging KeyValueTags nested in
// a configuration object with those represented as a map[string]interface{}.
// Currently only supports the DefaultConfig type when passed to the interface{} argument.
func MergeConfigTags(config interface{}, tags map[string]interface{}) KeyValueTags {
kvTags := New(tags)

if config == nil {
return kvTags
}

var result KeyValueTags

switch t := config.(type) {
case *DefaultConfig:
if t == nil || len(t.Tags) == 0 {
result = kvTags
} else {
result = t.Merge(kvTags)
}
}

return result
}

// New creates KeyValueTags from common Terraform Provider SDK types.
// Supports map[string]string, map[string]*string, map[string]interface{}, and []interface{}.
// When passed []interface{}, all elements are treated as keys and assigned nil values.
Expand Down
Loading

0 comments on commit 7d85dac

Please sign in to comment.