func (s *server) authHandler(ctx context.Context, w http.ResponseWriter, r *http.Request, next func(ctx context.Context, w http.ResponseWriter, r *http.Request)) { log := MustFromLogContext(ctx) idt, err := s.getIdentityFromReq(r) if err != nil { log.Error(err) http.Error(w, "", http.StatusUnauthorized) return } p := getPathFromReq(r) // already sanitized if !isUnderHome(p, idt) { // TODO use here share service log.Warnf("%s cannot access %s", *idt, p) http.Error(w, "", http.StatusForbidden) return } if p == getHome(idt) { http.Error(w, "", http.StatusMethodNotAllowed) return } log.Infof("path is %s", p) ctx = authlib.NewContext(ctx, idt) ctx = lib.NewContext(ctx, p) ctx = authlib.NewTokenContext(ctx, s.getTokenFromReq(r)) next(ctx, w, r) }
// authHandler validates the access token sent in the Cookie or if not present sends // a the Basic Auth params to the auth service to authenticate the request. func (s *server) authHandler(ctx context.Context, w http.ResponseWriter, r *http.Request, next func(ctx context.Context, w http.ResponseWriter, r *http.Request)) { logger := MustFromLogContext(ctx) idt, err := getIdentityFromReq(r, s.p.sharedSecret) if err == nil { logger.Info(idt) ctx = authlib.NewContext(ctx, idt) ctx = authlib.NewTokenContext(ctx, getTokenFromReq(r)) next(ctx, w, r) } else { // Authenticate against auth service // if basic credentials are found user, pass, ok := r.BasicAuth() if !ok { logger.Error("no credentials found in request") w.Header().Set("WWW-Authenticate", "Basic Realm='ClawIO credentials'") http.Error(w, "", http.StatusUnauthorized) return } con, err := getConnection(s.p.authServer) if err != nil { logger.Error(err) http.Error(w, "", http.StatusInternalServerError) return } defer con.Close() logger.Infof("connected to %s", s.p.authServer) client := authpb.NewAuthClient(con) in := &authpb.AuthRequest{} in.Username = user in.Password = pass res, err := client.Authenticate(ctx, in) if err != nil { logger.Error(err) if grpc.Code(err) == codes.Unauthenticated { w.Header().Set("WWW-Authenticate", "Basic Realm='ClawIO credentials'") http.Error(w, "", http.StatusUnauthorized) return } http.Error(w, "", http.StatusInternalServerError) return } logger.Infof("basic auth successful for username %s", user) idt, err := authlib.ParseToken(res.Token, s.p.sharedSecret) if err != nil { logger.Error(err) http.Error(w, "", http.StatusInternalServerError) return } logger.Info(idt) cookie := &http.Cookie{} cookie.Name = "OC_SessionPassphrase" cookie.Value = res.Token http.SetCookie(w, cookie) // token added to the request because when proxied // no all servers will handle basic auth, but all will handle // the access token r.Header.Set("Authorization", "Bearer "+res.Token) ctx = authlib.NewContext(ctx, idt) ctx = authlib.NewTokenContext(ctx, res.Token) next(ctx, w, r) } }