diff --git a/server/events/models/models.go b/server/events/models/models.go index f59adf255c..63ef9b723d 100644 --- a/server/events/models/models.go +++ b/server/events/models/models.go @@ -437,7 +437,10 @@ func GetProjectIdentifier(relRepoDir string, projectName string) string { if projectName != "" { return projectName } - return strings.ReplaceAll(relRepoDir, "/", "-") + // Replace directory separator / with - + // Replace . with _ to ensure projects with no project name and root dir set to "." have a valid URL + replacer := strings.NewReplacer("/", "-", ".", "_") + return replacer.Replace(relRepoDir) } // SplitRepoFullName splits a repo full name up into its owner and repo diff --git a/server/router_test.go b/server/router_test.go index 8b551ae7ca..5ebe2367f1 100644 --- a/server/router_test.go +++ b/server/router_test.go @@ -116,6 +116,26 @@ func TestGenerateProjectJobURL_ShouldGenerateURLWithDirectoryAndWorkspaceWhenPro Equals(t, expectedURL, gotURL) } +func TestGenerateProjectJobURL_ShouldGenerateURLWhenWorkingDirSetToBase(t *testing.T) { + router := setupJobsRouter(t) + ctx := models.ProjectCommandContext{ + Pull: models.PullRequest{ + BaseRepo: models.Repo{ + Owner: "test-owner", + Name: "test-repo", + }, + Num: 1, + }, + RepoRelDir: ".", + Workspace: "default", + } + expectedURL := "http://localhost:4141/jobs/test-owner/test-repo/1/_/default" + gotURL, err := router.GenerateProjectJobURL(ctx) + Ok(t, err) + + Equals(t, expectedURL, gotURL) +} + func TestGenerateProjectJobURL_ShouldGenerateURLWhenNestedRepo(t *testing.T) { router := setupJobsRouter(t) ctx := models.ProjectCommandContext{