diff --git a/mux.go b/mux.go index 94f5ddd9..b5ade933 100644 --- a/mux.go +++ b/mux.go @@ -10,6 +10,7 @@ import ( "net/http" "path" "regexp" + "sort" "github.com/gorilla/context" ) @@ -305,6 +306,17 @@ func (r *Router) walk(walkFn WalkFunc, ancestors []*Route) error { return nil } +type routes []*Route + +func (r routes) Len() int { return len(r) } +func (r routes) Swap(i, j int) { r[i], r[j] = r[j], r[i] } +func (r routes) Less(i, j int) bool { return r[i].GetPriority() > r[j].GetPriority() } + +// SortRoutes sort routes by route priority +func (r *Router) SortRoutes() { + sort.Sort(routes(r.routes)) +} + // ---------------------------------------------------------------------------- // Context // ---------------------------------------------------------------------------- diff --git a/route.go b/route.go index 6c53f9f1..8eb0990a 100644 --- a/route.go +++ b/route.go @@ -35,6 +35,8 @@ type Route struct { name string // Error resulted from building a route. err error + // Priority of this route + priority int buildVarsFunc BuildVarsFunc } @@ -127,6 +129,19 @@ func (r *Route) GetName() string { return r.name } +// Priority ----------------------------------------------------------------------- + +// Priority sets the priority for the route +func (r *Route) Priority(priority int) *Route { + r.priority = priority + return r +} + +// GetPriority returns the priority for the route. +func (r *Route) GetPriority() int { + return r.priority +} + // ---------------------------------------------------------------------------- // Matchers // ---------------------------------------------------------------------------- @@ -342,6 +357,39 @@ func (r *Route) PathPrefix(tpl string) *Route { return r } +// PathStrip ------------------------------------------------------------------ + +// PathStrip returns a regexp for the URL path. +// See Route.Path() for details on the tpl argument. +func (r *Route) PathStrip(tpl string) (*regexp.Regexp, error) { + rr, err := newRouteRegexp(tpl, false, false, false, r.strictSlash) + if err == nil { + return rr.regexp, nil + } else { + return nil, err + } +} + +// PathPrefixStrip ------------------------------------------------------------------ + +// PathPrefixStrip returns a regexp for the URL path prefix. This matches if the given +// template is a prefix of the full URL path. See Route.Path() for details on +// the tpl argument. +// +// Note that it does not treat slashes specially ("/foobar/" will be matched by +// the prefix "/foo") so you may want to use a trailing slash here. +// +// Also note that the setting of Router.StrictSlash() has no effect on routes +// with a PathPrefix matcher. +func (r *Route) PathPrefixStrip(tpl string) (*regexp.Regexp, error) { + rr, err := newRouteRegexp(tpl, false, true, false, r.strictSlash) + if err == nil { + return rr.regexp, nil + } else { + return nil, err + } +} + // Query ---------------------------------------------------------------------- // Queries adds a matcher for URL query values.