Skip to content
This repository has been archived by the owner on Feb 24, 2024. It is now read-only.

Application Route Namer #2075

Merged
merged 4 commits into from
Jan 7, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions app.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@ type App struct {
root *App
children []*App
filepaths []string

// Routenamer for the app. This field provides the ability to override the
// base route namer for something more specific to the app.
RouteNamer RouteNamer
}

// Muxer returns the underlying mux router to allow
Expand All @@ -48,6 +52,8 @@ func New(opts Options) *App {
moot: &sync.RWMutex{},
routes: RouteList{},
children: []*App{},

RouteNamer: baseRouteNamer{},
}

dem := a.defaultErrorMiddleware
Expand Down
58 changes: 1 addition & 57 deletions route_mappings.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import (
"strings"

"github.com/gobuffalo/envy"
"github.com/gobuffalo/flect"
"github.com/gobuffalo/flect/name"
"github.com/gorilla/handlers"
)
Expand Down Expand Up @@ -263,7 +262,7 @@ func (a *App) addRoute(method string, url string, h Handler) *RouteInfo {

url = path.Join(a.Prefix, url)
url = a.normalizePath(url)
name := a.buildRouteName(url)
name := a.RouteNamer.NameRoute(url)

hs := funcKey(h)
r := &RouteInfo{
Expand Down Expand Up @@ -291,61 +290,6 @@ func (a *App) addRoute(method string, url string, h Handler) *RouteInfo {
return r
}

//buildRouteName builds a route based on the path passed.
func (a *App) buildRouteName(p string) string {
if p == "/" || p == "" {
return "root"
}

resultParts := []string{}
parts := strings.Split(p, "/")

for index, part := range parts {

originalPart := parts[index]

var previousPart string
if index > 0 {
previousPart = parts[index-1]
}

var nextPart string
if len(parts) > index+1 {
nextPart = parts[index+1]
}

isIdentifierPart := strings.Contains(part, "{") && (strings.Contains(part, flect.Singularize(previousPart)))
isSimplifiedID := part == `{id}`

if isIdentifierPart || isSimplifiedID || part == "" {
continue
}

if strings.Contains(nextPart, "{") {
part = flect.Singularize(part)
}

if originalPart == "new" || originalPart == "edit" {
resultParts = append([]string{part}, resultParts...)
continue
}

if strings.Contains(previousPart, "}") {
resultParts = append(resultParts, part)
continue
}

resultParts = append(resultParts, part)
}

if len(resultParts) == 0 {
return "unnamed"
}

underscore := strings.TrimSpace(strings.Join(resultParts, "_"))
return name.VarCase(underscore)
}

func stripAsset(path string, h http.Handler, a *App) http.Handler {
if path == "" {
return h
Expand Down
74 changes: 74 additions & 0 deletions routenamer.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
package buffalo

import (
"strings"

"github.com/gobuffalo/flect"
"github.com/gobuffalo/flect/name"
)

// RouteNamer is in charge of naming a route from the
// path assigned, this name typically will be used if no
// name is assined with .Name(...).
type RouteNamer interface {
// NameRoute receives the path and returns the name
// for the route.
NameRoute(string) string
}

// BaseRouteNamer is the default route namer used by apps.
type baseRouteNamer struct{}

func (drn baseRouteNamer) NameRoute(p string) string {
if p == "/" || p == "" {
return "root"
}

resultParts := []string{}
parts := strings.Split(p, "/")

for index, part := range parts {

originalPart := parts[index]

var previousPart string
if index > 0 {
previousPart = parts[index-1]
}

var nextPart string
if len(parts) > index+1 {
nextPart = parts[index+1]
}

isIdentifierPart := strings.Contains(part, "{") && (strings.Contains(part, flect.Singularize(previousPart)))
isSimplifiedID := part == `{id}`

if isIdentifierPart || isSimplifiedID || part == "" {
continue
}

if strings.Contains(nextPart, "{") {
part = flect.Singularize(part)
}

if originalPart == "new" || originalPart == "edit" {
resultParts = append([]string{part}, resultParts...)
continue
}

if strings.Contains(previousPart, "}") {
resultParts = append(resultParts, part)
continue
}

resultParts = append(resultParts, part)
}

if len(resultParts) == 0 {
return "unnamed"
}

underscore := strings.TrimSpace(strings.Join(resultParts, "_"))
return name.VarCase(underscore)
}
4 changes: 2 additions & 2 deletions router_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -740,7 +740,7 @@ func Test_buildRouteName(t *testing.T) {
a := New(Options{})

for input, result := range cases {
fResult := a.buildRouteName(input)
fResult := a.RouteNamer.NameRoute(input)
r.Equal(result, fResult, input)
}

Expand All @@ -751,7 +751,7 @@ func Test_buildRouteName(t *testing.T) {
}

for input, result := range cases {
fResult := a.buildRouteName(input)
fResult := a.RouteNamer.NameRoute(input)
r.Equal(result, fResult, input)
}
}
Expand Down