David Townley 3 anni fa
parent
commit
32d3293e8a
25 ha cambiato i file con 277 aggiunte e 242 eliminazioni
  1. 4 18
      api/server/handlers/project_integration/get_gitlab_repo_buildpack.go
  2. 3 17
      api/server/handlers/project_integration/get_gitlab_repo_contents.go
  3. 3 16
      api/server/handlers/project_integration/get_gitlab_repo_procfile.go
  4. 14 5
      api/server/handlers/project_integration/list_gitlab_repo_branches.go
  5. 15 4
      api/server/handlers/project_integration/list_gitlab_repos.go
  6. 7 8
      api/server/handlers/release/create.go
  7. 1 10
      api/server/handlers/release/delete.go
  8. 8 11
      api/server/router/project_integration.go
  9. 1 1
      api/server/shared/config/env/envconfs.go
  10. 23 0
      api/types/git_installation.go
  11. 22 18
      dashboard/src/components/repo-selector/BranchList.tsx
  12. 5 5
      dashboard/src/components/repo-selector/BuildpackSelection.tsx
  13. 5 5
      dashboard/src/components/repo-selector/BuildpackStack.tsx
  14. 15 13
      dashboard/src/components/repo-selector/ContentsList.tsx
  15. 5 4
      dashboard/src/components/repo-selector/DetectContentsList.tsx
  16. 34 26
      dashboard/src/components/repo-selector/RepoList.tsx
  17. 5 5
      dashboard/src/main/home/cluster-dashboard/expanded-chart/build-settings/_BuildpackConfigSection.tsx
  18. 50 40
      dashboard/src/shared/api.tsx
  19. 1 1
      internal/integrations/buildpacks/go.go
  20. 1 1
      internal/integrations/buildpacks/nodejs.go
  21. 1 1
      internal/integrations/buildpacks/python.go
  22. 6 6
      internal/integrations/buildpacks/ruby.go
  23. 1 2
      internal/integrations/buildpacks/shared.go
  24. 42 24
      internal/integrations/ci/gitlab/ci.go
  25. 5 1
      zarf/helm/server.yaml

+ 4 - 18
api/server/handlers/project_integration/get_gitlab_repo_buildpack.go

@@ -11,7 +11,6 @@ import (
 	"github.com/porter-dev/porter/api/server/handlers"
 	"github.com/porter-dev/porter/api/server/shared"
 	"github.com/porter-dev/porter/api/server/shared/apierrors"
-	"github.com/porter-dev/porter/api/server/shared/commonutils"
 	"github.com/porter-dev/porter/api/server/shared/config"
 	"github.com/porter-dev/porter/api/types"
 	"github.com/porter-dev/porter/internal/integrations/buildpacks"
@@ -39,22 +38,9 @@ func (p *GetGitlabRepoBuildpackHandler) ServeHTTP(w http.ResponseWriter, r *http
 	user, _ := r.Context().Value(types.UserScope).(*models.User)
 	gi, _ := r.Context().Value(types.GitlabIntegrationScope).(*ints.GitlabIntegration)
 
-	request := &types.GetBuildpackRequest{}
+	request := &types.GetGitlabBuildpackRequest{}
 
 	ok := p.DecodeAndValidate(w, r, request)
-
-	if !ok {
-		return
-	}
-
-	owner, name, ok := commonutils.GetOwnerAndNameParams(p, w, r)
-
-	if !ok {
-		return
-	}
-
-	branch, ok := commonutils.GetBranchParam(p, w, r)
-
 	if !ok {
 		return
 	}
@@ -81,9 +67,9 @@ func (p *GetGitlabRepoBuildpackHandler) ServeHTTP(w http.ResponseWriter, r *http
 		dir = "."
 	}
 
-	tree, resp, err := client.Repositories.ListTree(fmt.Sprintf("%s/%s", owner, name), &gitlab.ListTreeOptions{
+	tree, resp, err := client.Repositories.ListTree(request.RepoPath, &gitlab.ListTreeOptions{
 		Path: gitlab.String(dir),
-		Ref:  gitlab.String(branch),
+		Ref:  gitlab.String(request.Branch),
 	})
 
 	if resp.StatusCode == http.StatusUnauthorized {
@@ -111,7 +97,7 @@ func (p *GetGitlabRepoBuildpackHandler) ServeHTTP(w http.ResponseWriter, r *http
 				}
 			}()
 			buildpacks.Runtimes[idx].DetectGitlab(
-				client, tree, owner, name, dir, branch,
+				client, tree, request.RepoPath, dir, request.Branch,
 				builderInfoMap[buildpacks.PaketoBuilder], builderInfoMap[buildpacks.HerokuBuilder],
 			)
 			wg.Done()

+ 3 - 17
api/server/handlers/project_integration/get_gitlab_repo_contents.go

@@ -10,7 +10,6 @@ import (
 	"github.com/porter-dev/porter/api/server/handlers"
 	"github.com/porter-dev/porter/api/server/shared"
 	"github.com/porter-dev/porter/api/server/shared/apierrors"
-	"github.com/porter-dev/porter/api/server/shared/commonutils"
 	"github.com/porter-dev/porter/api/server/shared/config"
 	"github.com/porter-dev/porter/api/types"
 	"github.com/porter-dev/porter/internal/models"
@@ -37,22 +36,9 @@ func (p *GetGitlabRepoContentsHandler) ServeHTTP(w http.ResponseWriter, r *http.
 	user, _ := r.Context().Value(types.UserScope).(*models.User)
 	gi, _ := r.Context().Value(types.GitlabIntegrationScope).(*ints.GitlabIntegration)
 
-	request := &types.GetContentsRequest{}
+	request := &types.GetGitlabContentsRequest{}
 
 	ok := p.DecodeAndValidate(w, r, request)
-
-	if !ok {
-		return
-	}
-
-	owner, name, ok := commonutils.GetOwnerAndNameParams(p, w, r)
-
-	if !ok {
-		return
-	}
-
-	branch, ok := commonutils.GetBranchParam(p, w, r)
-
 	if !ok {
 		return
 	}
@@ -79,9 +65,9 @@ func (p *GetGitlabRepoContentsHandler) ServeHTTP(w http.ResponseWriter, r *http.
 		return
 	}
 
-	tree, resp, err := client.Repositories.ListTree(fmt.Sprintf("%s/%s", owner, name), &gitlab.ListTreeOptions{
+	tree, resp, err := client.Repositories.ListTree(request.RepoPath, &gitlab.ListTreeOptions{
 		Path: gitlab.String(dir),
-		Ref:  gitlab.String(branch),
+		Ref:  gitlab.String(request.Branch),
 	})
 
 	if resp.StatusCode == http.StatusUnauthorized {

+ 3 - 16
api/server/handlers/project_integration/get_gitlab_repo_procfile.go

@@ -11,7 +11,6 @@ import (
 	"github.com/porter-dev/porter/api/server/handlers"
 	"github.com/porter-dev/porter/api/server/shared"
 	"github.com/porter-dev/porter/api/server/shared/apierrors"
-	"github.com/porter-dev/porter/api/server/shared/commonutils"
 	"github.com/porter-dev/porter/api/server/shared/config"
 	"github.com/porter-dev/porter/api/types"
 	"github.com/porter-dev/porter/internal/models"
@@ -40,7 +39,7 @@ func (p *GetGitlabRepoProcfileHandler) ServeHTTP(w http.ResponseWriter, r *http.
 	user, _ := r.Context().Value(types.UserScope).(*models.User)
 	gi, _ := r.Context().Value(types.GitlabIntegrationScope).(*ints.GitlabIntegration)
 
-	request := &types.GetProcfileRequest{}
+	request := &types.GetGitlabProcfileRequest{}
 
 	ok := p.DecodeAndValidate(w, r, request)
 
@@ -48,18 +47,6 @@ func (p *GetGitlabRepoProcfileHandler) ServeHTTP(w http.ResponseWriter, r *http.
 		return
 	}
 
-	owner, name, ok := commonutils.GetOwnerAndNameParams(p, w, r)
-
-	if !ok {
-		return
-	}
-
-	branch, ok := commonutils.GetBranchParam(p, w, r)
-
-	if !ok {
-		return
-	}
-
 	path, err := url.QueryUnescape(request.Path)
 	if err != nil {
 		p.HandleAPIError(w, r, apierrors.NewErrForbidden(fmt.Errorf("malformed query param path")))
@@ -76,9 +63,9 @@ func (p *GetGitlabRepoProcfileHandler) ServeHTTP(w http.ResponseWriter, r *http.
 		return
 	}
 
-	file, resp, err := client.RepositoryFiles.GetRawFile(fmt.Sprintf("%s/%s", owner, name),
+	file, resp, err := client.RepositoryFiles.GetRawFile(request.RepoPath,
 		strings.TrimPrefix(path, "./"), &gitlab.GetRawFileOptions{
-			Ref: gitlab.String(branch),
+			Ref: gitlab.String(request.Branch),
 		},
 	)
 

+ 14 - 5
api/server/handlers/project_integration/list_gitlab_repo_branches.go

@@ -8,7 +8,6 @@ import (
 	"github.com/porter-dev/porter/api/server/handlers"
 	"github.com/porter-dev/porter/api/server/shared"
 	"github.com/porter-dev/porter/api/server/shared/apierrors"
-	"github.com/porter-dev/porter/api/server/shared/commonutils"
 	"github.com/porter-dev/porter/api/server/shared/config"
 	"github.com/porter-dev/porter/api/types"
 	"github.com/porter-dev/porter/internal/models"
@@ -35,12 +34,14 @@ func (p *ListGitlabRepoBranchesHandler) ServeHTTP(w http.ResponseWriter, r *http
 	user, _ := r.Context().Value(types.UserScope).(*models.User)
 	gi, _ := r.Context().Value(types.GitlabIntegrationScope).(*ints.GitlabIntegration)
 
-	owner, name, ok := commonutils.GetOwnerAndNameParams(p, w, r)
-
-	if !ok {
+	request := &types.ListGitlabRepoBranchesRequest{}
+	if ok := p.DecodeAndValidate(w, r, request); !ok {
+		p.HandleAPIError(w, r, apierrors.NewErrInternal(errors.New("cannot decode and validate request")))
 		return
 	}
 
+	repoPath := request.RepoPath
+
 	client, err := getGitlabClient(p.Repo(), user.ID, project.ID, gi, p.Config())
 	if err != nil {
 		if errors.Is(err, errUnauthorizedGitlabUser) {
@@ -51,7 +52,15 @@ func (p *ListGitlabRepoBranchesHandler) ServeHTTP(w http.ResponseWriter, r *http
 		return
 	}
 
-	branches, resp, err := client.Branches.ListBranches(fmt.Sprintf("%s/%s", owner, name), &gitlab.ListBranchesOptions{})
+	branches, resp, err := client.Branches.ListBranches(repoPath,
+		&gitlab.ListBranchesOptions{
+			ListOptions: gitlab.ListOptions{
+				Page:    1,
+				PerPage: 20,
+			},
+			Search: &request.SearchTerm,
+		},
+	)
 
 	if resp.StatusCode == http.StatusUnauthorized {
 		p.HandleAPIError(w, r, apierrors.NewErrPassThroughToClient(fmt.Errorf("unauthorized gitlab user"), http.StatusUnauthorized))

+ 15 - 4
api/server/handlers/project_integration/list_gitlab_repos.go

@@ -50,10 +50,23 @@ func (p *ListGitlabReposHandler) ServeHTTP(w http.ResponseWriter, r *http.Reques
 		return
 	}
 
-	giProjects, resp, err := client.Projects.ListProjects(&gitlab.ListProjectsOptions{
+	searchTerm := r.URL.Query().Get("searchTerm")
+
+	fmt.Printf("searching: %s\n", searchTerm)
+
+	opts := &gitlab.ListProjectsOptions{
 		Simple:     gitlab.Bool(true),
 		Membership: gitlab.Bool(true),
-	})
+		ListOptions: gitlab.ListOptions{
+			PerPage: 20,
+			Page:    1,
+		},
+		Search:           gitlab.String(searchTerm),
+		SearchNamespaces: gitlab.Bool(true),
+	}
+
+	var res []string
+	giProjects, resp, err := client.Projects.ListProjects(opts)
 
 	if resp.StatusCode == http.StatusUnauthorized {
 		p.HandleAPIError(w, r, apierrors.NewErrPassThroughToClient(fmt.Errorf("unauthorized gitlab user"), http.StatusUnauthorized))
@@ -65,8 +78,6 @@ func (p *ListGitlabReposHandler) ServeHTTP(w http.ResponseWriter, r *http.Reques
 		return
 	}
 
-	var res []string
-
 	for _, giProject := range giProjects {
 		res = append(res, giProject.PathWithNamespace)
 	}

+ 7 - 8
api/server/handlers/release/create.go

@@ -373,12 +373,6 @@ func createGitAction(
 
 	telemetry.WithAttributes(span, telemetry.AttributeKV{Key: "is-dry-run", Value: isDryRun})
 
-	repoSplit := strings.Split(request.GitRepo, "/")
-
-	if len(repoSplit) != 2 {
-		return nil, nil, fmt.Errorf("invalid formatting of repo name")
-	}
-
 	encoded := ""
 	var err error
 
@@ -397,8 +391,7 @@ func createGitAction(
 	if request.GitlabIntegrationID != 0 {
 		giRunner := &gitlab.GitlabCI{
 			ServerURL:        config.ServerConf.ServerURL,
-			GitRepoOwner:     repoSplit[0],
-			GitRepoName:      repoSplit[1],
+			GitRepoPath:      request.GitRepo,
 			GitBranch:        request.GitBranch,
 			Repo:             config.Repo,
 			ProjectID:        projectID,
@@ -414,6 +407,12 @@ func createGitAction(
 
 		gitErr = giRunner.Setup()
 	} else {
+		repoSplit := strings.Split(request.GitRepo, "/")
+
+		if len(repoSplit) != 2 {
+			return nil, nil, fmt.Errorf("invalid formatting of repo name")
+		}
+
 		// create the commit in the git repo
 		gaRunner := &actions.GithubActions{
 			InstanceName:           config.ServerConf.InstanceName,

+ 1 - 10
api/server/handlers/release/delete.go

@@ -2,9 +2,7 @@ package release
 
 import (
 	"context"
-	"fmt"
 	"net/http"
-	"strings"
 
 	"github.com/porter-dev/porter/api/server/authz"
 	"github.com/porter-dev/porter/api/server/handlers"
@@ -60,17 +58,10 @@ func (c *DeleteReleaseHandler) ServeHTTP(w http.ResponseWriter, r *http.Request)
 
 			if gitAction != nil && gitAction.ID != 0 {
 				if gitAction.GitlabIntegrationID != 0 {
-					repoSplit := strings.Split(gitAction.GitRepo, "/")
-
-					if len(repoSplit) != 2 {
-						c.HandleAPIError(w, r, apierrors.NewErrInternal(fmt.Errorf("invalid formatting of repo name")))
-						return
-					}
 
 					giRunner := &gitlab.GitlabCI{
 						ServerURL:        c.Config().ServerConf.ServerURL,
-						GitRepoOwner:     repoSplit[0],
-						GitRepoName:      repoSplit[1],
+						GitRepoPath:      gitAction.GitRepo,
 						Repo:             c.Repo(),
 						ProjectID:        cluster.ProjectID,
 						ClusterID:        cluster.ID,

+ 8 - 11
api/server/router/project_integration.go

@@ -481,8 +481,8 @@ func getProjectIntegrationRoutes(
 			Method: types.HTTPVerbGet,
 			Path: &types.Path{
 				Parent: basePath,
-				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/{%s}/{%s}/branches",
-					relPath, types.URLParamIntegrationID, types.URLParamGitRepoOwner, types.URLParamGitRepoName),
+				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/branches",
+					relPath, types.URLParamIntegrationID),
 			},
 			Scopes: []types.PermissionScope{
 				types.UserScope,
@@ -511,9 +511,8 @@ func getProjectIntegrationRoutes(
 			Method: types.HTTPVerbGet,
 			Path: &types.Path{
 				Parent: basePath,
-				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/{%s}/{%s}/{%s}/contents", relPath,
-					types.URLParamIntegrationID, types.URLParamGitRepoOwner,
-					types.URLParamGitRepoName, types.URLParamGitBranch),
+				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/contents", relPath,
+					types.URLParamIntegrationID),
 			},
 			Scopes: []types.PermissionScope{
 				types.UserScope,
@@ -542,9 +541,8 @@ func getProjectIntegrationRoutes(
 			Method: types.HTTPVerbGet,
 			Path: &types.Path{
 				Parent: basePath,
-				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/{%s}/{%s}/{%s}/buildpack/detect", relPath,
-					types.URLParamIntegrationID, types.URLParamGitRepoOwner,
-					types.URLParamGitRepoName, types.URLParamGitBranch),
+				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/buildpack/detect", relPath,
+					types.URLParamIntegrationID),
 			},
 			Scopes: []types.PermissionScope{
 				types.UserScope,
@@ -573,9 +571,8 @@ func getProjectIntegrationRoutes(
 			Method: types.HTTPVerbGet,
 			Path: &types.Path{
 				Parent: basePath,
-				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/{%s}/{%s}/{%s}/procfile", relPath,
-					types.URLParamIntegrationID, types.URLParamGitRepoOwner,
-					types.URLParamGitRepoName, types.URLParamGitBranch),
+				RelativePath: fmt.Sprintf("%s/gitlab/{%s}/repos/procfile", relPath,
+					types.URLParamIntegrationID),
 			},
 			Scopes: []types.PermissionScope{
 				types.UserScope,

+ 1 - 1
api/server/shared/config/env/envconfs.go

@@ -112,7 +112,7 @@ type ServerConf struct {
 	DisableAllowlist bool `env:"DISABLE_ALLOWLIST,default=true"`
 
 	// Enable gitlab integration
-	EnableGitlab bool `env:"ENABLE_GITLAB,default=false"`
+	EnableGitlab bool `env:"ENABLE_GITLAB,default=true"`
 
 	// DisableRegistrySecretsInjection is used to denote if Porter should not inject
 	// imagePullSecrets into a kubernetes deployment (Porter application)

+ 23 - 0
api/types/git_installation.go

@@ -32,6 +32,29 @@ const (
 
 type ListRepoBranchesResponse []string
 
+type ListGitlabRepoBranchesRequest struct {
+	RepoPath   string `schema:"repo_path" form:"required"`
+	SearchTerm string `schema:"search_term"`
+}
+
+type GitlabRepoBranchRequest struct {
+	RepoPath string `schema:"repo_path" form:"required"`
+	Branch   string `schema:"branch" form:"required"`
+}
+
+type GetGitlabContentsRequest struct {
+	GitlabRepoBranchRequest
+	GetContentsRequest
+}
+type GetGitlabBuildpackRequest struct {
+	GitlabRepoBranchRequest
+	GetBuildpackRequest
+}
+type GetGitlabProcfileRequest struct {
+	GitlabRepoBranchRequest
+	GetProcfileRequest
+}
+
 type GithubDirectoryRequest struct {
 	Dir string `schema:"dir" form:"required"`
 }

+ 22 - 18
dashboard/src/components/repo-selector/BranchList.tsx

@@ -37,7 +37,7 @@ const BranchList: React.FC<Props> = ({
   useEffect(() => {
     // Get branches
     if (!actionConfig) {
-      return () => { };
+      return () => {};
     }
 
     if (actionConfig?.kind === "github") {
@@ -67,12 +67,13 @@ const BranchList: React.FC<Props> = ({
       api
         .getGitlabBranches(
           "<token>",
-          {},
+          {
+            repo_path: actionConfig.git_repo,
+            search_term: searchFilter,
+          },
           {
             project_id: currentProject.id,
             integration_id: actionConfig.gitlab_integration_id,
-            repo_owner: actionConfig.git_repo.split("/")[0],
-            repo_name: actionConfig.git_repo.split("/")[1],
           }
         )
         .then((res) => {
@@ -86,7 +87,7 @@ const BranchList: React.FC<Props> = ({
           setError(true);
         });
     }
-  }, []);
+  }, [searchFilter]);
 
   const renderBranchList = () => {
     if (loading) {
@@ -99,19 +100,22 @@ const BranchList: React.FC<Props> = ({
       return <LoadingWrapper>Error loading branches</LoadingWrapper>;
     }
 
-    let results = searchFilter != null
-      ? branches
-        .filter((branch) => {
-          return branch.toLowerCase().includes(
-            searchFilter.toLowerCase()
-          );
-        })
-        .sort((a: string, b: string) => {
-          const aIndex = a.toLowerCase().indexOf(searchFilter.toLowerCase());
-          const bIndex = b.toLowerCase().indexOf(searchFilter.toLowerCase());
-          return aIndex - bIndex;
-        })
-      : sortBranches(branches).slice(0, 10);
+    let results =
+      searchFilter != null
+        ? branches
+            .filter((branch) => {
+              return branch.toLowerCase().includes(searchFilter.toLowerCase());
+            })
+            .sort((a: string, b: string) => {
+              const aIndex = a
+                .toLowerCase()
+                .indexOf(searchFilter.toLowerCase());
+              const bIndex = b
+                .toLowerCase()
+                .indexOf(searchFilter.toLowerCase());
+              return aIndex - bIndex;
+            })
+        : sortBranches(branches).slice(0, 10);
 
     if (results.length == 0) {
       return <LoadingWrapper>No matching Branches found.</LoadingWrapper>;

+ 5 - 5
dashboard/src/components/repo-selector/BuildpackSelection.tsx

@@ -73,14 +73,14 @@ export const BuildpackSelection: React.FC<{
     if (actionConfig.kind === "gitlab") {
       return api.detectGitlabBuildpack<DetectBuildpackResponse>(
         "<token>",
-        { dir: folderPath || "." },
+        {
+          repo_path: actionConfig.git_repo,
+          branch: branch,
+          dir: folderPath || ".",
+        },
         {
           project_id: currentProject.id,
           integration_id: actionConfig.gitlab_integration_id,
-
-          repo_owner: actionConfig.git_repo.split("/")[0],
-          repo_name: actionConfig.git_repo.split("/")[1],
-          branch: branch,
         }
       );
     }

+ 5 - 5
dashboard/src/components/repo-selector/BuildpackStack.tsx

@@ -133,14 +133,14 @@ export const BuildpackStack: React.FC<{
     if (actionConfig.kind === "gitlab") {
       return api.detectGitlabBuildpack<DetectBuildpackResponse>(
         "<token>",
-        { dir: folderPath || "." },
+        {
+          repo_path: actionConfig.git_repo,
+          branch: branch,
+          dir: folderPath || ".",
+        },
         {
           project_id: currentProject.id,
           integration_id: actionConfig.gitlab_integration_id,
-
-          repo_owner: actionConfig.git_repo.split("/")[0],
-          repo_name: actionConfig.git_repo.split("/")[1],
-          branch: branch,
         }
       );
     }

+ 15 - 13
dashboard/src/components/repo-selector/ContentsList.tsx

@@ -71,13 +71,14 @@ export default class ContentsList extends Component<PropsType, StateType> {
       return api
         .getGitlabFolderContent(
           "<token>",
-          { dir: this.state.currentDir || "./" },
+          {
+            repo_path: actionConfig.git_repo,
+            branch: branch,
+            dir: this.state.currentDir || "./",
+          },
           {
             project_id: currentProject.id,
             integration_id: actionConfig.gitlab_integration_id,
-            repo_owner: actionConfig.git_repo.split("/")[0],
-            repo_name: actionConfig.git_repo.split("/")[1],
-            branch: branch,
           }
         )
         .then((res) => {
@@ -128,14 +129,14 @@ export default class ContentsList extends Component<PropsType, StateType> {
 
     return api.detectGitlabBuildpack(
       "<token>",
-      { dir: this.state.currentDir || "." },
+      {
+        repo_path: actionConfig.git_repo,
+        branch: branch,
+        dir: this.state.currentDir || ".",
+      },
       {
         project_id: currentProject.id,
         integration_id: actionConfig.gitlab_integration_id,
-
-        repo_owner: actionConfig.git_repo.split("/")[0],
-        repo_name: actionConfig.git_repo.split("/")[1],
-        branch: branch,
       }
     );
   };
@@ -162,13 +163,14 @@ export default class ContentsList extends Component<PropsType, StateType> {
 
     return api.getGitlabProcfileContents(
       "<token>",
-      { path: procfilePath },
+      {
+        repo_path: actionConfig.git_repo,
+        branch: branch,
+        path: procfilePath,
+      },
       {
         project_id: currentProject.id,
         integration_id: actionConfig.gitlab_integration_id,
-        owner: actionConfig.git_repo.split("/")[0],
-        name: actionConfig.git_repo.split("/")[1],
-        branch: branch,
       }
     );
   };

+ 5 - 4
dashboard/src/components/repo-selector/DetectContentsList.tsx

@@ -132,13 +132,14 @@ const DetectContentsList: React.FC<PropsType> = (props) => {
       return api
         .getGitlabFolderContent(
           "<token>",
-          { dir: currentDir || "./" },
+          {
+            repo_path: actionConfig.git_repo,
+            branch: branch,
+            dir: currentDir || "./",
+          },
           {
             project_id: currentProject.id,
             integration_id: actionConfig.gitlab_integration_id,
-            repo_owner: actionConfig.git_repo.split("/")[0],
-            repo_name: actionConfig.git_repo.split("/")[1],
-            branch: branch,
           }
         )
         .then((res) => {

+ 34 - 26
dashboard/src/components/repo-selector/RepoList.tsx

@@ -11,6 +11,7 @@ import SearchBar from "../SearchBar";
 import DynamicLink from "components/DynamicLink";
 import { useOutsideAlerter } from "shared/hooks/useOutsideAlerter";
 import Text from "components/porter/Text";
+import { search } from "../../shared/search";
 
 type Props = {
   actionConfig: ActionConfigType | null;
@@ -22,15 +23,15 @@ type Props = {
 
 type Provider =
   | {
-    provider: "github";
-    name: string;
-    installation_id: number;
-  }
+      provider: "github";
+      name: string;
+      installation_id: number;
+    }
   | {
-    provider: "gitlab";
-    instance_url: string;
-    integration_id: number;
-  };
+      provider: "gitlab";
+      instance_url: string;
+      integration_id: number;
+    };
 
 // Sort provider by name if it's github or instance url if it's gitlab
 const sortProviders = (providers: Provider[]) => {
@@ -110,14 +111,16 @@ const RepoList: React.FC<Props> = ({
 
       const repos = res.data.map((repo) => ({ ...repo, GHRepoID: repoId }));
       return repos;
-    } catch (error) { }
+    } catch (error) {}
   };
 
   const loadGitlabRepos = async (integrationId: number) => {
     try {
       const res = await api.getGitlabRepos<string[]>(
         "<token>",
-        {},
+        {
+          searchTerm: searchFilter,
+        },
         { project_id: currentProject.id, integration_id: integrationId }
       );
       const repos: RepoType[] = res.data.map((repo) => ({
@@ -126,7 +129,7 @@ const RepoList: React.FC<Props> = ({
         GitIntegrationId: integrationId,
       }));
       return repos;
-    } catch (error) { }
+    } catch (error) {}
   };
 
   const loadRepos = (provider: any) => {
@@ -160,7 +163,7 @@ const RepoList: React.FC<Props> = ({
       .finally(() => {
         setRepoLoading(false);
       });
-  }, [currentProvider]);
+  }, [currentProvider, searchFilter]);
 
   // clear out actionConfig and SelectedRepository if new search is performed
   useEffect(() => {
@@ -237,19 +240,24 @@ const RepoList: React.FC<Props> = ({
     }
 
     // show 10 most recently used repos if user hasn't searched anything yet
-    let results = searchFilter != null
-      ? repos
-        .filter((repo: RepoType) => {
-          return repo.FullName.toLowerCase().includes(
-            searchFilter.toLowerCase()
-          );
-        })
-        .sort((a: RepoType, b: RepoType) => {
-          const aIndex = a.FullName.toLowerCase().indexOf(searchFilter.toLowerCase());
-          const bIndex = b.FullName.toLowerCase().indexOf(searchFilter.toLowerCase());
-          return aIndex - bIndex;
-        })
-      : repos.slice(0, 10);
+    let results =
+      searchFilter != null
+        ? repos
+            .filter((repo: RepoType) => {
+              return repo.FullName.toLowerCase().includes(
+                searchFilter.toLowerCase()
+              );
+            })
+            .sort((a: RepoType, b: RepoType) => {
+              const aIndex = a.FullName.toLowerCase().indexOf(
+                searchFilter.toLowerCase()
+              );
+              const bIndex = b.FullName.toLowerCase().indexOf(
+                searchFilter.toLowerCase()
+              );
+              return aIndex - bIndex;
+            })
+        : repos.slice(0, 10);
 
     if (results.length == 0) {
       return <LoadingWrapper>No matching Github repos found.</LoadingWrapper>;
@@ -358,7 +366,7 @@ const ConnectToGithubButton = styled.a`
     props.disabled ? "#aaaabbee" : "#2E3338"};
   :hover {
     background: ${(props: { disabled?: boolean }) =>
-    props.disabled ? "" : "#353a3e"};
+      props.disabled ? "" : "#353a3e"};
   }
 
   > i {

+ 5 - 5
dashboard/src/main/home/cluster-dashboard/expanded-chart/build-settings/_BuildpackConfigSection.tsx

@@ -95,14 +95,14 @@ const BuildpackConfigSection = forwardRef<
     if (actionConfig.kind === "gitlab") {
       return api.detectGitlabBuildpack<DetectBuildpackResponse>(
         "<token>",
-        { dir: actionConfig.folder_path || "." },
+        {
+          repo_path: actionConfig.git_repo,
+          branch: actionConfig.git_branch,
+          dir: actionConfig.folder_path || ".",
+        },
         {
           project_id: currentProject.id,
           integration_id: actionConfig.gitlab_integration_id,
-
-          repo_owner: actionConfig.git_repo.split("/")[0],
-          repo_name: actionConfig.git_repo.split("/")[1],
-          branch: actionConfig.git_branch,
         }
       );
     }

+ 50 - 40
dashboard/src/shared/api.tsx

@@ -633,24 +633,27 @@ const detectBuildpack = baseApi<
     branch: string;
   }
 >("GET", (pathParams) => {
-  return `/api/projects/${pathParams.project_id}/gitrepos/${pathParams.git_repo_id
-    }/repos/${pathParams.kind}/${pathParams.owner}/${pathParams.name
-    }/${encodeURIComponent(pathParams.branch)}/buildpack/detect`;
+  return `/api/projects/${pathParams.project_id}/gitrepos/${
+    pathParams.git_repo_id
+  }/repos/${pathParams.kind}/${pathParams.owner}/${
+    pathParams.name
+  }/${encodeURIComponent(pathParams.branch)}/buildpack/detect`;
 });
 
 const detectGitlabBuildpack = baseApi<
-  { dir: string },
+  {
+    repo_path: string;
+    branch: string;
+    dir: string;
+  },
   {
     project_id: number;
     integration_id: number;
-    repo_owner: string;
-    repo_name: string;
-    branch: string;
   }
 >(
   "GET",
-  ({ project_id, integration_id, repo_name, repo_owner, branch }) =>
-    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/${repo_owner}/${repo_name}/${branch}/buildpack/detect`
+  ({ project_id, integration_id }) =>
+    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/buildpack/detect`
 );
 
 const getBranchContents = baseApi<
@@ -666,9 +669,11 @@ const getBranchContents = baseApi<
     branch: string;
   }
 >("GET", (pathParams) => {
-  return `/api/projects/${pathParams.project_id}/gitrepos/${pathParams.git_repo_id
-    }/repos/${pathParams.kind}/${pathParams.owner}/${pathParams.name
-    }/${encodeURIComponent(pathParams.branch)}/contents`;
+  return `/api/projects/${pathParams.project_id}/gitrepos/${
+    pathParams.git_repo_id
+  }/repos/${pathParams.kind}/${pathParams.owner}/${
+    pathParams.name
+  }/${encodeURIComponent(pathParams.branch)}/contents`;
 });
 
 const getProcfileContents = baseApi<
@@ -684,9 +689,11 @@ const getProcfileContents = baseApi<
     branch: string;
   }
 >("GET", (pathParams) => {
-  return `/api/projects/${pathParams.project_id}/gitrepos/${pathParams.git_repo_id
-    }/repos/${pathParams.kind}/${pathParams.owner}/${pathParams.name
-    }/${encodeURIComponent(pathParams.branch)}/procfile`;
+  return `/api/projects/${pathParams.project_id}/gitrepos/${
+    pathParams.git_repo_id
+  }/repos/${pathParams.kind}/${pathParams.owner}/${
+    pathParams.name
+  }/${encodeURIComponent(pathParams.branch)}/procfile`;
 });
 
 const getPorterYamlContents = baseApi<
@@ -702,28 +709,27 @@ const getPorterYamlContents = baseApi<
     branch: string;
   }
 >("GET", (pathParams) => {
-  return `/api/projects/${pathParams.project_id}/gitrepos/${pathParams.git_repo_id
-    }/repos/${pathParams.kind}/${pathParams.owner}/${pathParams.name
-    }/${encodeURIComponent(pathParams.branch)}/porteryaml`;
+  return `/api/projects/${pathParams.project_id}/gitrepos/${
+    pathParams.git_repo_id
+  }/repos/${pathParams.kind}/${pathParams.owner}/${
+    pathParams.name
+  }/${encodeURIComponent(pathParams.branch)}/porteryaml`;
 });
 
 const getGitlabProcfileContents = baseApi<
   {
+    repo_path: string;
+    branch: string;
     path: string;
   },
   {
     project_id: number;
     integration_id: number;
-    owner: string;
-    name: string;
-    branch: string;
   }
 >(
   "GET",
-  ({ project_id, integration_id, owner, name, branch }) =>
-    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/${owner}/${name}/${encodeURIComponent(
-      branch
-    )}/procfile`
+  ({ project_id, integration_id }) =>
+    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/procfile`
 );
 
 const getBranches = baseApi<
@@ -1558,9 +1564,11 @@ const getEnvGroup = baseApi<
     version?: number;
   }
 >("GET", (pathParams) => {
-  return `/api/projects/${pathParams.id}/clusters/${pathParams.cluster_id
-    }/namespaces/${pathParams.namespace}/envgroup?name=${pathParams.name}${pathParams.version ? "&version=" + pathParams.version : ""
-    }`;
+  return `/api/projects/${pathParams.id}/clusters/${
+    pathParams.cluster_id
+  }/namespaces/${pathParams.namespace}/envgroup?name=${pathParams.name}${
+    pathParams.version ? "&version=" + pathParams.version : ""
+  }`;
 });
 
 const getConfigMap = baseApi<
@@ -2134,7 +2142,9 @@ const getGitProviders = baseApi<{}, { project_id: number }>(
 );
 
 const getGitlabRepos = baseApi<
-  {},
+  {
+    search_term: string;
+  },
   { project_id: number; integration_id: number }
 >(
   "GET",
@@ -2143,34 +2153,34 @@ const getGitlabRepos = baseApi<
 );
 
 const getGitlabBranches = baseApi<
-  {},
+  {
+    repo_path: string;
+    search_term: string;
+  },
   {
     project_id: number;
     integration_id: number;
-    repo_owner: string;
-    repo_name: string;
   }
 >(
   "GET",
-  ({ project_id, integration_id, repo_owner, repo_name }) =>
-    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/${repo_owner}/${repo_name}/branches`
+  ({ project_id, integration_id }) =>
+    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/branches`
 );
 
 const getGitlabFolderContent = baseApi<
   {
+    repo_path: string;
+    branch: string;
     dir: string;
   },
   {
     project_id: number;
     integration_id: number;
-    repo_owner: string;
-    repo_name: string;
-    branch: string;
   }
 >(
   "GET",
-  ({ project_id, integration_id, repo_owner, repo_name, branch }) =>
-    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/${repo_owner}/${repo_name}/${branch}/contents`
+  ({ project_id, integration_id }) =>
+    `/api/projects/${project_id}/integrations/gitlab/${integration_id}/repos/contents`
 );
 
 const getLogPodValues = baseApi<
@@ -2487,7 +2497,7 @@ const removeStackEnvGroup = baseApi<
     `/api/v1/projects/${project_id}/clusters/${cluster_id}/namespaces/${namespace}/stacks/${stack_id}/remove_env_group/${env_group_name}`
 );
 
-const getGithubStatus = baseApi<{}, {}>("GET", ({ }) => `/api/status/github`);
+const getGithubStatus = baseApi<{}, {}>("GET", ({}) => `/api/status/github`);
 
 const createSecretAndOpenGitHubPullRequest = baseApi<
   {

+ 1 - 1
internal/integrations/buildpacks/go.go

@@ -155,7 +155,7 @@ func (runtime *goRuntime) DetectGithub(
 func (runtime *goRuntime) DetectGitlab(
 	client *gitlab.Client,
 	tree []*gitlab.TreeNode,
-	owner, name, path, ref string,
+	repoPath, path, ref string,
 	paketo, heroku *BuilderInfo,
 ) error {
 	results := make(chan struct {

+ 1 - 1
internal/integrations/buildpacks/nodejs.go

@@ -414,7 +414,7 @@ func (runtime *nodejsRuntime) DetectGithub(
 func (runtime *nodejsRuntime) DetectGitlab(
 	client *gitlab.Client,
 	tree []*gitlab.TreeNode,
-	owner, name, path, ref string,
+	repoPath, path, ref string,
 	paketo, heroku *BuilderInfo,
 ) error {
 	results := make(chan struct {

+ 1 - 1
internal/integrations/buildpacks/python.go

@@ -252,7 +252,7 @@ func (runtime *pythonRuntime) DetectGithub(
 func (runtime *pythonRuntime) DetectGitlab(
 	client *gitlab.Client,
 	tree []*gitlab.TreeNode,
-	owner, name, path, ref string,
+	repoPath, path, ref string,
 	paketo, heroku *BuilderInfo,
 ) error {
 	results := make(chan struct {

+ 6 - 6
internal/integrations/buildpacks/ruby.go

@@ -161,13 +161,13 @@ func (runtime *rubyRuntime) detectRackupGithub(
 }
 
 func (runtime *rubyRuntime) detectRackupGitlab(
-	client *gitlab.Client, owner, name, ref string, results chan struct {
+	client *gitlab.Client, repoPath, ref string, results chan struct {
 		string
 		bool
 	},
 ) {
 	fileContent, _, err := client.RepositoryFiles.GetRawFile(
-		fmt.Sprintf("%s/%s", owner, name), "Gemfile.lock", &gitlab.GetRawFileOptions{
+		repoPath, "Gemfile.lock", &gitlab.GetRawFileOptions{
 			Ref: gitlab.String(ref),
 		})
 	if err != nil {
@@ -325,7 +325,7 @@ func (runtime *rubyRuntime) DetectGithub(
 func (runtime *rubyRuntime) DetectGitlab(
 	client *gitlab.Client,
 	tree []*gitlab.TreeNode,
-	owner, name, path, ref string,
+	repoPath, path, ref string,
 	paketo, heroku *BuilderInfo,
 ) error {
 	gemfileFound := false
@@ -361,13 +361,13 @@ func (runtime *rubyRuntime) DetectGitlab(
 	}
 
 	fileContent, _, err := client.RepositoryFiles.GetRawFile(
-		fmt.Sprintf("%s/%s", owner, name), "Gemfile", &gitlab.GetRawFileOptions{
+		repoPath, "Gemfile", &gitlab.GetRawFileOptions{
 			Ref: gitlab.String(ref),
 		})
 	if err != nil {
 		paketo.Others = append(paketo.Others, paketoBuildpackInfo)
 		heroku.Others = append(heroku.Others, herokuBuildpackInfo)
-		return fmt.Errorf("error fetching contents of Gemfile for %s/%s: %v", owner, name, err)
+		return fmt.Errorf("error fetching contents of Gemfile for %s: %v", repoPath, err)
 	}
 	gemfileContent := string(fileContent)
 
@@ -405,7 +405,7 @@ func (runtime *rubyRuntime) DetectGitlab(
 	}
 	go runtime.detectPassenger(gemfileContent, results)
 	if !configRuFound && gemfileLockFound {
-		go runtime.detectRackupGitlab(client, owner, name, ref, results)
+		go runtime.detectRackupGitlab(client, repoPath, ref, results)
 	}
 	if rakefileFound {
 		go runtime.detectRake(gemfileContent, results)

+ 1 - 2
internal/integrations/buildpacks/shared.go

@@ -62,8 +62,7 @@ type Runtime interface {
 	DetectGitlab(
 		*gitlab.Client, // github client to pull contents of files
 		[]*gitlab.TreeNode, // the root folder structure of the git repo
-		string, // owner
-		string, // name
+		string, // repoPath
 		string, // path
 		string, // SHA, branch or tag
 		*BuilderInfo, // paketo

+ 42 - 24
internal/integrations/ci/gitlab/ci.go

@@ -15,10 +15,9 @@ import (
 )
 
 type GitlabCI struct {
-	ServerURL    string
-	GitRepoName  string
-	GitRepoOwner string
-	GitBranch    string
+	ServerURL   string
+	GitRepoPath string
+	GitBranch   string
 
 	Repo repository.Repository
 
@@ -44,18 +43,12 @@ func (g *GitlabCI) Setup() error {
 		return err
 	}
 
-	g.pID = fmt.Sprintf("%s/%s", g.GitRepoOwner, g.GitRepoName)
+	g.pID = g.GitRepoPath
 
-	branches, _, err := client.Branches.ListBranches(g.pID, &gitlab.ListBranchesOptions{})
-	if err != nil {
-		return fmt.Errorf("error fetching list of branches: %w", err)
-	}
+	err = g.setGitlabDefaultBranch(client)
 
-	for _, branch := range branches {
-		if branch.Default {
-			g.defaultGitBranch = branch.Name
-			break
-		}
+	if err != nil {
+		return err
 	}
 
 	err = g.createGitlabSecret(client)
@@ -194,18 +187,12 @@ func (g *GitlabCI) Cleanup() error {
 		return err
 	}
 
-	g.pID = fmt.Sprintf("%s/%s", g.GitRepoOwner, g.GitRepoName)
+	g.pID = g.GitRepoPath
 
-	branches, _, err := client.Branches.ListBranches(g.pID, &gitlab.ListBranchesOptions{})
-	if err != nil {
-		return fmt.Errorf("error fetching list of branches: %w", err)
-	}
+	err = g.setGitlabDefaultBranch(client)
 
-	for _, branch := range branches {
-		if branch.Default {
-			g.defaultGitBranch = branch.Name
-			break
-		}
+	if err != nil {
+		return err
 	}
 
 	err = g.deleteGitlabSecret(client)
@@ -495,3 +482,34 @@ func (g *GitlabCI) getPorterTokenSecretName() string {
 func getGitlabStageJobName(releaseName string) string {
 	return fmt.Sprintf("porter-%s", strings.ToLower(strings.ReplaceAll(releaseName, "_", "-")))
 }
+
+func (g *GitlabCI) setGitlabDefaultBranch(client *gitlab.Client) error {
+	opt := &gitlab.ListBranchesOptions{
+		ListOptions: gitlab.ListOptions{
+			PerPage: 20,
+			Page:    1,
+		},
+	}
+
+	for {
+		branches, resp, err := client.Branches.ListBranches(g.pID, opt)
+		if err != nil {
+			return fmt.Errorf("error fetching list of branches: %w", err)
+		}
+
+		for _, branch := range branches {
+			if branch.Default {
+				g.defaultGitBranch = branch.Name
+				return nil
+			}
+		}
+		// Exit the loop when we've seen all pages.
+		if resp.NextPage == 0 {
+			break
+		}
+
+		// Update the page number to get the next page.
+		opt.Page = resp.NextPage
+	}
+	return nil
+}

+ 5 - 1
zarf/helm/server.yaml

@@ -101,4 +101,8 @@ emptyDir:
 
 podSecurityContext: 
   runAsNonRoot: false
-  runAsUser: 0
+  runAsUser: 0
+
+server:
+  gitlab:
+    enabled: true