security sections are fully functional
This commit is contained in:
@@ -60,18 +60,41 @@ func (h *GitHTTPHandler) ServeGit(w http.ResponseWriter, r *http.Request) {
|
||||
}
|
||||
|
||||
// Authenticate and enforce permission checks.
|
||||
// Priority: user account → deploy key → anonymous (public repos only).
|
||||
var authedUser string
|
||||
user, authed := h.basicAuth(r)
|
||||
if authed {
|
||||
authedUser = user
|
||||
// Push requires write or admin permission.
|
||||
if service == "git-receive-pack" && !HasPermission(h.db, &repo, user, "write") {
|
||||
http.Error(w, "forbidden: you do not have write access to this repository", http.StatusForbidden)
|
||||
return
|
||||
}
|
||||
// Pull on a private repo requires at least read permission.
|
||||
if repo.IsPrivate && !HasPermission(h.db, &repo, user, "read") {
|
||||
http.Error(w, "forbidden: you do not have read access to this repository", http.StatusForbidden)
|
||||
var authedReadOnly bool
|
||||
|
||||
if _, p, hasAuth := r.BasicAuth(); hasAuth {
|
||||
if user, ok := h.basicAuth(r); ok {
|
||||
authedUser = user
|
||||
// User account: enforce member permissions.
|
||||
if service == "git-receive-pack" && !HasPermission(h.db, &repo, user, "write") {
|
||||
http.Error(w, "forbidden: you do not have write access to this repository", http.StatusForbidden)
|
||||
return
|
||||
}
|
||||
if repo.IsPrivate && !HasPermission(h.db, &repo, user, "read") {
|
||||
http.Error(w, "forbidden: you do not have read access to this repository", http.StatusForbidden)
|
||||
return
|
||||
}
|
||||
} else if rdOnly, ok := AuthenticateDeployKey(h.db, repo.ID, p); ok {
|
||||
// Deploy key: the password field carries the raw token; username is ignored.
|
||||
authedUser = "deploy-key"
|
||||
authedReadOnly = rdOnly
|
||||
if service == "git-receive-pack" && rdOnly {
|
||||
http.Error(w, "forbidden: this deploy key is read-only", http.StatusForbidden)
|
||||
return
|
||||
}
|
||||
} else if _, repoID, hasWrite, ok := LookupAccessToken(h.db, p); ok && repoID == repo.ID {
|
||||
// Access token used as git credential (username ignored, password = token).
|
||||
authedUser = "access-token"
|
||||
if service == "git-receive-pack" && !hasWrite {
|
||||
http.Error(w, "forbidden: this access token has read-only scope", http.StatusForbidden)
|
||||
return
|
||||
}
|
||||
} else {
|
||||
// Credentials provided but invalid.
|
||||
w.Header().Set("WWW-Authenticate", `Basic realm="ForgeBucket"`)
|
||||
http.Error(w, "invalid credentials", http.StatusUnauthorized)
|
||||
return
|
||||
}
|
||||
} else if service == "git-receive-pack" || repo.IsPrivate {
|
||||
@@ -79,6 +102,7 @@ func (h *GitHTTPHandler) ServeGit(w http.ResponseWriter, r *http.Request) {
|
||||
http.Error(w, "authentication required", http.StatusUnauthorized)
|
||||
return
|
||||
}
|
||||
_ = authedReadOnly
|
||||
|
||||
// Build PATH_INFO: /{reponame}.git/{suffix}
|
||||
// Strip the /{owner}/{repoGit} prefix from the raw URL path to get the suffix.
|
||||
|
||||
Reference in New Issue
Block a user