Skip to content

Commit

Permalink
Add etags to acm_service_perimeter_resource (#12736) (#9058)
Browse files Browse the repository at this point in the history
[upstream:0fcf74e7eb30d982aaead225987fc0ca71495724]

Signed-off-by: Modular Magician <[email protected]>
  • Loading branch information
modular-magician authored Jan 14, 2025
1 parent 25f3217 commit fce141a
Show file tree
Hide file tree
Showing 3 changed files with 54 additions and 8 deletions.
3 changes: 3 additions & 0 deletions .changelog/12736.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
```release-note:enhancement
accesscontextmanager: added `etag` to `google_access_context_manager_service_perimeter_resource` to prevent overriding list of resources
```
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,11 @@ Format: projects/{project_number}`,
Computed: true,
Description: `The name of the Access Policy this resource belongs to.`,
},
"etag": {
Type: schema.TypeString,
Computed: true,
Description: `The perimeter etag is internally used to prevent overwriting the list of perimeter resources on PATCH calls. It is retrieved from the same GET perimeter API call that's used to get the current list of resources. The resource to add or remove is merged into that list and then this etag is sent with the PATCH call along with the updated resource list.`,
},
},
UseJSONNumber: true,
}
Expand Down Expand Up @@ -122,6 +127,21 @@ func resourceAccessContextManagerServicePerimeterResourceCreate(d *schema.Resour
}

headers := make(http.Header)
etag := d.Get("etag").(string)

if etag == "" {
log.Printf("[ERROR] Unable to get etag: %s", err)
return nil
}
obj["etag"] = etag

// updateMask is a URL parameter but not present in the schema, so ReplaceVars
// won't set it
updateMask := []string{"status.resources", "etag"}
url, err = transport_tpg.AddQueryParams(url, map[string]string{"updateMask": strings.Join(updateMask, ",")})
if err != nil {
return err
}
res, err := transport_tpg.SendRequest(transport_tpg.SendRequestOptions{
Config: config,
Method: "PATCH",
Expand Down Expand Up @@ -213,10 +233,9 @@ func resourceAccessContextManagerServicePerimeterResourceRead(d *schema.Resource
if err != nil {
return transport_tpg.HandleNotFoundError(err, d, fmt.Sprintf("AccessContextManagerServicePerimeterResource %q", d.Id()))
}
// post_read template for access_context_manager_service_perimeter_resource

// this is a placeholder for now but in the future we can use this to access
// the etag from the read response
if err := d.Set("etag", res["etag"]); err != nil {
log.Printf("[ERROR] Unable to set etag: %s", err)
}

res, err = flattenNestedAccessContextManagerServicePerimeterResource(d, meta, res)
if err != nil {
Expand All @@ -233,6 +252,9 @@ func resourceAccessContextManagerServicePerimeterResourceRead(d *schema.Resource
if err := d.Set("resource", flattenNestedAccessContextManagerServicePerimeterResourceResource(res["resource"], d, config)); err != nil {
return fmt.Errorf("Error reading ServicePerimeterResource: %s", err)
}
if err := d.Set("etag", flattenNestedAccessContextManagerServicePerimeterResourceEtag(res["etag"], d, config)); err != nil {
return fmt.Errorf("Error reading ServicePerimeterResource: %s", err)
}

return nil
}
Expand Down Expand Up @@ -275,6 +297,21 @@ func resourceAccessContextManagerServicePerimeterResourceDelete(d *schema.Resour
}

headers := make(http.Header)
etag := d.Get("etag").(string)

if etag == "" {
log.Printf("[ERROR] Unable to get etag: %s", err)
return nil
}
obj["etag"] = etag

// updateMask is a URL parameter but not present in the schema, so ReplaceVars
// won't set it
updateMask := []string{"status.resources", "etag"}
url, err = transport_tpg.AddQueryParams(url, map[string]string{"updateMask": strings.Join(updateMask, ",")})
if err != nil {
return err
}

log.Printf("[DEBUG] Deleting ServicePerimeterResource %q", d.Id())
res, err := transport_tpg.SendRequest(transport_tpg.SendRequestOptions{
Expand Down Expand Up @@ -328,6 +365,10 @@ func flattenNestedAccessContextManagerServicePerimeterResourceResource(v interfa
return v
}

func flattenNestedAccessContextManagerServicePerimeterResourceEtag(v interface{}, d *schema.ResourceData, config *transport_tpg.Config) interface{} {
return v
}

func expandNestedAccessContextManagerServicePerimeterResourceResource(v interface{}, d tpgresource.TerraformResourceData, config *transport_tpg.Config) (interface{}, error) {
return v, nil
}
Expand Down Expand Up @@ -486,10 +527,9 @@ func resourceAccessContextManagerServicePerimeterResourceListForPatch(d *schema.
if err != nil {
return nil, err
}
// post_read template for access_context_manager_service_perimeter_resource

// this is a placeholder for now but in the future we can use this to access
// the etag from the read response
if err := d.Set("etag", res["etag"]); err != nil {
log.Printf("[ERROR] Unable to set etag: %s", err)
}
var v interface{}
var ok bool
if v, ok = res["status"]; ok && v != nil {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,9 @@ In addition to the arguments listed above, the following computed attributes are
* `access_policy_id` -
The name of the Access Policy this resource belongs to.

* `etag` -
The perimeter etag is internally used to prevent overwriting the list of perimeter resources on PATCH calls. It is retrieved from the same GET perimeter API call that's used to get the current list of resources. The resource to add or remove is merged into that list and then this etag is sent with the PATCH call along with the updated resource list.


## Timeouts

Expand Down

0 comments on commit fce141a

Please sign in to comment.