github.com/Racer159/jackal@v0.32.7-0.20240401174413-0bd2339e4f2e/src/test/e2e/22_git_and_gitops_test.go (about) 1 // SPDX-License-Identifier: Apache-2.0 2 // SPDX-FileCopyrightText: 2021-Present The Jackal Authors 3 4 // Package test provides e2e tests for Jackal. 5 package test 6 7 import ( 8 "encoding/base64" 9 "encoding/json" 10 "fmt" 11 "net/http" 12 "path/filepath" 13 "testing" 14 15 "github.com/Racer159/jackal/src/internal/packager/git" 16 "github.com/Racer159/jackal/src/pkg/cluster" 17 "github.com/Racer159/jackal/src/types" 18 "github.com/stretchr/testify/require" 19 ) 20 21 func TestGit(t *testing.T) { 22 t.Log("E2E: Git") 23 e2e.SetupWithCluster(t) 24 25 buildPath := filepath.Join("src", "test", "packages", "22-git-data") 26 stdOut, stdErr, err := e2e.Jackal("package", "create", buildPath, "-o=build", "--confirm") 27 require.NoError(t, err, stdOut, stdErr) 28 29 path := fmt.Sprintf("build/jackal-package-git-data-test-%s-1.0.0.tar.zst", e2e.Arch) 30 defer e2e.CleanFiles(path) 31 32 // Deploy the git data example (with component globbing to test that as well) 33 stdOut, stdErr, err = e2e.Jackal("package", "deploy", path, "--components=full-repo,specific-*", "--confirm") 34 require.NoError(t, err, stdOut, stdErr) 35 36 c, err := cluster.NewCluster() 37 require.NoError(t, err) 38 tunnelGit, err := c.Connect(cluster.JackalGit) 39 require.NoError(t, err) 40 defer tunnelGit.Close() 41 42 testGitServerConnect(t, tunnelGit.HTTPEndpoint()) 43 testGitServerReadOnly(t, tunnelGit.HTTPEndpoint()) 44 testGitServerTagAndHash(t, tunnelGit.HTTPEndpoint()) 45 } 46 47 func TestGitOpsFlux(t *testing.T) { 48 t.Log("E2E: GitOps / Flux") 49 e2e.SetupWithCluster(t) 50 51 waitFluxPodInfoDeployment(t) 52 } 53 54 func TestGitOpsArgoCD(t *testing.T) { 55 t.Log("E2E: ArgoCD / Flux") 56 e2e.SetupWithCluster(t) 57 58 waitArgoDeployment(t) 59 } 60 61 func testGitServerConnect(t *testing.T, gitURL string) { 62 // Make sure Gitea comes up cleanly 63 resp, err := http.Get(gitURL + "/explore/repos") 64 require.NoError(t, err) 65 require.Equal(t, 200, resp.StatusCode) 66 } 67 68 func testGitServerReadOnly(t *testing.T, gitURL string) { 69 // Init the state variable 70 state, err := cluster.NewClusterOrDie().LoadJackalState() 71 require.NoError(t, err) 72 73 gitCfg := git.New(state.GitServer) 74 75 // Get the repo as the readonly user 76 repoName := "jackal-public-test-2469062884" 77 getRepoRequest, _ := http.NewRequest("GET", fmt.Sprintf("%s/api/v1/repos/%s/%s", gitURL, state.GitServer.PushUsername, repoName), nil) 78 getRepoResponseBody, _, err := gitCfg.DoHTTPThings(getRepoRequest, types.JackalGitReadUser, state.GitServer.PullPassword) 79 require.NoError(t, err) 80 81 // Make sure the only permissions are pull (read) 82 var bodyMap map[string]interface{} 83 err = json.Unmarshal(getRepoResponseBody, &bodyMap) 84 require.NoError(t, err) 85 permissionsMap := bodyMap["permissions"].(map[string]interface{}) 86 require.False(t, permissionsMap["admin"].(bool)) 87 require.False(t, permissionsMap["push"].(bool)) 88 require.True(t, permissionsMap["pull"].(bool)) 89 } 90 91 func testGitServerTagAndHash(t *testing.T, gitURL string) { 92 // Init the state variable 93 state, err := cluster.NewClusterOrDie().LoadJackalState() 94 require.NoError(t, err, "Failed to load Jackal state") 95 repoName := "jackal-public-test-2469062884" 96 97 gitCfg := git.New(state.GitServer) 98 99 // Get the Jackal repo tag 100 repoTag := "v0.0.1" 101 getRepoTagsRequest, _ := http.NewRequest("GET", fmt.Sprintf("%s/api/v1/repos/%s/%s/tags/%s", gitURL, types.JackalGitPushUser, repoName, repoTag), nil) 102 getRepoTagsResponseBody, _, err := gitCfg.DoHTTPThings(getRepoTagsRequest, types.JackalGitReadUser, state.GitServer.PullPassword) 103 require.NoError(t, err) 104 105 // Make sure the pushed tag exists 106 var tagMap map[string]interface{} 107 err = json.Unmarshal(getRepoTagsResponseBody, &tagMap) 108 require.NoError(t, err) 109 require.Equal(t, repoTag, tagMap["name"]) 110 111 // Get the Jackal repo commit 112 repoHash := "01a23218923f24194133b5eb11268cf8d73ff1bb" 113 getRepoCommitsRequest, _ := http.NewRequest("GET", fmt.Sprintf("%s/api/v1/repos/%s/%s/git/commits/%s", gitURL, types.JackalGitPushUser, repoName, repoHash), nil) 114 getRepoCommitsResponseBody, _, err := gitCfg.DoHTTPThings(getRepoCommitsRequest, types.JackalGitReadUser, state.GitServer.PullPassword) 115 require.NoError(t, err) 116 require.Contains(t, string(getRepoCommitsResponseBody), repoHash) 117 } 118 119 func waitFluxPodInfoDeployment(t *testing.T) { 120 // Deploy the flux example and verify that it works 121 path := fmt.Sprintf("build/jackal-package-podinfo-flux-%s.tar.zst", e2e.Arch) 122 stdOut, stdErr, err := e2e.Jackal("package", "deploy", path, "--confirm") 123 require.NoError(t, err, stdOut, stdErr) 124 125 // Tests the URL mutation for GitRepository CRD for Flux. 126 stdOut, stdErr, err = e2e.Kubectl("get", "gitrepositories", "podinfo", "-n", "flux-system", "-o", "jsonpath={.spec.url}") 127 require.NoError(t, err, stdOut, stdErr) 128 expectedMutatedRepoURL := fmt.Sprintf("%s/%s/podinfo-1646971829.git", types.JackalInClusterGitServiceURL, types.JackalGitPushUser) 129 require.Equal(t, expectedMutatedRepoURL, stdOut) 130 131 // Remove the flux example when deployment completes 132 stdOut, stdErr, err = e2e.Jackal("package", "remove", "podinfo-flux", "--confirm") 133 require.NoError(t, err, stdOut, stdErr) 134 135 // Prune the flux images to reduce disk pressure 136 stdOut, stdErr, err = e2e.Jackal("tools", "registry", "prune", "--confirm") 137 require.NoError(t, err, stdOut, stdErr) 138 } 139 140 func waitArgoDeployment(t *testing.T) { 141 // Deploy the argocd example and verify that it works 142 path := fmt.Sprintf("build/jackal-package-argocd-%s.tar.zst", e2e.Arch) 143 stdOut, stdErr, err := e2e.Jackal("package", "deploy", path, "--components=argocd-apps", "--confirm") 144 require.NoError(t, err, stdOut, stdErr) 145 146 expectedMutatedRepoURL := fmt.Sprintf("%s/%s/podinfo-1646971829.git", types.JackalInClusterGitServiceURL, types.JackalGitPushUser) 147 148 // Tests the mutation of the private repository Secret for ArgoCD. 149 stdOut, stdErr, err = e2e.Kubectl("get", "secret", "argocd-repo-github-podinfo", "-n", "argocd", "-o", "jsonpath={.data.url}") 150 require.NoError(t, err, stdOut, stdErr) 151 152 expectedMutatedPrivateRepoURLSecret, err := base64.StdEncoding.DecodeString(stdOut) 153 require.NoError(t, err, stdOut, stdErr) 154 require.Equal(t, expectedMutatedRepoURL, string(expectedMutatedPrivateRepoURLSecret)) 155 156 // Tests the mutation of the repoURL for Application CRD source(s) for ArgoCD. 157 stdOut, stdErr, err = e2e.Kubectl("get", "application", "apps", "-n", "argocd", "-o", "jsonpath={.spec.sources[0].repoURL}") 158 require.NoError(t, err, stdOut, stdErr) 159 require.Equal(t, expectedMutatedRepoURL, stdOut) 160 161 // Remove the argocd example when deployment completes 162 stdOut, stdErr, err = e2e.Jackal("package", "remove", "argocd", "--confirm") 163 require.NoError(t, err, stdOut, stdErr) 164 165 // Prune the ArgoCD images to reduce disk pressure 166 stdOut, stdErr, err = e2e.Jackal("tools", "registry", "prune", "--confirm") 167 require.NoError(t, err, stdOut, stdErr) 168 }