github.com/argoproj/argo-cd/v3@v3.2.1/test/e2e/cluster_test.go (about)

     1  package e2e
     2  
     3  import (
     4  	"fmt"
     5  	"net/url"
     6  	"testing"
     7  	"time"
     8  
     9  	"github.com/stretchr/testify/assert"
    10  	"github.com/stretchr/testify/require"
    11  
    12  	. "github.com/argoproj/argo-cd/v3/pkg/apis/application/v1alpha1"
    13  	"github.com/argoproj/argo-cd/v3/test/e2e/fixture"
    14  	accountFixture "github.com/argoproj/argo-cd/v3/test/e2e/fixture/account"
    15  	"github.com/argoproj/argo-cd/v3/test/e2e/fixture/app"
    16  	clusterFixture "github.com/argoproj/argo-cd/v3/test/e2e/fixture/cluster"
    17  	"github.com/argoproj/argo-cd/v3/util/errors"
    18  )
    19  
    20  func TestClusterList(t *testing.T) {
    21  	fixture.SkipIfAlreadyRun(t)
    22  	defer fixture.RecordTestRun(t)
    23  
    24  	last := ""
    25  	expected := fmt.Sprintf(`SERVER                          NAME        VERSION  STATUS      MESSAGE  PROJECT
    26  https://kubernetes.default.svc  in-cluster  %v     Successful           `, fixture.GetVersions(t).ServerVersion)
    27  
    28  	clusterFixture.
    29  		Given(t).
    30  		Project(fixture.ProjectName)
    31  
    32  	// We need an application targeting the cluster, otherwise the test will
    33  	// fail if run isolated.
    34  	app.GivenWithSameState(t).
    35  		Path(guestbookPath).
    36  		When().
    37  		CreateApp()
    38  
    39  	tries := 25
    40  	for i := 0; i <= tries; i++ {
    41  		clusterFixture.GivenWithSameState(t).
    42  			When().
    43  			List().
    44  			Then().
    45  			AndCLIOutput(func(output string, _ error) {
    46  				last = output
    47  			})
    48  		if expected == last {
    49  			break
    50  		} else if i < tries {
    51  			// We retry with a simple backoff
    52  			time.Sleep(time.Duration(i+1) * 100 * time.Millisecond)
    53  		}
    54  	}
    55  	assert.Equal(t, expected, last)
    56  }
    57  
    58  func TestClusterAdd(t *testing.T) {
    59  	clusterFixture.
    60  		Given(t).
    61  		Project(fixture.ProjectName).
    62  		Upsert(true).
    63  		Server(KubernetesInternalAPIServerAddr).
    64  		When().
    65  		Create().
    66  		List().
    67  		Then().
    68  		AndCLIOutput(func(output string, _ error) {
    69  			assert.Equal(t, fmt.Sprintf(`SERVER                          NAME              VERSION  STATUS      MESSAGE  PROJECT
    70  https://kubernetes.default.svc  test-cluster-add  %v     Successful           %s`, fixture.GetVersions(t).ServerVersion, fixture.ProjectName), output)
    71  		})
    72  }
    73  
    74  func TestClusterAddPermissionDenied(t *testing.T) {
    75  	accountFixture.Given(t).
    76  		Name("test").
    77  		When().
    78  		Create().
    79  		Login().
    80  		SetPermissions([]fixture.ACL{}, "org-admin")
    81  
    82  	clusterFixture.
    83  		GivenWithSameState(t).
    84  		Project(fixture.ProjectName).
    85  		Upsert(true).
    86  		Server(KubernetesInternalAPIServerAddr).
    87  		When().
    88  		IgnoreErrors().
    89  		Create().
    90  		Then().
    91  		AndCLIOutput(func(_ string, err error) {
    92  			assert.ErrorContains(t, err, "PermissionDenied desc = permission denied")
    93  		})
    94  }
    95  
    96  func TestClusterAddAllowed(t *testing.T) {
    97  	accountFixture.Given(t).
    98  		Name("test").
    99  		When().
   100  		Create().
   101  		Login().
   102  		SetPermissions([]fixture.ACL{
   103  			{
   104  				Resource: "clusters",
   105  				Action:   "create",
   106  				Scope:    fixture.ProjectName + "/*",
   107  			},
   108  			{
   109  				Resource: "clusters",
   110  				Action:   "get",
   111  				Scope:    fixture.ProjectName + "/*",
   112  			},
   113  		}, "org-admin")
   114  
   115  	clusterFixture.
   116  		GivenWithSameState(t).
   117  		Project(fixture.ProjectName).
   118  		Upsert(true).
   119  		Server(KubernetesInternalAPIServerAddr).
   120  		When().
   121  		Create().
   122  		List().
   123  		Then().
   124  		AndCLIOutput(func(output string, _ error) {
   125  			assert.Equal(t, fmt.Sprintf(`SERVER                          NAME                      VERSION  STATUS      MESSAGE  PROJECT
   126  https://kubernetes.default.svc  test-cluster-add-allowed  %v     Successful           argo-project`, fixture.GetVersions(t).ServerVersion), output)
   127  		})
   128  }
   129  
   130  func TestClusterListDenied(t *testing.T) {
   131  	accountFixture.Given(t).
   132  		Name("test").
   133  		When().
   134  		Create().
   135  		Login().
   136  		SetPermissions([]fixture.ACL{
   137  			{
   138  				Resource: "clusters",
   139  				Action:   "create",
   140  				Scope:    fixture.ProjectName + "/*",
   141  			},
   142  		}, "org-admin")
   143  
   144  	clusterFixture.
   145  		GivenWithSameState(t).
   146  		Project(fixture.ProjectName).
   147  		Upsert(true).
   148  		Server(KubernetesInternalAPIServerAddr).
   149  		When().
   150  		Create().
   151  		List().
   152  		Then().
   153  		AndCLIOutput(func(output string, _ error) {
   154  			assert.Equal(t, "SERVER  NAME  VERSION  STATUS  MESSAGE  PROJECT", output)
   155  		})
   156  }
   157  
   158  func TestClusterSet(t *testing.T) {
   159  	fixture.EnsureCleanState(t)
   160  	defer fixture.RecordTestRun(t)
   161  	clusterFixture.
   162  		GivenWithSameState(t).
   163  		Project(fixture.ProjectName).
   164  		Name("in-cluster").
   165  		Namespaces([]string{"namespace-edit-1", "namespace-edit-2"}).
   166  		Server(KubernetesInternalAPIServerAddr).
   167  		When().
   168  		SetNamespaces().
   169  		GetByName("in-cluster").
   170  		Then().
   171  		AndCLIOutput(func(output string, _ error) {
   172  			assert.Contains(t, output, "namespace-edit-1")
   173  			assert.Contains(t, output, "namespace-edit-2")
   174  		})
   175  }
   176  
   177  func TestClusterGet(t *testing.T) {
   178  	fixture.SkipIfAlreadyRun(t)
   179  	fixture.EnsureCleanState(t)
   180  	defer fixture.RecordTestRun(t)
   181  	output := errors.NewHandler(t).FailOnErr(fixture.RunCli("cluster", "get", "https://kubernetes.default.svc")).(string)
   182  
   183  	assert.Contains(t, output, "name: in-cluster")
   184  	assert.Contains(t, output, "server: https://kubernetes.default.svc")
   185  	assert.Contains(t, output, fmt.Sprintf(`serverVersion: "%v"`, fixture.GetVersions(t).ServerVersion))
   186  	assert.Contains(t, output, `config:
   187    tlsClientConfig:
   188      insecure: false`)
   189  
   190  	assert.Contains(t, output, `status: Successful`)
   191  }
   192  
   193  func TestClusterNameInRestAPI(t *testing.T) {
   194  	fixture.EnsureCleanState(t)
   195  
   196  	var cluster Cluster
   197  	err := fixture.DoHttpJsonRequest("GET", "/api/v1/clusters/in-cluster?id.type=name", &cluster)
   198  	require.NoError(t, err)
   199  
   200  	assert.Equal(t, "in-cluster", cluster.Name)
   201  	assert.Contains(t, cluster.Server, "https://kubernetes.default.svc")
   202  
   203  	err = fixture.DoHttpJsonRequest("PUT",
   204  		"/api/v1/clusters/in-cluster?id.type=name&updatedFields=labels", &cluster, []byte(`{"labels":{"test": "val"}}`)...)
   205  	require.NoError(t, err)
   206  	assert.Equal(t, map[string]string{"test": "val"}, cluster.Labels)
   207  }
   208  
   209  func TestClusterURLInRestAPI(t *testing.T) {
   210  	fixture.EnsureCleanState(t)
   211  
   212  	clusterURL := url.QueryEscape(KubernetesInternalAPIServerAddr)
   213  
   214  	var cluster Cluster
   215  	err := fixture.DoHttpJsonRequest("GET", "/api/v1/clusters/"+clusterURL, &cluster)
   216  	require.NoError(t, err)
   217  
   218  	assert.Equal(t, "in-cluster", cluster.Name)
   219  	assert.Contains(t, cluster.Server, "https://kubernetes.default.svc")
   220  
   221  	err = fixture.DoHttpJsonRequest("PUT",
   222  		fmt.Sprintf("/api/v1/clusters/%s?&updatedFields=labels", clusterURL), &cluster, []byte(`{"labels":{"test": "val"}}`)...)
   223  	require.NoError(t, err)
   224  	assert.Equal(t, map[string]string{"test": "val"}, cluster.Labels)
   225  }
   226  
   227  func TestClusterDeleteDenied(t *testing.T) {
   228  	accountFixture.Given(t).
   229  		Name("test").
   230  		When().
   231  		Create().
   232  		Login().
   233  		SetPermissions([]fixture.ACL{
   234  			{
   235  				Resource: "clusters",
   236  				Action:   "create",
   237  				Scope:    fixture.ProjectName + "/*",
   238  			},
   239  			{
   240  				Resource: "clusters",
   241  				Action:   "get",
   242  				Scope:    fixture.ProjectName + "/*",
   243  			},
   244  		}, "org-admin")
   245  
   246  	// Attempt to remove cluster creds by name
   247  	clusterFixture.
   248  		GivenWithSameState(t).
   249  		Project(fixture.ProjectName).
   250  		Upsert(true).
   251  		Server(KubernetesInternalAPIServerAddr).
   252  		When().
   253  		Create().
   254  		DeleteByName().
   255  		Then().
   256  		AndCLIOutput(func(_ string, err error) {
   257  			assert.ErrorContains(t, err, "PermissionDenied desc = permission denied")
   258  		})
   259  
   260  	// Attempt to remove cluster creds by server
   261  	clusterFixture.
   262  		GivenWithSameState(t).
   263  		Project(fixture.ProjectName).
   264  		Upsert(true).
   265  		Server(KubernetesInternalAPIServerAddr).
   266  		When().
   267  		Create().
   268  		DeleteByServer().
   269  		Then().
   270  		AndCLIOutput(func(_ string, err error) {
   271  			assert.ErrorContains(t, err, "PermissionDenied desc = permission denied")
   272  		})
   273  }
   274  
   275  func TestClusterDelete(t *testing.T) {
   276  	accountFixture.Given(t).
   277  		Name("default").
   278  		When().
   279  		Create().
   280  		Login().
   281  		SetPermissions([]fixture.ACL{
   282  			{
   283  				Resource: "clusters",
   284  				Action:   "create",
   285  				Scope:    fixture.ProjectName + "/*",
   286  			},
   287  			{
   288  				Resource: "clusters",
   289  				Action:   "get",
   290  				Scope:    fixture.ProjectName + "/*",
   291  			},
   292  			{
   293  				Resource: "clusters",
   294  				Action:   "delete",
   295  				Scope:    fixture.ProjectName + "/*",
   296  			},
   297  		}, "org-admin")
   298  
   299  	clstAction := clusterFixture.
   300  		GivenWithSameState(t).
   301  		Name("default").
   302  		Project(fixture.ProjectName).
   303  		Upsert(true).
   304  		Server(KubernetesInternalAPIServerAddr).
   305  		When().
   306  		CreateWithRBAC()
   307  
   308  	// Check that RBAC is created
   309  	_, err := fixture.Run("", "kubectl", "get", "serviceaccount", "argocd-manager", "-n", "kube-system")
   310  	require.NoError(t, err, "Expected no error from not finding serviceaccount argocd-manager")
   311  
   312  	_, err = fixture.Run("", "kubectl", "get", "clusterrole", "argocd-manager-role")
   313  	require.NoError(t, err, "Expected no error from not finding clusterrole argocd-manager-role")
   314  
   315  	_, err = fixture.Run("", "kubectl", "get", "clusterrolebinding", "argocd-manager-role-binding")
   316  	require.NoError(t, err, "Expected no error from not finding clusterrolebinding argocd-manager-role-binding")
   317  
   318  	clstAction.DeleteByName().
   319  		Then().
   320  		AndCLIOutput(func(output string, _ error) {
   321  			assert.Equal(t, "Cluster 'default' removed", output)
   322  		})
   323  
   324  	// Check that RBAC is removed after delete
   325  	output, err := fixture.Run("", "kubectl", "get", "serviceaccount", "argocd-manager", "-n", "kube-system")
   326  	require.Error(t, err, "Expected error from not finding serviceaccount argocd-manager but got:\n%s", output)
   327  
   328  	output, err = fixture.Run("", "kubectl", "get", "clusterrole", "argocd-manager-role")
   329  	require.Error(t, err, "Expected error from not finding clusterrole argocd-manager-role but got:\n%s", output)
   330  
   331  	output, err = fixture.Run("", "kubectl", "get", "clusterrolebinding", "argocd-manager-role-binding")
   332  	assert.Error(t, err, "Expected error from not finding clusterrolebinding argocd-manager-role-binding but got:\n%s", output)
   333  }