Skip to content

Commit

Permalink
Chore: add soft delete to configuration variable (#866)
Browse files Browse the repository at this point in the history
* add soft delete to configuration variable

* add soft delete flag to environment import resource

* streamline the soft delete test

* streamline soft delete test on config variable

* add default and change GetOk to Get

* fix configuration variable import

---------

Co-authored-by: Alon Noga <[email protected]>
Co-authored-by: Tomer Heber <[email protected]>
  • Loading branch information
3 people authored Jun 5, 2024
1 parent 44768b3 commit d5d18eb
Show file tree
Hide file tree
Showing 8 changed files with 114 additions and 3 deletions.
1 change: 1 addition & 0 deletions client/api_client.go
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,7 @@ type ApiClientInterface interface {
EnvironmentImportCreate(payload *EnvironmentImportCreatePayload) (*EnvironmentImport, error)
EnvironmentImportUpdate(id string, payload *EnvironmentImportUpdatePayload) (*EnvironmentImport, error)
EnvironmentImportGet(id string) (*EnvironmentImport, error)
EnvironmentImportDelete(id string) error
ConfigurationSetCreate(payload *CreateConfigurationSetPayload) (*ConfigurationSet, error)
ConfigurationSetUpdate(id string, payload *UpdateConfigurationSetPayload) (*ConfigurationSet, error)
ConfigurationSet(id string) (*ConfigurationSet, error)
Expand Down
14 changes: 14 additions & 0 deletions client/api_client_mock.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 4 additions & 0 deletions client/environment_import.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,3 +84,7 @@ func (client *ApiClient) EnvironmentImportGet(id string) (*EnvironmentImport, er

return &result, nil
}

func (client *ApiClient) EnvironmentImportDelete(id string) error {
return client.http.Delete("/environment-imports/"+id, nil)
}
12 changes: 12 additions & 0 deletions client/environment_import_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -107,4 +107,16 @@ var _ = Describe("Environment Import Client", func() {
})
})

Describe("EnvironmentImportDelete", func() {
var err error

BeforeEach(func() {
mockHttpClient.EXPECT().Delete("/environment-imports/"+mockEnvironmentImport.Id, nil).Times(1)
err = apiClient.EnvironmentImportDelete(mockEnvironmentImport.Id)
})

It("Should not return error", func() {
Expect(err).To(BeNil())
})
})
})
13 changes: 13 additions & 0 deletions env0/resource_configuration_variable.go
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,12 @@ func resourceConfigurationVariable() *schema.Resource {
Description: "the value of this variable must match provided regular expression (enforced only in env0 UI)",
Optional: true,
},
"soft_delete": {
Type: schema.TypeBool,
Description: "soft delete the configuration variable, once removed from the configuration it won't be deleted from env0",
Optional: true,
Default: false,
},
},
}
}
Expand Down Expand Up @@ -237,6 +243,11 @@ func resourceConfigurationVariableUpdate(ctx context.Context, d *schema.Resource
}

func resourceConfigurationVariableDelete(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics {
// don't delete if soft delete is set
if softDelete := d.Get("soft_delete"); softDelete.(bool) {
return nil
}

apiClient := meta.(client.ApiClientInterface)

id := d.Id()
Expand All @@ -250,6 +261,8 @@ func resourceConfigurationVariableDelete(ctx context.Context, d *schema.Resource
func resourceConfigurationVariableImport(ctx context.Context, d *schema.ResourceData, meta interface{}) ([]*schema.ResourceData, error) {
var configurationParams ConfigurationVariableParams
inputData := d.Id()
// soft delete isn't part of the configuration variable, so we need to set it
d.Set("soft_delete", false)
err := json.Unmarshal([]byte(inputData), &configurationParams)
// We need this conversion since getConfigurationVariable query by the scope and in our BE we use blueprint as the scope name instead of template
if string(configurationParams.Scope) == "TEMPLATE" {
Expand Down
23 changes: 23 additions & 0 deletions env0/resource_configuration_variable_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -773,4 +773,27 @@ resource "%s" "test" {
mock.EXPECT().ConfigurationVariableDelete(configVar.Id).Times(1).Return(nil)
})
})

t.Run("When soft delete is on, it should not actually delete", func(t *testing.T) {
createTestCase := resource.TestCase{
Steps: []resource.TestStep{
{
Config: resourceConfigCreate(resourceType, resourceName, map[string]interface{}{
"name": configVar.Name,
"description": configVar.Description,
"value": configVar.Value,
"is_read_only": strconv.FormatBool(*configVar.IsReadOnly),
"is_required": strconv.FormatBool(*configVar.IsRequired),
"soft_delete": true,
}),
},
},
}

runUnitTest(t, createTestCase, func(mock *client.MockApiClientInterface) {
mock.EXPECT().ConfigurationVariableCreate(configurationVariableCreateParams).Times(1).Return(configVar, nil)
mock.EXPECT().ConfigurationVariablesById(configVar.Id).Times(1).Return(configVar, nil)
mock.EXPECT().ConfigurationVariableDelete(configVar.Id).Times(0)
})
})
}
20 changes: 17 additions & 3 deletions env0/resource_environment_import.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,12 @@ func resourceEnvironmentImport() *schema.Resource {
Description: "iac version of the environment",
Optional: true,
},
"soft_delete": {
Type: schema.TypeBool,
Description: "soft delete the configuration variable, once removed from the configuration it won't be deleted from env0",
Optional: true,
Default: false,
},
},
}
}
Expand Down Expand Up @@ -126,9 +132,17 @@ func resourceEnvironmentImportUpdate(ctx context.Context, d *schema.ResourceData
return nil
}

// should not actually delete the environment import
// this resource is used to populate the environment import wizard data
// we don't want to delete the environment import after it's been created outside the wizard
func resourceEnvironmentImportDelete(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics {
// don't delete if soft delete is set
if softDelete := d.Get("soft_delete"); softDelete.(bool) {
return nil
}

apiClient := meta.(client.ApiClientInterface)

if err := apiClient.EnvironmentImportDelete(d.Id()); err != nil {
return diag.Errorf("could not delete environment import: %v", err)
}

return nil
}
30 changes: 30 additions & 0 deletions env0/resource_environment_import_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,37 @@ func TestEnvironmentImportResource(t *testing.T) {
gomock.InOrder(
mock.EXPECT().EnvironmentImportGet(gomock.Any()).Times(2).Return(&environmentImport, nil), // 1 after create, 1 before update
mock.EXPECT().EnvironmentImportGet(gomock.Any()).Times(1).Return(&updatedEnvironmentImport, nil), // 1 after update
mock.EXPECT().EnvironmentImportDelete(environmentImport.Id).Times(1), // 1 after update
)
})
})

t.Run("Environment Import soft delete", func(t *testing.T) {
environmentImport := client.EnvironmentImport{
Id: "id0",
Name: "name0",
}

testCase := resource.TestCase{
Steps: []resource.TestStep{
{
Config: resourceConfigCreate(resourceType, resourceName, map[string]interface{}{
"name": environmentImport.Name,
"soft_delete": true,
})},
},
}

runUnitTest(t, testCase, func(mock *client.MockApiClientInterface) {
mock.EXPECT().EnvironmentImportCreate(&client.EnvironmentImportCreatePayload{
Name: environmentImport.Name,
}).Times(1).Return(&environmentImport, nil)

gomock.InOrder(
mock.EXPECT().EnvironmentImportGet(gomock.Any()).Times(2).Return(&environmentImport, nil),
mock.EXPECT().EnvironmentImportDelete(environmentImport.Id).Times(0),
)
})
})

}

0 comments on commit d5d18eb

Please sign in to comment.