Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-pages.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTuomo Ala-Vannesluoma <tuomoav@gmail.com>2018-09-30 15:05:27 +0300
committerTuomo Ala-Vannesluoma <tuomoav@gmail.com>2018-09-30 15:05:27 +0300
commitc69313b2ed71fbecd8acca283954dc3cfe424acb (patch)
tree63c4e2cbc80c82bcb7cd6181e13c2b2f3b6992a3
parentcee3464d6fe99efebac5f8d1b569f1301babdade (diff)
parentd07b803b6f8519566940843e389a6c2d73424a76 (diff)
Merge commit 'd07b803b6f8519566940843e389a6c2d73424a76' into auth
-rw-r--r--internal/domain/domain.go82
-rw-r--r--internal/domain/domain_test.go30
2 files changed, 64 insertions, 48 deletions
diff --git a/internal/domain/domain.go b/internal/domain/domain.go
index 4ac43100..a402d9e0 100644
--- a/internal/domain/domain.go
+++ b/internal/domain/domain.go
@@ -101,15 +101,25 @@ func setContentType(w http.ResponseWriter, fullPath string) {
}
}
+func getHost(r *http.Request) string {
+ host := strings.ToLower(r.Host)
+
+ if splitHost, _, err := net.SplitHostPort(host); err == nil {
+ host = splitHost
+ }
+
+ return host
+}
+
// Look up a project inside the domain based on the host and path. Returns the
// project and its name (if applicable)
-func (d *D) getProject(r *http.Request) (*project, string) {
+func (d *D) getProjectWithSubpath(r *http.Request) (*project, string, string) {
// Check for a project specified in the URL: http://group.gitlab.io/projectA
// If present, these projects shadow the group domain.
split := strings.SplitN(r.URL.Path, "/", 3)
if len(split) >= 2 {
if project := d.projects[split[1]]; project != nil {
- return project, split[1]
+ return project, split[1], strings.Join(split[2:], "/")
}
}
@@ -117,21 +127,11 @@ func (d *D) getProject(r *http.Request) (*project, string) {
// return the group project if it exists.
if host := getHost(r); host != "" {
if groupProject := d.projects[host]; groupProject != nil {
- return groupProject, host
+ return groupProject, host, strings.Join(split[1:], "/")
}
}
- return nil, ""
-}
-
-func getHost(r *http.Request) string {
- host := strings.ToLower(r.Host)
-
- if splitHost, _, err := net.SplitHostPort(host); err == nil {
- host = splitHost
- }
-
- return host
+ return nil, "", ""
}
// IsHTTPSOnly figures out if the request should be handled with HTTPS
@@ -147,7 +147,7 @@ func (d *D) IsHTTPSOnly(r *http.Request) bool {
}
// Check projects served under the group domain, including the default one
- if project, _ := d.getProject(r); project != nil {
+ if project, _, _ := d.getProjectWithSubpath(r); project != nil {
return project.HTTPSOnly
}
@@ -166,7 +166,7 @@ func (d *D) IsAccessControlEnabled(r *http.Request) bool {
}
// Check projects served under the group domain, including the default one
- if project, _ := d.getProject(r); project != nil {
+ if project, _, _ := d.getProjectWithSubpath(r); project != nil {
return project.AccessControl
}
@@ -186,7 +186,7 @@ func (d *D) IsNamespaceProject(r *http.Request) bool {
}
// Check projects served under the group domain, including the default one
- if project, _ := d.getProject(r); project != nil {
+ if project, _, _ := d.getProjectWithSubpath(r); project != nil {
return project.NamespaceProject
}
@@ -203,9 +203,7 @@ func (d *D) GetID(r *http.Request) uint64 {
return d.config.ID
}
- project, _ := d.getProject(r)
-
- if project != nil {
+ if project, _, _ := d.getProjectWithSubpath(r); project != nil {
return project.ID
}
@@ -222,9 +220,7 @@ func (d *D) HasProject(r *http.Request) bool {
return true
}
- project, _ := d.getProject(r)
-
- if project != nil {
+ if project, _, _ := d.getProjectWithSubpath(r); project != nil {
return true
}
@@ -337,20 +333,18 @@ func (d *D) tryNotFound(w http.ResponseWriter, r *http.Request, projectName stri
return nil
}
-func (d *D) tryFile(w http.ResponseWriter, r *http.Request, projectName, pathSuffix string, subPath ...string) error {
+func (d *D) tryFile(w http.ResponseWriter, r *http.Request, projectName string, subPath ...string) error {
fullPath, err := d.resolvePath(projectName, subPath...)
-
if locationError, _ := err.(*locationDirectoryError); locationError != nil {
if endsWithSlash(r.URL.Path) {
fullPath, err = d.resolvePath(projectName, filepath.Join(subPath...), "index.html")
} else {
+ // Concat Host with URL.Path
redirectPath := "//" + r.Host + "/"
- if pathSuffix != "" {
- redirectPath += pathSuffix + "/"
- }
- if locationError.RelativePath != "" {
- redirectPath += strings.TrimPrefix(locationError.RelativePath, "/") + "/"
- }
+ redirectPath += strings.TrimPrefix(r.URL.Path, "/")
+
+ // Ensure that there's always "/" at end
+ redirectPath = strings.TrimSuffix(redirectPath, "/") + "/"
http.Redirect(w, r, redirectPath, 302)
return nil
}
@@ -364,16 +358,13 @@ func (d *D) tryFile(w http.ResponseWriter, r *http.Request, projectName, pathSuf
}
func (d *D) serveFileFromGroup(w http.ResponseWriter, r *http.Request) bool {
- // The Path always contains "/" at the beginning
- split := strings.SplitN(r.URL.Path, "/", 3)
-
- // Try to serve file for http://group.example.com/subpath/... => /group/subpath/...
- if len(split) >= 2 && d.tryFile(w, r, split[1], split[1], split[2:]...) == nil {
+ project, projectName, subPath := d.getProjectWithSubpath(r)
+ if project == nil {
+ httperrors.Serve404(w)
return true
}
- // Try to serve file for http://group.example.com/... => /group/group.example.com/...
- if r.Host != "" && d.tryFile(w, r, strings.ToLower(r.Host), "", r.URL.Path) == nil {
+ if d.tryFile(w, r, projectName, subPath) == nil {
return true
}
@@ -382,25 +373,24 @@ func (d *D) serveFileFromGroup(w http.ResponseWriter, r *http.Request) bool {
func (d *D) serveNotFoundFromGroup(w http.ResponseWriter, r *http.Request) {
// The Path always contains "/" at the beginning
- split := strings.SplitN(r.URL.Path, "/", 3)
-
- // Try serving not found page for http://group.example.com/subpath/ => /group/subpath/404.html
- if len(split) >= 2 && d.tryNotFound(w, r, split[1]) == nil {
+ project, projectName, _ := d.getProjectWithSubpath(r)
+ if project == nil {
+ httperrors.Serve404(w)
return
}
- // Try serving not found page for http://group.example.com/ => /group/group.example.com/404.html
- if r.Host != "" && d.tryNotFound(w, r, strings.ToLower(r.Host)) == nil {
+ // Try serving custom not-found page
+ if d.tryNotFound(w, r, projectName) == nil {
return
}
- // Serve generic not found
+ // Generic 404
httperrors.Serve404(w)
}
func (d *D) serveFileFromConfig(w http.ResponseWriter, r *http.Request) bool {
// Try to serve file for http://host/... => /group/project/...
- if d.tryFile(w, r, d.projectName, "", r.URL.Path) == nil {
+ if d.tryFile(w, r, d.projectName, r.URL.Path) == nil {
return true
}
diff --git a/internal/domain/domain_test.go b/internal/domain/domain_test.go
index 4c08aee5..de780197 100644
--- a/internal/domain/domain_test.go
+++ b/internal/domain/domain_test.go
@@ -31,6 +31,12 @@ func TestGroupServeHTTP(t *testing.T) {
testGroup := &D{
group: "group",
projectName: "",
+ projects: map[string]*project{
+ "group.test.io": &project{},
+ "group.gitlab-example.com": &project{},
+ "project": &project{},
+ "project2": &project{},
+ },
}
assert.HTTPBodyContains(t, serveFileOrNotFound(testGroup), "GET", "http://group.test.io/", nil, "main-dir")
@@ -205,6 +211,12 @@ func TestGroupServeHTTPGzip(t *testing.T) {
testGroup := &D{
group: "group",
projectName: "",
+ projects: map[string]*project{
+ "group.test.io": &project{},
+ "group.gitlab-example.com": &project{},
+ "project": &project{},
+ "project2": &project{},
+ },
}
testSet := []struct {
@@ -268,15 +280,24 @@ func TestGroup404ServeHTTP(t *testing.T) {
testGroup := &D{
group: "group.404",
projectName: "",
+ projects: map[string]*project{
+ "domain.404": &project{},
+ "group.404.test.io": &project{},
+ "project.404": &project{},
+ "project.404.symlink": &project{},
+ "project.no.404": &project{},
+ },
}
testHTTP404(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/project.404/not/existing-file", nil, "Custom 404 project page")
testHTTP404(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/project.404/", nil, "Custom 404 project page")
- testHTTP404(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/project.no.404/not/existing-file", nil, "Custom 404 group page")
testHTTP404(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/not/existing-file", nil, "Custom 404 group page")
testHTTP404(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/not-existing-file", nil, "Custom 404 group page")
testHTTP404(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/", nil, "Custom 404 group page")
assert.HTTPBodyNotContains(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/project.404.symlink/not/existing-file", nil, "Custom 404 project page")
+
+ // Ensure the namespace project's custom 404.html is not used by projects
+ testHTTP404(t, serveFileOrNotFound(testGroup), "GET", "http://group.404.test.io/project.no.404/not/existing-file", nil, "The page you're looking for could not be found.")
}
func TestDomain404ServeHTTP(t *testing.T) {
@@ -350,7 +371,12 @@ func TestDomainCertificate(t *testing.T) {
}
func TestCacheControlHeaders(t *testing.T) {
- testGroup := &D{group: "group"}
+ testGroup := &D{
+ group: "group",
+ projects: map[string]*project{
+ "group.test.io": &project{},
+ },
+ }
w := httptest.NewRecorder()
req, err := http.NewRequest("GET", "http://group.test.io/", nil)
require.NoError(t, err)