package snap import ( "fmt" "io" "io/ioutil" "net/http" "git.twelvetwelve.org/library/core/log" "github.com/gorilla/mux" ) type ServiceStatus struct { Message string } type ServiceResponse struct { Code int Message []byte } func (s *ServiceResponse) WriteResponse(w http.ResponseWriter) { fmt.Printf("Response: %d/%s\n", s.Code, s.Message) w.WriteHeader(s.Code) w.Write(s.Message) } func (s *Server) serviceWrapper(handle func(c *ServiceRequest) *ServiceResponse) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { if s.debug { log.Debugf("request: %+v\n", r.RequestURI) } c := &ServiceRequest{ r: r, } if s.auth != nil { if rec, code := s.auth.DoAuth(w, r); code == http.StatusOK { c.auth = rec } } resp := handle(c) // discard the rest of the body content io.Copy(ioutil.Discard, r.Body) defer r.Body.Close() resp.WriteResponse(w) } } func (s *Server) serviceWrapperAuthenticated(handle func(c *ServiceRequest) *ServiceResponse) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { if s.debug { log.Debugf("request: %+v\n", r.RequestURI) } // cleanup content of anything sent to us defer func() { io.Copy(ioutil.Discard, r.Body) r.Body.Close() }() if s.auth == nil { resp := ServiceResponse{ Code: http.StatusForbidden, Message: []byte("Not Authenticated"), } resp.WriteResponse(w) return } rec, code := s.auth.DoAuth(w, r) switch code { case http.StatusOK: c := &ServiceRequest{ r: r, auth: rec, } resp := handle(c) resp.WriteResponse(w) return case http.StatusUnauthorized: resp := ServiceResponse{ Code: http.StatusForbidden, Message: []byte("Not Authenticated"), } resp.WriteResponse(w) return default: resp := ServiceResponse{ Code: code, Message: []byte(http.StatusText(code)), } resp.WriteResponse(w) return } } } func (s *Server) HandleServiceFunc(path string, f func(c *ServiceRequest) *ServiceResponse) *mux.Route { return s.router.HandleFunc(path, s.serviceWrapper(f)) } func (s *Server) HandleServiceFuncWithAuth(path string, f func(c *ServiceRequest) *ServiceResponse) *mux.Route { return s.router.HandleFunc(path, s.serviceWrapperAuthenticated(f)) }