diff --git a/CHANGELOG.md b/CHANGELOG.md index 3223e7c7..f773a22b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,11 +1,16 @@ -## 1.4.0 (not yet released) +## 1.4.0 (March 4, 2024) FEATURES: * **New Resource:** `project_user` - Separate resource to manage project memberships for users. * **New Resource:** `project_group` - Separate resource to project project memberships for groups. -* resource/project: Add `cd ..` attribute to toggle if `project` resource should use its `member` or not to manage project users. Should be set to `true` when using in conjunction with `project_user` resource. -* resource/project: Add `use_project_group_resource` attribute to toggle if `project` resource should use its `group` or not to manage project users. Should be set to `true` when using in conjunction with `project_group` resource. +* resource/project: Add `use_project_user_resource` attribute to toggle if `project` resource should use its `member` or not to manage project users. Should be set to `false` to continue using existing `member` attribute. +* resource/project: Add `use_project_group_resource` attribute to toggle if `project` resource should use its `group` or not to manage project users. Should be set to `false` to continue using existing `group` attribute. +* resource/project: Switch default value for `use_project_role_resource` attribute to `true` so new provider practioners won't need to explicity set this attribute to use `project_role` resource. + +Issue: [#83](https://github.com/jfrog/terraform-provider-project/issues/83), [#98](https://github.com/jfrog/terraform-provider-project/issues/98) + +PR: [#101](https://github.com/jfrog/terraform-provider-project/pull/101) ## 1.3.5 (Feburary 9, 2024) diff --git a/docs/resources/project.md b/docs/resources/project.md index b876b86e..2f1085b8 100644 --- a/docs/resources/project.md +++ b/docs/resources/project.md @@ -101,9 +101,9 @@ resource "project" "myproject" { ~>This setting only applies to self-hosted environment. See [Manage Storage Quotas](https://jfrog.com/help/r/jfrog-platform-administration-documentation/manage-storage-quotas). - `description` (String) - `email_notification` (Boolean) Alerts will be sent when reaching 75% and 95% of the storage quota. This serves as a notification only and is not a blocker -- `group` (Block Set) Project group. Element has one to one mapping with the [JFrog Project Groups API](https://www.jfrog.com/confluence/display/JFROG/Artifactory+REST+API#ArtifactoryRESTAPI-UpdateGroupinProject) (see [below for nested schema](#nestedblock--group)) +- `group` (Block Set, Deprecated) Project group. Element has one to one mapping with the [JFrog Project Groups API](https://www.jfrog.com/confluence/display/JFROG/Artifactory+REST+API#ArtifactoryRESTAPI-UpdateGroupinProject) (see [below for nested schema](#nestedblock--group)) - `max_storage_in_gibibytes` (Number) Storage quota in GiB. Must be 1 or larger. Set to -1 for unlimited storage. This is translated to binary bytes for Artifactory API. So for a 1TB quota, this should be set to 1024 (vs 1000) which will translate to 1099511627776 bytes for the API. -- `member` (Block Set) Member of the project. Element has one to one mapping with the [JFrog Project Users API](https://www.jfrog.com/confluence/display/JFROG/Artifactory+REST+API#ArtifactoryRESTAPI-UpdateUserinProject). (see [below for nested schema](#nestedblock--member)) +- `member` (Block Set, Deprecated) Member of the project. Element has one to one mapping with the [JFrog Project Users API](https://www.jfrog.com/confluence/display/JFROG/Artifactory+REST+API#ArtifactoryRESTAPI-UpdateUserinProject). (see [below for nested schema](#nestedblock--member)) - `repos` (Set of String) (Optional) List of existing repo keys to be assigned to the project. **Note** We *strongly* recommend using this attribute to manage the list of repositories. If you wish to use the alternate method of setting `project_key` attribute in each `artifactory_*_repository` resource in the `artifactory` provider, you will need to use `lifecycle.ignore_changes` in the `project` resource to avoid state drift. ```hcl @@ -114,7 +114,9 @@ lifecycle { } ``` - `role` (Block Set, Deprecated) Project role. Element has one to one mapping with the [JFrog Project Roles API](https://www.jfrog.com/confluence/display/JFROG/Artifactory+REST+API#ArtifactoryRESTAPI-AddaNewRole) (see [below for nested schema](#nestedblock--role)) -- `use_project_role_resource` (Boolean) When set to true, this resource will ignore the `roles` attributes and allow roles to be managed by `project_role` resource instead. Default to false. +- `use_project_group_resource` (Boolean) When set to true, this resource will ignore the `group` attributes and allow users to be managed by `project_group` resource instead. Default to `true`. +- `use_project_role_resource` (Boolean) When set to true, this resource will ignore the `roles` attributes and allow roles to be managed by `project_role` resource instead. Default to `true`. +- `use_project_user_resource` (Boolean) When set to true, this resource will ignore the `member` attributes and allow users to be managed by `project_user` resource instead. Default to `true`. ### Read-Only diff --git a/docs/resources/user.md b/docs/resources/user.md index e44b8d78..30245bec 100644 --- a/docs/resources/user.md +++ b/docs/resources/user.md @@ -31,7 +31,7 @@ resource "project_user" "myuser" { ### Optional -- `ignore_missing_user` (Boolean) When set to true, the resource will not fail if the user does not exist. Default to false. This is useful when the user is externally managed and the local account wasn't created yet. +- `ignore_missing_user` (Boolean) When set to `true`, the resource will not fail if the user does not exist. Default to `false`. This is useful when the user is externally managed and the local account wasn't created yet. ### Read-Only diff --git a/pkg/project/membership_test.go b/pkg/project/membership_test.go index 6fe7534b..bc564858 100644 --- a/pkg/project/membership_test.go +++ b/pkg/project/membership_test.go @@ -42,6 +42,8 @@ func TestAccProject_membership(t *testing.T) { index_resources = true } + use_project_user_resource = false + member { name = "{{ .username1 }}" roles = ["{{ .developeRole }}"] @@ -60,6 +62,8 @@ func TestAccProject_membership(t *testing.T) { index_resources = true } + use_project_user_resource = false + member { name = "{{ .username1 }}" roles = ["{{ .developeRole }}", "{{ .contributorRole }}"] @@ -82,6 +86,8 @@ func TestAccProject_membership(t *testing.T) { manage_resources = true index_resources = true } + + use_project_user_resource = false } `, params) @@ -177,6 +183,8 @@ func TestAccProject_group(t *testing.T) { index_resources = true } + use_project_group_resource = false + group { name = "{{ .group1 }}" roles = ["{{ .developeRole }}"] @@ -195,6 +203,8 @@ func TestAccProject_group(t *testing.T) { index_resources = true } + use_project_group_resource = false + group { name = "{{ .group1 }}" roles = ["{{ .developeRole }}", "{{ .contributorRole }}"] @@ -217,6 +227,8 @@ func TestAccProject_group(t *testing.T) { manage_resources = true index_resources = true } + + use_project_group_resource = false } `, params) diff --git a/pkg/project/project_group.go b/pkg/project/project_group.go deleted file mode 100644 index 66e017b8..00000000 --- a/pkg/project/project_group.go +++ /dev/null @@ -1,42 +0,0 @@ -package project - -import ( - "context" - "fmt" - - "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - "github.com/jfrog/terraform-provider-shared/util" -) - -type ProjectGroup struct { - ProjectKey string `json:"-"` - Name string `json:"name"` - Roles []string `json:"roles"` -} - -func unpackProjectGroup(d *schema.ResourceData) ProjectGroup { - return ProjectGroup{ - ProjectKey: d.Get("project_key").(string), - Name: d.Get("name").(string), - Roles: util.CastToStringArr(d.Get("roles").(*schema.Set).List()), - } -} - -func packProjectGroup(ctx context.Context, data *schema.ResourceData, m ProjectGroup) diag.Diagnostics { - setValue := util.MkLens(data) - - setValue("name", m.Name) - setValue("project_key", m.ProjectKey) - errors := setValue("roles", m.Roles) - - if len(errors) > 0 { - return diag.Errorf("failed to pack project member %q", errors) - } - - return nil -} - -func (m ProjectGroup) Id() string { - return fmt.Sprintf(`%s:%s`, m.ProjectKey, m.Name) -} diff --git a/pkg/project/project_user.go b/pkg/project/project_user.go deleted file mode 100644 index 5154bdeb..00000000 --- a/pkg/project/project_user.go +++ /dev/null @@ -1,45 +0,0 @@ -package project - -import ( - "context" - "fmt" - - "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - "github.com/jfrog/terraform-provider-shared/util" -) - -type ProjectUser struct { - ProjectKey string `json:"-"` - Name string `json:"name"` - Roles []string `json:"roles"` - IgnoreMissingUser bool `json:"-"` -} - -func unpackProjectUser(d *schema.ResourceData) ProjectUser { - return ProjectUser{ - ProjectKey: d.Get("project_key").(string), - Name: d.Get("name").(string), - Roles: util.CastToStringArr(d.Get("roles").(*schema.Set).List()), - IgnoreMissingUser: d.Get("ignore_missing_user").(bool), - } -} - -func packProjectUser(ctx context.Context, data *schema.ResourceData, m ProjectUser) diag.Diagnostics { - setValue := util.MkLens(data) - - setValue("name", m.Name) - setValue("project_key", m.ProjectKey) - setValue("roles", m.Roles) - errors := setValue("ignore_missing_user", m.IgnoreMissingUser) - - if len(errors) > 0 { - return diag.Errorf("failed to pack project member %q", errors) - } - - return nil -} - -func (m ProjectUser) Id() string { - return fmt.Sprintf(`%s:%s`, m.ProjectKey, m.Name) -} diff --git a/pkg/project/repo.go b/pkg/project/repo.go index ab2ec69f..b0011a9e 100644 --- a/pkg/project/repo.go +++ b/pkg/project/repo.go @@ -99,7 +99,7 @@ var updateRepos = func(ctx context.Context, projectKey string, terraformRepoKeys return nil, fmt.Errorf("failed to add repos for project: %s", addErr) } - deleteErr := deleteRepos(ctx, projectKey, repoKeysToBeDeleted, m) + deleteErr := deleteRepos(ctx, repoKeysToBeDeleted, m) if deleteErr != nil { return nil, fmt.Errorf("failed to delete repos for project: %s", deleteErr) } @@ -139,7 +139,7 @@ var addRepo = func(ctx context.Context, projectKey string, repoKey RepoKey, req return err } -var deleteRepos = func(ctx context.Context, projectKey string, repoKeys []RepoKey, m interface{}) error { +var deleteRepos = func(ctx context.Context, repoKeys []RepoKey, m interface{}) error { tflog.Debug(ctx, fmt.Sprintf("deleteRepos: %s", repoKeys)) req := m.(util.ProvderMetadata).Client.R(). @@ -148,7 +148,7 @@ var deleteRepos = func(ctx context.Context, projectKey string, repoKeys []RepoKe AddRetryCondition(retryOnSpecificMsgBody("Web server is returning an unknown error")) for _, repoKey := range repoKeys { - err := deleteRepo(ctx, projectKey, repoKey, req) + err := deleteRepo(ctx, repoKey, req) if err != nil { return fmt.Errorf("failed to delete repo %s: %s", repoKey, err) } @@ -157,7 +157,7 @@ var deleteRepos = func(ctx context.Context, projectKey string, repoKeys []RepoKe return nil } -var deleteRepo = func(ctx context.Context, projectKey string, repoKey RepoKey, req *resty.Request) error { +var deleteRepo = func(ctx context.Context, repoKey RepoKey, req *resty.Request) error { tflog.Debug(ctx, fmt.Sprintf("deleteRepo: %s", repoKey)) type Error struct { diff --git a/pkg/project/resource_project.go b/pkg/project/resource_project.go index d39a1175..d697a36d 100644 --- a/pkg/project/resource_project.go +++ b/pkg/project/resource_project.go @@ -266,8 +266,8 @@ func projectResource() *schema.Resource { "use_project_role_resource": { Type: schema.TypeBool, Optional: true, - Default: false, - Description: "When set to true, this resource will ignore the `roles` attributes and allow roles to be managed by `project_role` resource instead. Default to false.", + Default: true, + Description: "When set to true, this resource will ignore the `roles` attributes and allow roles to be managed by `project_role` resource instead. Default to `true`.", }, }, ) @@ -297,6 +297,12 @@ func projectResource() *schema.Resource { Description: "Member of the project. Element has one to one mapping with the [JFrog Project Users API](https://www.jfrog.com/confluence/display/JFROG/Artifactory+REST+API#ArtifactoryRESTAPI-UpdateUserinProject).", Deprecated: "Replaced by `project_user` resource. This should not be used in combination with `project_user` resource. Use `use_project_user_resource` attribute to control which resource manages project roles.", }, + "use_project_user_resource": { + Type: schema.TypeBool, + Optional: true, + Default: true, + Description: "When set to true, this resource will ignore the `member` attributes and allow users to be managed by `project_user` resource instead. Default to `true`.", + }, "group": { Type: schema.TypeSet, Optional: true, @@ -319,17 +325,11 @@ func projectResource() *schema.Resource { Description: "Project group. Element has one to one mapping with the [JFrog Project Groups API](https://www.jfrog.com/confluence/display/JFROG/Artifactory+REST+API#ArtifactoryRESTAPI-UpdateGroupinProject)", Deprecated: "Replaced by `project_group` resource. This should not be used in combination with `project_group` resource. Use `use_project_group_resource` attribute to control which resource manages project roles.", }, - "use_project_user_resource": { - Type: schema.TypeBool, - Optional: true, - Default: false, - Description: "When set to true, this resource will ignore the `member` attributes and allow users to be managed by `project_user` resource instead. Default to false.", - }, "use_project_group_resource": { Type: schema.TypeBool, Optional: true, - Default: false, - Description: "When set to true, this resource will ignore the `group` attributes and allow users to be managed by `project_group` resource instead. Default to false.", + Default: true, + Description: "When set to true, this resource will ignore the `group` attributes and allow users to be managed by `project_group` resource instead. Default to `true`.", }, }, ) @@ -466,7 +466,9 @@ func projectResource() *schema.Resource { return diag.FromErr(err) } - _, err = m.(util.ProvderMetadata).Client.R().SetBody(project).Post(projectsUrl) + _, err = m.(util.ProvderMetadata).Client.R(). + SetBody(project). + Post(projectsUrl) if err != nil { return diag.FromErr(err) } @@ -534,7 +536,7 @@ func projectResource() *schema.Resource { } } - useProjectUserResource := data.Get("use_project_role_resource").(bool) + useProjectUserResource := data.Get("use_project_user_resource").(bool) if !useProjectUserResource { _, err = updateMembers(ctx, data.Id(), usersMembershipType, users, m) if err != nil { @@ -567,7 +569,7 @@ func projectResource() *schema.Resource { return diag.FromErr(err) } - deleteErr := deleteRepos(ctx, data.Id(), repos, m) + deleteErr := deleteRepos(ctx, repos, m) if deleteErr != nil { return diag.FromErr(fmt.Errorf("failed to delete repos for project: %s", deleteErr)) } @@ -607,16 +609,16 @@ func projectResource() *schema.Resource { } var resourceStateUpgradeV1 = func(ctx context.Context, rawState map[string]any, meta any) (map[string]any, error) { - // set use_project_role_resource to true for existing state so the resource will continue - // using `roles` attribute until explicitly set to false - rawState["use_project_role_resource"] = true + // set use_project_role_resource to false for existing state so the resource will continue + // using `roles` attribute until explicitly set to true + rawState["use_project_role_resource"] = false return rawState, nil } var resourceStateUpgradeV2 = func(ctx context.Context, rawState map[string]any, meta any) (map[string]any, error) { // like in v1 where the project_role was introduced, just for project_user and project_group - rawState["use_project_user_resource"] = true - rawState["use_project_group_resource"] = true + rawState["use_project_user_resource"] = false + rawState["use_project_group_resource"] = false return rawState, nil } diff --git a/pkg/project/resource_project_group.go b/pkg/project/resource_project_group.go index 0225577c..3cd11277 100644 --- a/pkg/project/resource_project_group.go +++ b/pkg/project/resource_project_group.go @@ -14,6 +14,16 @@ import ( const projectGroupsUrl = "access/api/v1/projects/{projectKey}/groups/{name}" +type ProjectGroup struct { + ProjectKey string `json:"-"` + Name string `json:"name"` + Roles []string `json:"roles"` +} + +func (m ProjectGroup) Id() string { + return fmt.Sprintf(`%s:%s`, m.ProjectKey, m.Name) +} + func projectGroupResource() *schema.Resource { var projectGroupSchema = map[string]*schema.Schema{ "project_key": { @@ -26,6 +36,7 @@ func projectGroupResource() *schema.Resource { "name": { Type: schema.TypeString, Required: true, + ForceNew: true, ValidateDiagFunc: validation.ToDiagFunc(validation.StringIsNotEmpty), Description: "The name of an artifactory group.", }, @@ -37,6 +48,28 @@ func projectGroupResource() *schema.Resource { }, } + var unpackProjectGroup = func(d *schema.ResourceData) ProjectGroup { + return ProjectGroup{ + ProjectKey: d.Get("project_key").(string), + Name: d.Get("name").(string), + Roles: util.CastToStringArr(d.Get("roles").(*schema.Set).List()), + } + } + + var packProjectGroup = func(_ context.Context, data *schema.ResourceData, m ProjectGroup) diag.Diagnostics { + setValue := util.MkLens(data) + + setValue("name", m.Name) + setValue("project_key", m.ProjectKey) + errors := setValue("roles", m.Roles) + + if len(errors) > 0 { + return diag.Errorf("failed to pack project member %q", errors) + } + + return nil + } + var readProjectGroup = func(ctx context.Context, data *schema.ResourceData, m interface{}) diag.Diagnostics { projectGroup := unpackProjectGroup(data) var loadedProjectGroup ProjectGroup diff --git a/pkg/project/resource_project_group_test.go b/pkg/project/resource_project_group_test.go index 54b5370e..36f355aa 100644 --- a/pkg/project/resource_project_group_test.go +++ b/pkg/project/resource_project_group_test.go @@ -43,9 +43,7 @@ func TestAccProjectGroup(t *testing.T) { block_deployments_on_limit = true email_notification = false - lifecycle { - ignore_changes = ["member"] - } + use_project_group_resource = true } resource "project_group" "{{ .group }}" { @@ -72,6 +70,12 @@ func TestAccProjectGroup(t *testing.T) { return verifyProjectUser(group, projectKey, request) }), ProviderFactories: testAccProviders(), + ExternalProviders: map[string]resource.ExternalProvider{ + "artifactory": { + Source: "jfrog/artifactory", + VersionConstraint: "10.1.4", + }, + }, Steps: []resource.TestStep{ { Config: config, diff --git a/pkg/project/resource_project_role.go b/pkg/project/resource_project_role.go index b88640d5..892c939c 100644 --- a/pkg/project/resource_project_role.go +++ b/pkg/project/resource_project_role.go @@ -111,7 +111,7 @@ func projectRoleResource() *schema.Resource { }, } - var packRole = func(ctx context.Context, data *schema.ResourceData, role Role, projectKey string) diag.Diagnostics { + var packRole = func(_ context.Context, data *schema.ResourceData, role Role, projectKey string) diag.Diagnostics { setValue := util.MkLens(data) setValue("name", role.Name) diff --git a/pkg/project/resource_project_role_test.go b/pkg/project/resource_project_role_test.go index d4135f95..193303ce 100644 --- a/pkg/project/resource_project_role_test.go +++ b/pkg/project/resource_project_role_test.go @@ -24,7 +24,6 @@ func TestAccProjectRole_full(t *testing.T) { manage_resources = true index_resources = true } - use_project_role_resource = true } resource "project_role" "{{ .name }}" { @@ -107,6 +106,8 @@ func TestAccProjectRole_conflict_with_project(t *testing.T) { manage_resources = true index_resources = true } + + use_project_role_resource = false } resource "project_role" "{{ .name }}" { diff --git a/pkg/project/resource_project_test.go b/pkg/project/resource_project_test.go index 310c5a25..55f319fe 100644 --- a/pkg/project/resource_project_test.go +++ b/pkg/project/resource_project_test.go @@ -331,6 +331,10 @@ func TestAccProject_full(t *testing.T) { block_deployments_on_limit = {{ .block_deployments_on_limit }} email_notification = {{ .email_notification }} + use_project_group_resource = false + use_project_user_resource = false + use_project_role_resource = false + member { name = artifactory_managed_user.{{ .username1 }}.name roles = ["Developer","Project Admin"] @@ -419,6 +423,8 @@ func TestAccProject_full(t *testing.T) { resource.TestCheckResourceAttr(resourceName, "admin_privileges.0.manage_members", fmt.Sprintf("%t", params["manage_members"])), resource.TestCheckResourceAttr(resourceName, "admin_privileges.0.manage_resources", fmt.Sprintf("%t", params["manage_resources"])), resource.TestCheckResourceAttr(resourceName, "admin_privileges.0.index_resources", fmt.Sprintf("%t", params["index_resources"])), + resource.TestCheckResourceAttr(resourceName, "use_project_user_resource", "false"), + resource.TestCheckResourceAttr(resourceName, "use_project_group_resource", "false"), resource.TestCheckResourceAttr(resourceName, "use_project_role_resource", "false"), resource.TestCheckResourceAttr(resourceName, "member.#", "2"), resource.TestCheckResourceAttr(resourceName, "member.0.name", username1), @@ -525,7 +531,6 @@ func TestAccProject_migrate_schema(t *testing.T) { max_storage_in_gibibytes = {{ .max_storage_in_gibibytes }} block_deployments_on_limit = {{ .block_deployments_on_limit }} email_notification = {{ .email_notification }} - use_project_role_resource = true } ` diff --git a/pkg/project/resource_project_user.go b/pkg/project/resource_project_user.go index 833af928..76c70550 100644 --- a/pkg/project/resource_project_user.go +++ b/pkg/project/resource_project_user.go @@ -15,6 +15,17 @@ import ( const projectUsersUrl = "access/api/v1/projects/{projectKey}/users/{name}" +type ProjectUser struct { + ProjectKey string `json:"-"` + Name string `json:"name"` + Roles []string `json:"roles"` + IgnoreMissingUser bool `json:"-"` +} + +func (m ProjectUser) Id() string { + return fmt.Sprintf(`%s:%s`, m.ProjectKey, m.Name) +} + func projectUserResource() *schema.Resource { var projectUserSchema = map[string]*schema.Schema{ "project_key": { @@ -27,6 +38,7 @@ func projectUserResource() *schema.Resource { "name": { Type: schema.TypeString, Required: true, + ForceNew: true, ValidateDiagFunc: validation.ToDiagFunc(validation.StringIsNotEmpty), Description: "The name of an artifactory user.", }, @@ -40,10 +52,34 @@ func projectUserResource() *schema.Resource { Type: schema.TypeBool, Optional: true, Default: false, - Description: "When set to true, the resource will not fail if the user does not exist. Default to false. This is useful when the user is externally managed and the local account wasn't created yet.", + Description: "When set to `true`, the resource will not fail if the user does not exist. Default to `false`. This is useful when the user is externally managed and the local account wasn't created yet.", }, } + var packProjectUser = func(_ context.Context, data *schema.ResourceData, m ProjectUser) diag.Diagnostics { + setValue := util.MkLens(data) + + setValue("name", m.Name) + setValue("project_key", m.ProjectKey) + setValue("roles", m.Roles) + errors := setValue("ignore_missing_user", m.IgnoreMissingUser) + + if len(errors) > 0 { + return diag.Errorf("failed to pack project member %q", errors) + } + + return nil + } + + var unpackProjectUser = func(d *schema.ResourceData) ProjectUser { + return ProjectUser{ + ProjectKey: d.Get("project_key").(string), + Name: d.Get("name").(string), + Roles: util.CastToStringArr(d.Get("roles").(*schema.Set).List()), + IgnoreMissingUser: d.Get("ignore_missing_user").(bool), + } + } + var readProjectUser = func(ctx context.Context, data *schema.ResourceData, m interface{}) diag.Diagnostics { projectUser := unpackProjectUser(data) var loadedProjectUser ProjectUser diff --git a/pkg/project/resource_project_user_test.go b/pkg/project/resource_project_user_test.go index 9391a3c4..9abd65c4 100644 --- a/pkg/project/resource_project_user_test.go +++ b/pkg/project/resource_project_user_test.go @@ -49,9 +49,7 @@ func TestAccProjectUser(t *testing.T) { block_deployments_on_limit = true email_notification = false - lifecycle { - ignore_changes = ["member"] - } + use_project_user_resource = true } resource "project_user" "{{ .username }}" { @@ -79,6 +77,12 @@ func TestAccProjectUser(t *testing.T) { return verifyProjectUser(username, projectKey, request) }), ProviderFactories: testAccProviders(), + ExternalProviders: map[string]resource.ExternalProvider{ + "artifactory": { + Source: "jfrog/artifactory", + VersionConstraint: "10.1.4", + }, + }, Steps: []resource.TestStep{ { Config: config, @@ -117,8 +121,6 @@ func TestAccProjectUser_missing_user_fails(t *testing.T) { username := fmt.Sprintf("not_existing%s", strings.ToLower(randSeq(5))) email := username + "@tempurl.org" - resourceName := "project_user." + username - params := map[string]interface{}{ "project_name": projectName, "project_key": projectKey, @@ -141,9 +143,7 @@ func TestAccProjectUser_missing_user_fails(t *testing.T) { block_deployments_on_limit = true email_notification = false - lifecycle { - ignore_changes = ["member"] - } + use_project_user_resource = true } resource "project_user" "{{ .username }}" { @@ -156,10 +156,7 @@ func TestAccProjectUser_missing_user_fails(t *testing.T) { config := test.ExecuteTemplate("TestAccProjectUser", template, params) resource.Test(t, resource.TestCase{ - PreCheck: func() { testAccPreCheck(t) }, - CheckDestroy: verifyDeleted(resourceName, func(id string, request *resty.Request) (*resty.Response, error) { - return verifyProjectUser(username, projectKey, request) - }), + PreCheck: func() { testAccPreCheck(t) }, ProviderFactories: testAccProviders(), Steps: []resource.TestStep{ { @@ -201,9 +198,7 @@ func TestAccProjectMember_missing_user_ignored(t *testing.T) { block_deployments_on_limit = true email_notification = false - lifecycle { - ignore_changes = ["member"] - } + use_project_user_resource = true } resource "project_user" "{{ .username }}" { diff --git a/pkg/project/role_test.go b/pkg/project/role_test.go index 76260161..ed398598 100644 --- a/pkg/project/role_test.go +++ b/pkg/project/role_test.go @@ -37,6 +37,8 @@ func TestAccProject_role(t *testing.T) { index_resources = true } + use_project_role_resource = false + role { name = "{{ .role1 }}" description = "test description" @@ -66,6 +68,8 @@ func TestAccProject_role(t *testing.T) { index_resources = true } + use_project_role_resource = false + role { name = "{{ .role1 }}" description = "test description" @@ -102,6 +106,8 @@ func TestAccProject_role(t *testing.T) { manage_resources = true index_resources = true } + + use_project_role_resource = false } `, params)