@@ -122,7 +122,7 @@ func Run(ctx *cli.Context) { | |||
cwd = ctx.Args()[0] | |||
} | |||
if abspath, err := filepath.Abs(cwd); err == nil { | |||
env.Set(internal.ROOT, abspath) | |||
env.Set(internal.BaseDir, abspath) | |||
} else { | |||
log.Fatalf("Failed to retrieve the directory: %v", err) | |||
} |
@@ -1,19 +0,0 @@ | |||
package rex | |||
import ( | |||
"flag" | |||
"runtime" | |||
) | |||
var ( | |||
debug bool | |||
port int | |||
maxprocs int | |||
) | |||
func configure() { | |||
flag.BoolVar(&debug, "debug", Env.Bool("DEBUG", true), "flag to toggle debug mode") | |||
flag.IntVar(&port, "port", Env.Int("PORT", 5000), "port to run the application server") | |||
flag.IntVar(&maxprocs, "maxprocs", Env.Int("MAXPROCS", runtime.NumCPU()), "maximum cpu processes to run the server") | |||
flag.Parse() | |||
} |
@@ -7,6 +7,7 @@ import ( | |||
"net/http" | |||
"path/filepath" | |||
"github.com/goanywhere/env" | |||
"github.com/goanywhere/rex" | |||
"github.com/goanywhere/rex/livereload" | |||
) | |||
@@ -21,7 +22,7 @@ func Index(w http.ResponseWriter, r *http.Request) { | |||
http.Error(w, err.Error(), http.StatusInternalServerError) | |||
} else { | |||
w.Header().Set("Content-Type", "text/html") | |||
var user = User{Username: rex.Env.String("USER", "guest")} | |||
var user = User{Username: env.String("USER", "guest")} | |||
html.Execute(w, user) | |||
} | |||
} | |||
@@ -84,15 +85,16 @@ func remove(w http.ResponseWriter, r *http.Request) { | |||
} | |||
func main() { | |||
rex.Use(livereload.Middleware) | |||
rex.Get("/", Index) | |||
app := rex.New() | |||
app.Use(livereload.Middleware) | |||
app.Get("/", Index) | |||
api := rex.Group("/v1/") | |||
api := app.Group("/v1/") | |||
api.Use(JSON) | |||
api.Get("/", fetch) | |||
api.Post("/", create) | |||
api.Put("/", update) | |||
api.Delete("/", remove) | |||
rex.Run() | |||
app.Run() | |||
} |
@@ -1,3 +1,3 @@ | |||
package internal | |||
const ROOT = "rex.root" | |||
const BaseDir string = "rex.root" |
@@ -1,60 +0,0 @@ | |||
package internal | |||
import ( | |||
"path" | |||
"github.com/goanywhere/env" | |||
) | |||
type Env struct { | |||
Base string | |||
} | |||
func New(dotenv string) *Env { | |||
env.Load(dotenv) | |||
return &Env{Base: path.Base(dotenv)} | |||
} | |||
func (self *Env) Get(key string) (string, bool) { | |||
return env.Get(key) | |||
} | |||
func (self *Env) Set(key string, value interface{}) error { | |||
return env.Set(key, value) | |||
} | |||
func (self *Env) String(key string, fallback ...string) string { | |||
return env.String(key, fallback...) | |||
} | |||
func (self *Env) Strings(key string, fallback ...[]string) []string { | |||
return env.Strings(key, fallback...) | |||
} | |||
func (self *Env) Int(key string, fallback ...int) int { | |||
return env.Int(key, fallback...) | |||
} | |||
func (self *Env) Int64(key string, fallback ...int64) int64 { | |||
return env.Int64(key, fallback...) | |||
} | |||
func (self *Env) Uint(key string, fallback ...uint) uint { | |||
return env.Uint(key, fallback...) | |||
} | |||
func (self *Env) Uint64(key string, fallback ...uint64) uint64 { | |||
return env.Uint64(key, fallback...) | |||
} | |||
func (self *Env) Bool(key string, fallback ...bool) bool { | |||
return env.Bool(key, fallback...) | |||
} | |||
func (self *Env) Float(key string, fallback ...float64) float64 { | |||
return env.Float(key, fallback...) | |||
} | |||
func (self *Env) Map(spec interface{}) error { | |||
return env.Map(spec) | |||
} |
@@ -1,78 +1,14 @@ | |||
package rex | |||
import ( | |||
"net/http" | |||
"path/filepath" | |||
"path" | |||
"github.com/goanywhere/env" | |||
"github.com/goanywhere/fs" | |||
"github.com/goanywhere/rex/internal" | |||
. "github.com/goanywhere/rex/middleware" | |||
) | |||
var ( | |||
Default = New() | |||
Env *internal.Env | |||
) | |||
// Get is a shortcut for mux.HandleFunc(pattern, handler).Methods("GET"), | |||
// it also fetch the full function name of the handler (with package) to name the route. | |||
func Get(pattern string, handler interface{}) { | |||
Default.Get(pattern, handler) | |||
} | |||
// Head is a shortcut for mux.HandleFunc(pattern, handler).Methods("HEAD") | |||
// it also fetch the full function name of the handler (with package) to name the route. | |||
func Head(pattern string, handler interface{}) { | |||
Default.Head(pattern, handler) | |||
} | |||
// Options is a shortcut for mux.HandleFunc(pattern, handler).Methods("OPTIONS") | |||
// it also fetch the full function name of the handler (with package) to name the route. | |||
// NOTE method OPTIONS is **NOT** cachable, beware of what you are going to do. | |||
func Options(pattern string, handler interface{}) { | |||
Default.Options(pattern, handler) | |||
} | |||
// Post is a shortcut for mux.HandleFunc(pattern, handler).Methods("POST") | |||
// it also fetch the full function name of the handler (with package) to name the route. | |||
func Post(pattern string, handler interface{}) { | |||
Default.Post(pattern, handler) | |||
} | |||
// Put is a shortcut for mux.HandleFunc(pattern, handler).Methods("PUT") | |||
// it also fetch the full function name of the handler (with package) to name the route. | |||
func Put(pattern string, handler interface{}) { | |||
Default.Put(pattern, handler) | |||
} | |||
// Delete is a shortcut for mux.HandleFunc(pattern, handler).Methods("DELETE") | |||
// it also fetch the full function name of the handler (with package) to name the route. | |||
func Delete(pattern string, handler interface{}) { | |||
Default.Delete(pattern, handler) | |||
} | |||
// Group creates a new application group under the given path. | |||
func Group(path string) *Server { | |||
return Default.Group(path) | |||
} | |||
// FileServer registers a handler to serve HTTP (GET|HEAD) requests | |||
// with the contents of file system under the given directory. | |||
func FileServer(prefix, dir string) { | |||
Default.FileServer(prefix, dir) | |||
} | |||
// Use appends middleware module into the serving list, modules will be served in FIFO order. | |||
func Use(module func(http.Handler) http.Handler) { | |||
Default.Use(module) | |||
} | |||
func Run() { | |||
Default.Use(Logger) | |||
Default.Run() | |||
} | |||
func init() { | |||
var basedir = fs.Getcd(2) | |||
Env = internal.New(filepath.Join(basedir, ".env")) | |||
env.Set("basedir", basedir) | |||
env.Load(path.Join(basedir, ".env")) | |||
} |
@@ -1,17 +1,28 @@ | |||
package rex | |||
import ( | |||
"flag" | |||
"fmt" | |||
"log" | |||
"net/http" | |||
"path/filepath" | |||
"reflect" | |||
"runtime" | |||
"sync" | |||
"time" | |||
"github.com/goanywhere/env" | |||
"github.com/gorilla/mux" | |||
) | |||
var ( | |||
debug bool | |||
port int | |||
maxprocs int | |||
once sync.Once | |||
) | |||
type Server struct { | |||
middleware *middleware | |||
mux *mux.Router | |||
@@ -24,9 +35,19 @@ func New() *Server { | |||
middleware: new(middleware), | |||
mux: mux.NewRouter().StrictSlash(true), | |||
} | |||
self.configure() | |||
return self | |||
} | |||
func (self *Server) configure() { | |||
once.Do(func() { | |||
flag.BoolVar(&debug, "debug", env.Bool("DEBUG", true), "flag to toggle debug mode") | |||
flag.IntVar(&port, "port", env.Int("PORT", 5000), "port to run the application server") | |||
flag.IntVar(&maxprocs, "maxprocs", env.Int("MAXPROCS", runtime.NumCPU()), "maximum cpu processes to run the server") | |||
flag.Parse() | |||
}) | |||
} | |||
// build constructs all server/subservers along with their middleware modules chain. | |||
func (self *Server) build() http.Handler { | |||
if !self.ready { | |||
@@ -150,7 +171,6 @@ func (self *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) { | |||
// Run starts the application server to serve incoming requests at the given address. | |||
func (self *Server) Run() { | |||
configure() | |||
runtime.GOMAXPROCS(maxprocs) | |||
go func() { |