func NoTransactionFilter(ctx maze.IContext) error { return TM.NoTransaction(func(DB db.IDb) error { appCtx := ctx.(*AppCtx) appCtx.Store = DB return ctx.Proceed() }) }
func TransactionFilter(ctx maze.IContext) error { return TM.Transaction(func(DB db.IDb) error { appCtx := ctx.(*AppCtx) appCtx.Store = DB p := appCtx.Principal if p != nil { appCtx.Store.SetAttribute(entity.ATTR_USERID, p.UserId) } return ctx.Proceed() }) }
func PingFilter(ctx maze.IContext) error { ctx.GetResponse().Header().Set("Content-Type", "text/html; charset=utf-8") // TODO what happens if this is called right after the user submited a password change // and the reply was not yet delivered/processed app := ctx.(*AppCtx) p := app.Principal // check if version is valid - if the user changed the password the version changes var uid int64 store := app.Store ok, err := store.Query(T.USER).Column(T.USER_C_ID). Where(T.USER_C_ID.Matches(p.UserId).And(T.USER_C_VERSION.Matches(p.Version))). SelectInto(&uid) if !ok { // version is different logger.Debugf("Unable to revalidate the token, because the user no longer exists or it was changed (different version)") http.Error(ctx.GetResponse(), "Unauthorized", http.StatusUnauthorized) return nil } else if err != nil { return err } tokenString, err := serializePrincipal(p) if err != nil { return err } ctx.GetResponse().Write([]byte(tokenString)) return nil }
func AuthenticationFilter(ctx maze.IContext) error { p := deserializePrincipal(ctx.GetRequest()) if p != nil { // for authorizations and business logic ctx.(*AppCtx).Principal = p return ctx.Proceed() } else { logger.Debugf("Unable to proceed: invalid token!") http.Error(ctx.GetResponse(), "Unauthorized", http.StatusUnauthorized) } return nil }
func LoginFilter(ctx maze.IContext) error { ctx.GetResponse().Header().Set("Content-Type", "text/html; charset=utf-8") //logger.Debugf("serving static(): " + ctx.GetRequest().URL.Path) username := ctx.GetRequest().FormValue("username") pass := ctx.GetRequest().FormValue("password") var err error if username != "" && pass != "" { store := ctx.(*AppCtx).Store // usernames are stored in lowercase username = strings.ToLower(username) var user entity.User var ok bool if ok, err = store.Query(T.USER). All(). Inner(T.USER_A_ROLES).Fetch(). Where( db.And(T.USER_C_USERNAME.Matches(username), T.USER_C_PASSWORD.Matches(pass))). SelectTree(&user); ok && err == nil { // role array roles := make([]lov.ERole, len(user.Roles)) for k, v := range user.Roles { roles[k] = v.Kind } tokenString, err := serializePrincipal(&Principal{ *user.Id, *user.Username, roles, *user.Version, }) if err != nil { return err } ctx.GetResponse().Write([]byte(tokenString)) } } return err }
// Limit limits the body of a post, compress response and format eventual errors func Limit(ctx maze.IContext) (err error) { r := ctx.GetRequest() // https only -- redirect in openshift if HttpsOnly && !isHttps(r) { url := "https://" + r.Host + r.RequestURI logger.Debugf("redirecting to %s", url) http.Redirect(ctx.GetResponse(), r, url, http.StatusMovedPermanently) return } /* Very Important: Before compressing the response, the "Content-Type" header must be properly set! */ // encodes only text files var zip bool var ext = filepath.Ext(r.URL.Path) for _, v := range zipexts { if v == ext { zip = true break } } // TODO gzip encoding should occour only after a size threshold if zip && strings.Contains(fmt.Sprint(r.Header["Accept-Encoding"]), "gzip") { appCtx := ctx.(*AppCtx) w := appCtx.Response w.Header().Set("Content-Encoding", "gzip") // Get a Writer from the Pool gz := zippers.Get().(*gzip.Writer) // When done, put the Writer back in to the Pool defer zippers.Put(gz) // We use Reset to set the writer we want to use. gz.Reset(w) defer gz.Close() appCtx.Response = gzipResponseWriter{Writer: gz, ResponseWriter: w} } defer func() { if r := recover(); r != nil { if e, ok := r.(runtime.Error); ok { logger.Errorf("%s\n========== Begin Stack Trace ==========\n%s\n========== End Stack Trace ==========\n", e, debug.Stack()) } err = formatError(ctx.GetResponse(), r.(error)) } }() logger.Debugf("requesting %s", r.URL.Path) r.Body = http.MaxBytesReader(ctx.GetResponse(), r.Body, postLimit) err = ctx.Proceed() if err != nil { err = formatError(ctx.GetResponse(), err) } return err }