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

Add support for Azure Policy Assignment metadata #7725

Merged
48 changes: 48 additions & 0 deletions azurerm/internal/services/policy/policy_assignment_resource.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,12 @@ import (
"context"
"fmt"
"log"
"reflect"
"strconv"
"time"

"encoding/json"

"github.com/Azure/azure-sdk-for-go/services/resources/mgmt/2019-09-01/policy"
"github.com/hashicorp/terraform-plugin-sdk/helper/resource"
"github.com/hashicorp/terraform-plugin-sdk/helper/schema"
Expand Down Expand Up @@ -123,10 +126,43 @@ func resourceArmPolicyAssignment() *schema.Resource {
Optional: true,
Elem: &schema.Schema{Type: schema.TypeString},
},

"metadata": {
tyconsulting marked this conversation as resolved.
Show resolved Hide resolved
Type: schema.TypeString,
Optional: true,
Computed: true,
tyconsulting marked this conversation as resolved.
Show resolved Hide resolved
ValidateFunc: validation.StringIsJSON,
DiffSuppressFunc: policyAssignmentsMetadataDiffSuppressFunc,
},
},
}
}

func policyAssignmentsMetadataDiffSuppressFunc(_, old, new string, _ *schema.ResourceData) bool {
var oldPolicyAssignmentsMetadata map[string]interface{}
errOld := json.Unmarshal([]byte(old), &oldPolicyAssignmentsMetadata)
if errOld != nil {
return false
}

var newPolicyAssignmentsMetadata map[string]interface{}
if new != "" {
errNew := json.Unmarshal([]byte(new), &newPolicyAssignmentsMetadata)
if errNew != nil {
return false
}
}

// Ignore the following keys if they're found in the metadata JSON
ignoreKeys := [5]string{"assignedBy", "createdBy", "createdOn", "updatedBy", "updatedOn"}
for _, key := range ignoreKeys {
delete(oldPolicyAssignmentsMetadata, key)
delete(newPolicyAssignmentsMetadata, key)
}

return reflect.DeepEqual(oldPolicyAssignmentsMetadata, newPolicyAssignmentsMetadata)
}

func resourceArmPolicyAssignmentCreateUpdate(d *schema.ResourceData, meta interface{}) error {
client := meta.(*clients.Client).Policy.AssignmentsClient
ctx, cancel := timeouts.ForCreateUpdate(meta.(*clients.Client).StopContext, d)
Expand Down Expand Up @@ -181,6 +217,14 @@ func resourceArmPolicyAssignmentCreateUpdate(d *schema.ResourceData, meta interf
assignment.AssignmentProperties.Parameters = expandedParams
}

if metaDataString := d.Get("metadata").(string); metaDataString != "" {
metaData, err := structure.ExpandJsonFromString(metaDataString)
if err != nil {
return fmt.Errorf("unable to parse metadata: %s", err)
}
assignment.AssignmentProperties.Metadata = &metaData
}

if v, ok := d.GetOk("not_scopes"); ok {
assignment.AssignmentProperties.NotScopes = expandAzureRmPolicyNotScopes(v.([]interface{}))
}
Expand Down Expand Up @@ -257,6 +301,10 @@ func resourceArmPolicyAssignmentRead(d *schema.ResourceData, meta interface{}) e
d.Set("display_name", props.DisplayName)
d.Set("enforcement_mode", props.EnforcementMode == policy.Default)

if metadataStr := flattenJSON(props.Metadata); metadataStr != "" {
d.Set("metadata", metadataStr)
}

if params := props.Parameters; params != nil {
json, err := flattenParameterValuesValueToString(params)
if err != nil {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -241,6 +241,13 @@ resource "azurerm_policy_assignment" "test" {
name = "acctestpa-%[1]d"
scope = azurerm_resource_group.test.id
policy_definition_id = azurerm_policy_definition.test.id

metadata = <<METADATA
tyconsulting marked this conversation as resolved.
Show resolved Hide resolved
{
"category": "General"
}
METADATA

}
`, data.RandomInteger, data.Locations.Primary)
}
Expand Down
8 changes: 8 additions & 0 deletions website/docs/r/policy_assignment.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,12 @@ resource "azurerm_policy_assignment" "example" {
description = "Policy Assignment created via an Acceptance Test"
display_name = "My Example Policy Assignment"

metadata = <<METADATA
{
"category": "General"
}
METADATA

parameters = <<PARAMETERS
{
"allowedLocations": {
Expand Down Expand Up @@ -90,6 +96,8 @@ The following arguments are supported:

* `display_name` - (Optional) A friendly display name to use for this Policy Assignment. Changing this forces a new resource to be created.

* `metadata` - (Optional) The metadata for the policy assignment. This is a json object representing additional metadata that should be stored with the policy assignment.

* `parameters` - (Optional) Parameters for the policy definition. This field is a JSON object that maps to the Parameters field from the Policy Definition. Changing this forces a new resource to be created.

~> **NOTE:** This value is required when the specified Policy Definition contains the `parameters` field.
Expand Down