Skip to content

Commit 804fb69

Browse files
authored
added private repositories argocd_repository acceptance tests, fixed sensitive repository data permadiffs, removed 1.4.x support (#24)
* added private repositories acceptance tests * repository: add ForceNew flag to repo attribute * fix sensitive data (passwords, keys) not being returned by ArgoCD API * removed 1.4.x support
1 parent b25af60 commit 804fb69

18 files changed

+315
-80
lines changed

.github/workflows/tests.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ jobs:
1414
strategy:
1515
fail-fast: false
1616
matrix:
17-
argocd_version: ["v1.6.1", "v1.5.8", "v1.4.3"]
17+
argocd_version: ["v1.6.2", "v1.5.8"]
1818
steps:
1919
- uses: actions/checkout@v2
2020
- uses: actions/setup-go@v1

README.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,14 @@
44

55
---
66

7+
## Compatibility promise
8+
9+
This provider is compatible with _at least_ the last 2 major releases of ArgoCD (e.g, ranging from 1.(n).m, to 1.(n-1).0, where `n` is the latest available major version).
10+
11+
Older releases are not supported and some resources may not work as expected.
12+
13+
---
14+
715
## Requirements
816

917
- [Terraform](https://www.terraform.io/downloads.html) 0.12.24+

argocd/features_test.go

Lines changed: 14 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import (
44
"fmt"
55
"github.com/Masterminds/semver"
66
"github.com/argoproj/argo-cd/pkg/apiclient/version"
7+
"github.com/stretchr/testify/assert"
78
"math/rand"
89
"testing"
910
)
@@ -14,39 +15,34 @@ const (
1415
semverLess
1516
)
1617

17-
func serverInterfaceTestData(argocdVersion string, semverOperator int) ServerInterface {
18-
18+
func serverInterfaceTestData(t *testing.T, argocdVersion string, semverOperator int) ServerInterface {
1919
v, err := semver.NewVersion(argocdVersion)
20-
if err != nil {
21-
panic(err)
22-
}
20+
assert.NoError(t, err)
21+
2322
incPatch := rand.Int63n(100)
2423
incMinor := rand.Int63n(100)
2524
incMajor := rand.Int63n(100)
2625

2726
switch semverOperator {
2827
case semverEquals:
2928
case semverGreater:
30-
if v, err = semver.NewVersion(
29+
v, err = semver.NewVersion(
3130
fmt.Sprintf("%d.%d.%d",
3231
v.Major()+incMajor,
3332
v.Minor()+incMinor,
3433
v.Patch()+incPatch,
35-
)); err != nil {
36-
panic(err)
37-
}
38-
34+
))
35+
assert.NoError(t, err)
3936
case semverLess:
40-
if v, err = semver.NewVersion(
37+
v, err = semver.NewVersion(
4138
fmt.Sprintf("%d.%d.%d",
4239
v.Major()-incMajor%v.Major(),
4340
v.Minor()-incMinor%v.Minor(),
4441
v.Patch()-incPatch%v.Patch(),
45-
)); err != nil {
46-
panic(err)
47-
}
42+
))
43+
assert.NoError(t, err)
4844
default:
49-
panic("unsupported semver test semverOperator")
45+
t.Error("unsupported semver test semverOperator")
5046
}
5147

5248
vm := &version.VersionMessage{
@@ -72,21 +68,21 @@ func TestServerInterface_isFeatureSupported(t *testing.T) {
7268
}{
7369
{
7470
name: "featureTokenID-1.5.3",
75-
fields: serverInterfaceTestData("1.5.3", semverEquals),
71+
fields: serverInterfaceTestData(t, "1.5.3", semverEquals),
7672
args: args{feature: featureTokenIDs},
7773
want: true,
7874
wantErr: false,
7975
},
8076
{
8177
name: "featureTokenID-1.5.3+",
82-
fields: serverInterfaceTestData("1.5.3", semverGreater),
78+
fields: serverInterfaceTestData(t, "1.5.3", semverGreater),
8379
args: args{feature: featureTokenIDs},
8480
want: true,
8581
wantErr: false,
8682
},
8783
{
8884
name: "featureTokenID-1.5.3-",
89-
fields: serverInterfaceTestData("1.5.3", semverLess),
85+
fields: serverInterfaceTestData(t, "1.5.3", semverLess),
9086
args: args{feature: featureTokenIDs},
9187
want: false,
9288
wantErr: false,

argocd/resource_argocd_project_token_test.go

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import (
44
"fmt"
55
"github.com/hashicorp/terraform-plugin-sdk/helper/resource"
66
"github.com/hashicorp/terraform-plugin-sdk/terraform"
7+
"github.com/stretchr/testify/assert"
78
"math"
89
"math/rand"
910
"regexp"
@@ -14,9 +15,7 @@ import (
1415
func TestAccArgoCDProjectToken(t *testing.T) {
1516
expiresInDurationFunc := func(i int) time.Duration {
1617
d, err := time.ParseDuration(fmt.Sprintf("%ds", i))
17-
if err != nil {
18-
panic(err)
19-
}
18+
assert.NoError(t, err)
2019
return d
2120
}
2221
count := 3 + rand.Intn(7)

argocd/resource_argocd_repository.go

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,9 @@ func resourceArgoCDRepositoryCreate(d *schema.ResourceData, meta interface{}) er
3838
if err != nil {
3939
return err
4040
}
41+
if r == nil {
42+
return fmt.Errorf("ArgoCD did not return an error or a repository result")
43+
}
4144
if r.ConnectionState.Status == application.ConnectionStatusFailed {
4245
return fmt.Errorf(
4346
"could not connect to repository %s: %s",
@@ -56,7 +59,7 @@ func resourceArgoCDRepositoryRead(d *schema.ResourceData, meta interface{}) erro
5659

5760
featureRepositoryGetSupported, err := server.isFeatureSupported(featureRepositoryGet)
5861
if err != nil {
59-
panic(err)
62+
return err
6063
}
6164

6265
switch featureRepositoryGetSupported {
@@ -100,7 +103,6 @@ func resourceArgoCDRepositoryRead(d *schema.ResourceData, meta interface{}) erro
100103
return nil
101104
}
102105
}
103-
104106
}
105107
return flattenRepository(r, d)
106108
}
@@ -123,6 +125,9 @@ func resourceArgoCDRepositoryUpdate(d *schema.ResourceData, meta interface{}) er
123125
return err
124126
}
125127
}
128+
if r == nil {
129+
return fmt.Errorf("ArgoCD did not return an error or a repository result")
130+
}
126131
if r.ConnectionState.Status == application.ConnectionStatusFailed {
127132
return fmt.Errorf(
128133
"could not connect to repository %s: %s",

argocd/resource_argocd_repository_credentials_test.go

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -6,20 +6,17 @@ import (
66
"crypto/x509"
77
"encoding/pem"
88
"fmt"
9-
"github.com/hashicorp/terraform-plugin-sdk/helper/acctest"
109
"github.com/hashicorp/terraform-plugin-sdk/helper/resource"
10+
"github.com/stretchr/testify/assert"
1111
"testing"
1212
)
1313

1414
func TestAccArgoCDRepositoryCredentials(t *testing.T) {
15-
repoUrl := fmt.Sprintf("https://git.local/%s/%s",
16-
acctest.RandString(10),
17-
acctest.RandString(10))
18-
username := fmt.Sprintf(acctest.RandString(10))
15+
repoUrl := "https://private-git-repository.argocd.svc.clusterlocal/project.git"
16+
username := "git"
1917
sshPrivateKey, err := generateSSHPrivateKey()
20-
if err != nil {
21-
panic(err)
22-
}
18+
assert.NoError(t, err)
19+
2320
resource.ParallelTest(t, resource.TestCase{
2421
PreCheck: func() { testAccPreCheck(t) },
2522
Providers: testAccProviders,
@@ -65,3 +62,9 @@ func generateSSHPrivateKey() (privateKey string, err error) {
6562
}
6663
return string(pem.EncodeToMemory(&privBlock)), nil
6764
}
65+
66+
func mustGenerateSSHPrivateKey(t *testing.T) string {
67+
pk, err := generateSSHPrivateKey()
68+
assert.NoError(t, err)
69+
return pk
70+
}

argocd/resource_argocd_repository_test.go

Lines changed: 69 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -7,27 +7,54 @@ import (
77
)
88

99
func TestAccArgoCDRepository(t *testing.T) {
10+
repoUrl := "[email protected]:project.git"
11+
1012
resource.ParallelTest(t, resource.TestCase{
1113
PreCheck: func() { testAccPreCheck(t) },
1214
Providers: testAccProviders,
1315
Steps: []resource.TestStep{
16+
//{
17+
// Config: testAccArgoCDRepositorySimple(),
18+
// Check: resource.ComposeTestCheckFunc(
19+
// resource.TestCheckResourceAttr(
20+
// "argocd_repository.simple",
21+
// "connection_state_status",
22+
// "Successful",
23+
// ),
24+
// ),
25+
//},
26+
//{
27+
// Config: testAccArgoCDRepositoryHelm(),
28+
// Check: resource.ComposeTestCheckFunc(
29+
// resource.TestCheckResourceAttr(
30+
// "argocd_repository.helm",
31+
// "connection_state_status",
32+
// "Successful",
33+
// ),
34+
// ),
35+
//},
36+
//{
37+
// Config: testAccArgoCDRepositoryPublicUsageInApplication(acctest.RandString(10)),
38+
// Check: resource.ComposeTestCheckFunc(
39+
// resource.TestCheckResourceAttrSet(
40+
// "argocd_application.public",
41+
// "metadata.0.uid",
42+
// ),
43+
// ),
44+
//},
1445
{
15-
Config: testAccArgoCDRepositorySimple(),
46+
Config: testAccArgoCDRepositoryPrivateGitSSH(repoUrl),
47+
//ExpectNonEmptyPlan: true,
1648
Check: resource.ComposeTestCheckFunc(
1749
resource.TestCheckResourceAttr(
18-
"argocd_repository.simple",
50+
"argocd_repository.private",
1951
"connection_state_status",
2052
"Successful",
2153
),
22-
),
23-
},
24-
{
25-
Config: testAccArgoCDRepositoryHelm(),
26-
Check: resource.ComposeTestCheckFunc(
2754
resource.TestCheckResourceAttr(
28-
"argocd_repository.helm",
29-
"connection_state_status",
30-
"Successful",
55+
"argocd_repository.private",
56+
"inherited_creds",
57+
"false",
3158
),
3259
),
3360
},
@@ -52,3 +79,35 @@ resource "argocd_repository" "helm" {
5279
}
5380
`)
5481
}
82+
83+
func testAccArgoCDRepositoryPublicUsageInApplication(name string) string {
84+
return testAccArgoCDRepositorySimple() + fmt.Sprintf(`
85+
resource "argocd_application" "public" {
86+
metadata {
87+
name = "%s"
88+
namespace = "argocd"
89+
}
90+
spec {
91+
source {
92+
repo_url = argocd_repository.simple.repo
93+
path = "examples/helloWorld"
94+
}
95+
destination {
96+
server = "https://kubernetes.default.svc"
97+
namespace = "default"
98+
}
99+
}
100+
}
101+
`, name)
102+
}
103+
104+
func testAccArgoCDRepositoryPrivateGitSSH(repoUrl string) string {
105+
return fmt.Sprintf(`
106+
resource "argocd_repository" "private" {
107+
repo = "%s"
108+
type = "git"
109+
insecure = true
110+
ssh_private_key = "-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAAAMwAAAAtzc2gtZW\nQyNTUxOQAAACCGe6Vx0gbKqKCI0wIplfgK5JBjCDO3bhtU3sZfLoeUZgAAAJB9cNEifXDR\nIgAAAAtzc2gtZWQyNTUxOQAAACCGe6Vx0gbKqKCI0wIplfgK5JBjCDO3bhtU3sZfLoeUZg\nAAAEAJeUrObjoTbGO1Sq4TXHl/j4RJ5aKMC1OemWuHmLK7XYZ7pXHSBsqooIjTAimV+Ark\nkGMIM7duG1Texl8uh5RmAAAAC3Rlc3RAYXJnb2NkAQI=\n-----END OPENSSH PRIVATE KEY-----"
111+
}
112+
`, repoUrl)
113+
}

argocd/schema_repository.go

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ func repositorySchema() map[string]*schema.Schema {
1010
"repo": {
1111
Type: schema.TypeString,
1212
Description: "URL of the repo",
13+
ForceNew: true,
1314
Required: true,
1415
},
1516
"enable_lfs": {
@@ -20,7 +21,7 @@ func repositorySchema() map[string]*schema.Schema {
2021
"inherited_creds": {
2122
Type: schema.TypeBool,
2223
Description: "Whether credentials were inherited from a credential set",
23-
Optional: true,
24+
Computed: true,
2425
},
2526
"insecure": {
2627
Type: schema.TypeBool,
@@ -44,11 +45,11 @@ func repositorySchema() map[string]*schema.Schema {
4445
Optional: true,
4546
},
4647
"ssh_private_key": {
47-
Type: schema.TypeString,
48-
Sensitive: true,
49-
Description: "SSH private key data for authenticating at the repo server only for Git repos",
50-
// TODO: add a validator
51-
Optional: true,
48+
Type: schema.TypeString,
49+
Sensitive: false,
50+
Description: "SSH private key data for authenticating at the repo server only for Git repos",
51+
ValidateFunc: validateSSHPrivateKey,
52+
Optional: true,
5253
},
5354
"tls_client_cert_data": {
5455
Type: schema.TypeString,

argocd/schema_repository_credentials.go

Lines changed: 6 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -19,21 +19,15 @@ func repositoryCredentialsSchema() map[string]*schema.Schema {
1919
"password": {
2020
Type: schema.TypeString,
2121
Sensitive: true,
22-
Description: "Password for authenticating at the repo server, cannot be managed once created!",
22+
Description: "Password for authenticating at the repo server",
2323
Optional: true,
24-
DiffSuppressFunc: func(k, old, new string, d *schema.ResourceData) bool {
25-
return true
26-
},
2724
},
2825
"ssh_private_key": {
29-
Type: schema.TypeString,
30-
Sensitive: true,
31-
Description: "SSH private key data for authenticating at the repo server only for Git repos, cannot be managed once created!",
32-
// TODO: add a validator
33-
Optional: true,
34-
DiffSuppressFunc: func(k, old, new string, d *schema.ResourceData) bool {
35-
return true
36-
},
26+
Type: schema.TypeString,
27+
Sensitive: true,
28+
Description: "SSH private key data for authenticating at the repo server only for Git repos",
29+
ValidateFunc: validateSSHPrivateKey,
30+
Optional: true,
3731
},
3832
"tls_client_cert_data": {
3933
Type: schema.TypeString,

argocd/structure_repository.go

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -31,9 +31,7 @@ func expandRepository(d *schema.ResourceData) *application.Repository {
3131
if v, ok := d.GetOk("password"); ok {
3232
repository.Password = v.(string)
3333
}
34-
if v, ok := d.GetOk("ssh_private_key"); ok {
35-
repository.SSHPrivateKey = v.(string)
36-
}
34+
repository.SSHPrivateKey = d.Get("ssh_private_key").(string)
3735
if v, ok := d.GetOk("tls_client_cert_data"); ok {
3836
repository.TLSClientCertData = v.(string)
3937
}
@@ -57,11 +55,12 @@ func flattenRepository(repository *application.Repository, d *schema.ResourceDat
5755
"insecure": repository.Insecure,
5856
"name": repository.Name,
5957
"username": repository.Username,
60-
"password": repository.Password,
61-
"ssh_private_key": repository.SSHPrivateKey,
62-
"tls_client_cert_data": repository.TLSClientCertData,
63-
"tls_client_cert_key": repository.TLSClientCertKey,
64-
"type": repository.Type,
58+
// TODO: ArgoCD API does not return sensitive data!
59+
//"password": repository.Password,
60+
//"ssh_private_key": repository.SSHPrivateKey,
61+
//"tls_client_cert_key": repository.TLSClientCertKey,
62+
"tls_client_cert_data": repository.TLSClientCertData,
63+
"type": repository.Type,
6564
}
6665
for k, v := range r {
6766
if err := persistToState(k, v, d); err != nil {

0 commit comments

Comments
 (0)