From 74113fad490ccdaa00961c5818eaa107781dfd79 Mon Sep 17 00:00:00 2001 From: Quentin Dufour Date: Fri, 15 Sep 2023 14:32:44 +0200 Subject: [PATCH] WIP auth API --- api.go | 114 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ main.go | 5 +-- 2 files changed, 116 insertions(+), 3 deletions(-) create mode 100644 api.go diff --git a/api.go b/api.go new file mode 100644 index 0000000..1007914 --- /dev/null +++ b/api.go @@ -0,0 +1,114 @@ +package main + +import ( + //"context" + //"errors" + "fmt" + //garage "git.deuxfleurs.fr/garage-sdk/garage-admin-sdk-golang" + "github.com/go-ldap/ldap/v3" + //"github.com/gorilla/mux" + "log" + "net/http" + "strings" +) + +func checkLoginAPI(w http.ResponseWriter, r *http.Request) *LoginStatus { + username, password, ok := r.BasicAuth() + if !ok { + w.Header().Set("WWW-Authenticate", `Basic realm="restricted", charset="UTF-8"`) + http.Error(w, "Unauthorized", http.StatusUnauthorized) + return nil + } + user_dn := buildUserDN(username) + + login_info := &LoginInfo{ + DN: user_dn, + Username: username, + Password: password, + } + + l := ldapOpen(w) + if l == nil { + log.Println(l) + http.Error(w, "Internal server error", http.StatusInternalServerError) + return nil + } + + err := l.Bind(login_info.DN, login_info.Password) + if err != nil { + w.Header().Set("WWW-Authenticate", `Basic realm="restricted", charset="UTF-8"`) + http.Error(w, "Unauthorized", http.StatusUnauthorized) + return nil + } + + loginStatus := &LoginStatus{ + Info: login_info, + conn: l, + } + + requestKind := "(objectClass=organizationalPerson)" + + if strings.EqualFold(login_info.DN, config.AdminAccount) { + requestKind = "(objectclass=*)" + } + searchRequest := ldap.NewSearchRequest( + login_info.DN, + ldap.ScopeBaseObject, ldap.NeverDerefAliases, 0, 0, false, + requestKind, + []string{ + "dn", + "displayname", + "givenname", + "sn", + "mail", + "memberof", + "description", + "garage_s3_access_key", + FIELD_NAME_DIRECTORY_VISIBILITY, + FIELD_NAME_PROFILE_PICTURE, + }, + nil) + + sr, err := l.Search(searchRequest) + if err != nil { + log.Println(err) + http.Error(w, "Internal server error", http.StatusInternalServerError) + return nil + } + + if len(sr.Entries) != 1 { + log.Println(fmt.Sprintf("Unable to find entry for %s", login_info.DN)) + http.Error(w, "Internal server error", http.StatusInternalServerError) + return nil + } + + loginStatus.UserEntry = sr.Entries[0] + + loginStatus.CanAdmin = strings.EqualFold(loginStatus.Info.DN, config.AdminAccount) + loginStatus.CanInvite = false + for _, attr := range loginStatus.UserEntry.Attributes { + if strings.EqualFold(attr.Name, "memberof") { + for _, group := range attr.Values { + if config.GroupCanInvite != "" && strings.EqualFold(group, config.GroupCanInvite) { + loginStatus.CanInvite = true + } + if config.GroupCanAdmin != "" && strings.EqualFold(group, config.GroupCanAdmin) { + loginStatus.CanAdmin = true + } + } + } + } + + return loginStatus +} + +func handleAPIGarageBucket(w http.ResponseWriter, r *http.Request) { + login, s3key, err := checkLoginAndS3(w, r) + if err != nil { + log.Println(err) + return + } + log.Println(login,s3key) + + return +} diff --git a/main.go b/main.go index 92fd2dc..1402ff2 100644 --- a/main.go +++ b/main.go @@ -130,6 +130,8 @@ func main() { r.HandleFunc("/", handleHome) r.HandleFunc("/logout", handleLogout) + r.HandleFunc("/api/unstable/garage/bucket/{b}", handleAPIGarageBucket) + r.HandleFunc("/profile", handleProfile) r.HandleFunc("/passwd", handlePasswd) r.HandleFunc("/picture/{name}", handleDownloadPicture) @@ -198,9 +200,6 @@ func logRequest(handler http.Handler) http.Handler { func checkLogin(w http.ResponseWriter, r *http.Request) *LoginStatus { var login_info *LoginInfo - //@FIXME check authentication header - - session, err := store.Get(r, SESSION_NAME) if err == nil { username, ok := session.Values["login_username"]