Repository: gobuffalo/buffalo
Pull request #1961 (2020-04-14 17:07:22)

v0.16.5


Patch:
diff --git a/genny/assets/webpack/webpack-packr.go b/genny/assets/webpack/webpack-packr.go
new file mode 100644
index 00000000..7370ca82
--- /dev/null
+++ b/genny/assets/webpack/webpack-packr.go
@@ -0,0 +1,8 @@
+// +build !skippackr
+// Code generated by github.com/gobuffalo/packr/v2. DO NOT EDIT.
+
+// You can use the "packr clean" command to clean up this,
+// and any other packr generated files.
+package webpack
+
+import _ "github.com/gobuffalo/buffalo/packrd"
diff --git a/genny/build/build-packr.go b/genny/build/build-packr.go
new file mode 100644
index 00000000..9a999f39
--- /dev/null
+++ b/genny/build/build-packr.go
@@ -0,0 +1,8 @@
+// +build !skippackr
+// Code generated by github.com/gobuffalo/packr/v2. DO NOT EDIT.
+
+// You can use the "packr clean" command to clean up this,
+// and any other packr generated files.
+package build
+
+import _ "github.com/gobuffalo/buffalo/packrd"
diff --git a/genny/newapp/api/templates/actions/app.go.tmpl b/genny/newapp/api/templates/actions/app.go.tmpl
index 7b3087e3..78e68155 100644
--- a/genny/newapp/api/templates/actions/app.go.tmpl
+++ b/genny/newapp/api/templates/actions/app.go.tmpl
@@ -9,7 +9,7 @@ import (
 
   {{ if .opts.App.WithPop }}
   "{{.opts.App.ModelsPkg}}"
-  "github.com/gobuffalo/buffalo-pop/pop/v2/popmw"
+  "github.com/gobuffalo/buffalo-pop/v2/pop/popmw"
   {{ end -}}
 
   "github.com/rs/cors"
diff --git a/packrd/packed-packr.go b/packrd/packed-packr.go
index 84dfe826..d37f3fe7 100644
--- a/packrd/packed-packr.go
+++ b/packrd/packed-packr.go
@@ -33,7 +33,7 @@ var _ = func() error {
 		"37c2dc1a1f60c5e3d5255a61cf48ad1a": "1f8b08000000000000ff2ccdb10dc3201046e13a37c52f2a68f00caed266058c023939e690392ac4ee511257affaf46a887bc84fe4939336223eaa9c0a4b80c9acafbef928c79265eb2985b72c570dddcc18f052b5f9b556bf466529edb167cc69c811a55e22b8b05a8741c025fdfdb7b2e10fbed83a47933e010000fffff34f28648b000000",
 		"3baa9872a06bb993286ec8aa69b4f41f": "1f8b08000000000000ff5490cf4ec3300c87ef3cc54f968640a2aae04ad20b4fe22d5e172d69a6381b428877476bba35bbe49f3ffbb3639cbf601758d5524edf343c01eddb2e852ebaeefd638e006663b14f192fc7374451e551f4157ec23eb01ef08b4de51a32ea381337bc851e651c2417cc6b774d3f623310720ab2c468cdab82a8635b0c30db73296942f93989a57aa1fb3021a9101c17ee9cd7e8ef520267cf5de0ad044b5f33d796058c9e78aad4c13b2793a592cf42c373f151f4d3f457e0a195beea9b597be72febffe0efd6fb7a5e9065fb0f0000ffff829b6c549e010000",
 		"42ef67a69104cc24dbb29e2ddffdf564": "1f8b08000000000000ffbc544f6b1b3f10bde7530c22fee14064c32f3db9eb2d213625d006d386dcb5d6d82ba295965939ae2bf4dd8bf68fbd9bbabeb5975d09cd8cde7b9a3789546fb0d6a2aae6ac3cf00f5064fc7f965e0124f95d7720b9325a19e499b6eb57967a3fb1a5ab265fad443df94c765786904cf3bb3aaf5771a3ad709cd43677754d80643407adccebb31d1bdc77859e4481936f58d91dad31849570f9f8e6167c5d66062c730632677849aa107460e1063c8c9a8a000f84c2213ce11e86c856644ba410da9b213439c954aab7f4aafd5d254e641a3bc8cda6fef2dcbe21b5ebcc924442d968e37214f29812375cf7587a0f24cc16e1ba84d91c1a4cf7ce5105bc85138338a80d98183579b04561cdf3a144600e7f38d60b4c5c9e7a1fa36a9d56a25a0bad7e2244d15d9ef6eaa191c7c46edff17779fa9fc9aaf2639714ff28644328b3f2707aa28d25180fc57c11f4202afcaecc56630837a00c9c8d58e91d091d42ff891247ddb2af4e71419e77121597358a571c1f4468b535bc50526a6469e4e3fdf5052e13ef63fda1ba21764b3275327d07a8aff1199d5b2cfdaccb9638469dac31f0c53bb0b5393c0c42568244f1b8086176fe498e441f1710ce194b998d65b7109b6006ec45e13e7a6cf4478028951b2268adf657d0ed051965b627804ba9dc6580ff5c41193b9ad82d30299ce005badc4a3603b6587e593e2f8f076b6b368a8a78724f0807bb836a47f8e9446e8195237bf88d5f3baf4edb539325d3ce5ffd29d77a3a99d6132c4eba5e1f4603f1351a87d48cb4d11c4ab15546384be376a5aca941b457ff0a0000ffffc89382642d060000",
-		"4334b0f46d779c32dd8a3ee235a4b42e": "1f8b08000000000000ff84565f6fdb38127fd7a718e8c9361c0ab8470329906bd3e60eae6354bee680a26818716c714b71b82465c730f4dd174349891d20bb0f8664f237ff677e2327abdf728720aba8c9862cd38d231f619201e43b1debf64954d4143b7a6ab75b69a840bb3fe6efde0e4f066cc95718827907d91cae4604a39df4b231b4dba17f5fe00cf4d685d67a32065511b06a3de65906703a81de82201783b8714e3ce858afc941d7b1f0e9f47af395149ab0febdebba7f8cedca912bf8b7ff173f9a43de9b42abe0aaebb237f23e1415f9f0bedae72260089c7dc6546423da188f0edfcfc31928cfa659561470bbfa0e3a401b504124a8d13808071dab1a02c6a8ed2ec093e45bb270a8d123c41a59523a677425b9feace109b5dd816fad804fb895ad897c9a2bdca321d7a08db9c8f6d2278bd7c0ed20be609ce45fee7fddaebee7f34bec3461a573301b02e08427976f9c63d5bd33d218f0d4460c20ad82462b65f0203d721fc120ca52a1a6d628784250b8d51695804dad036b8a358245bf47a8d046f4405b3852ebdf4429b2a2e0a36fd4725ee667c6e6b0f3d4ba30078c951002d8018595911e156ceed770f5013edd3fac58476fb7416903f7d9915a904a813c773e123c4ae71e6126b711fd6c50c62996ac22999b43ac65ecdfe1a08d81d5fd066ab9c7fec2e2e14c27c78b106493aac761fb1639548f815a5f8d0ea75803c8000734660cfa3f11a40934b89dd48f69f708558dd56f54a06d4a2679859edf8e178948c13f969ce9cfda6078642f247cbcd97cbcbbba592e7b8d7308043a8e0593e6208fdc5e2cec8cac508191218eb692cc85eb73f65dc73e23cee31eede82ceb78294bca2c032381c53d7a6e8e4a321b886cdbda8a3b6d32bd68403865c045e3c6bcbe06ab4d3a81fe60ec37b1c2c3647cbf77c9ab1e06706bf70b9e81f9f0bfec87b88ce47101e3488b556bcca91b416b8f0fd26358c08f9fa3dee16cd4cb14e08318666f321577d22a837e54d1bd31b8920d2e20ff754e677c26b8345df76bf024efc5ba69969e3c7e6da44646cd993a8247a53d56298965b91c7321fe17709278ba2c9793e9abf49276e0f1cf1643ecb91b23fa0093ad36e985e7ed3815177acee85bac479965faffaab8c4d8f7c3a07ce03a488c1809fe5bdeaf2eb49e91a1289988ce46bdf82390cd47b7ff761f24e30f5eba0028abfac5beb620217a6943bf23c588854a7c97a6c5491e9ff3a998cc1c39f191acc5849b8eb86fd8d03eb9ae74904f86875a873799e13d2236af56264dda48e2d3bfa7d3d1775e30fd7ee905bfdc6e267991cfe18e1a1cba84c109e231b6de322eeb12db8e45ecc769bcbee02a2683e17668066941db8a9ab412fa8424d2d9f2b8e9009622dc6d36eb52405ec7e8164581cfb271067969e570fda13f0f6f2ecee8f3d5be220c309b598ab319a04da92acba5481b8079fc82c46143a02839cdca0edc3115350d67a90d8960c1797a3e2e60f4e065870acddf3185a22a14093324081af208da6ec937c9ca99ecbb9f1a45cf31af43f2c21e5f5f62fbcc88d36b59c62f9f33c8a4d776493365b9fc36d462d1b30e2fdd6bc89d27d5a64e1906bb2c976b8ee40ea5421f16d048f72344de343ffbc729ffffd567f207e915aaabb5a748f962284f9e58a59b665df657000000ffffdf36aa0e120a0000",
+		"4334b0f46d779c32dd8a3ee235a4b42e": "1f8b08000000000000ff84565f6fdb38127fd7a718e8c9361c0ab8470329906bd3e60eae6354bee680a26818716c714b71b82465c730f4dd174349891d20bb4f92c8dffc9ff98d9cac7ecb1d82aca2261bb24c378e7c84490690ef74acdb27515153ece8a9dd6ea5a102edfe98bf7b3b3c19b0255f6108e61d6473b81a118c76d2cbc6d06e87fe7d8133d05b175aebc9185445c0aaf5986719c0e9047a0b825c0ce2c639f1a063bd26075dc7c2a7d3ebcd575268c2faf7aeebfe31b62b47aed8ffabe08723d71cf2de145a05575d97bd91f7a1a8c887f7d53e170143e0ec33a6221bd1c67874f87e1ece407936cdb2a280dbd577d001da800a22418dc64138e858d51030466d77019e24df9285438d1e21d6c892d239a32bc9f5670d4fa8ed0e7c6b057cc2ad6c4de4d35ce11e0db9066dcc45b6973e59bc066e07f105e324ff72ffeb76f53d9f5f62a7092b9d83d91000273cb97ce31cabee9d91c680a73662006915345a298307e991fb080651960a35b546c11382c2adb6a8046c6a1d5853ac112cfa3d428536a207dac2915aff264a9115051f7da396f3323f3336879da7d6853960ac8410c00e28ac8cf4a86073bf86ab0ff0e9fe61c53a7abb0d4a1bb8cf8ed482540ae4b9f391e0513af70833b98de86783324eb16415c9dc1c622d63ff0e076d0cacee3750cb3df617160f673a395e84209b543d0edbb7c8a17a0cd4fa6a7438c51a400638a03163d0ff89204da0c1eda47e4cbb47a86aac7ea3026d5332c92bf4fc76bc48440afeb1e44c7fd606c3237b21e1e3cde6e3ddd5cd72d96b9c4320d0712c98340779e4f662616764850a8c0c71b495642e5c9fb3ef3af619711ef768476759c74b5952661918092ceed173735492d94064dbd656dc6993e94503c229032e1a37e6f535586dd209f40763bf89151e26e3fbbd4b5ef530805bbb5ff00ccc87efb21fe23292c7058c232d56ad31a76e04ad3d3e488f61013f7e8e7a87b3512f53800f6298bdc954dc49ab0cfa5145f7c6e04a36b880fcd7399df199e0d274ddafc193bc17eba6597af2f8b5911a193567ea081e95f658a52496e572cc85f85fc049e2e9b25c4ea6afd24bda81c73f5b0cb1e76e8ce8034cb6daa4179eb7e3545ce839a36fb11e6596e9fb557189b1ef8741f9c07590183112fcb7bc5f5d683d23435132119d8d7af147209b8f6effed3e48c61fbc74015056f58b7d6d4142f4d2867e478a110b95f82e4d8b933c3ee75331993972e223598b09371d71dfb0a17d725de9209f0c0fb50e6f32c37b446c5ead4c9ab491c4a77f4fa7a3efbc60fafdd20b7eb9dd4cf2229fc31d353874098313c4636cbd655cd625b61d8bd88fd3787dc1554c06c3edd00cd282b615356925f40949a4b3e571d3012c45b8db6cd6a580bc8ed12d8a029f65e30cf2d2cae1fa437f1ede5c9cd1e7ab7d45186036b3146733409b5255964b913600f3f80589c3864051729a951db8632a6a1ace521b12c182f3f47c5cc0e8c1cb0e159aff630a4555281266481034e411b4dd926f929533d9777f358a9e635e87e4853dbebec4f69911a7d7b28c7f3e679049afed9266ca72f96da8c5a2671d5ebad7903b4faa4d9d320c76592ed71cc91d4a853e2ca091ee4788bc697ef68f53feffabcfe40fd22b54576b4f91f2c5509e3cb14a37cdbaecaf000000ffff4ca8780e120a0000",
 		"47cdc99cfd7800b23c57b35568e02598": "1f8b08000000000000ff8c535d6f2b35107df7af18dd20f1c2eea64208a9a848a50905419b28dcb6b74fc8b167774dbc33c61ff44651fe3bb2779380e04a5779f0c66766ceccf19919bcef4d001340c2906c345588b24358b0daa16f8d4590a4c1e39fc9780cf0fdcd04c1d5b7f5fc1b31833e4617ae9b46b30ab52e58ad7868903a43d8a480be4b4663bea8cc203b6c0a51e1a9b6c958dd881f37ab07e8789bda565a6ea6f3fa70a8d9c5503fa30f86e9780419a0a4a01762f9f80cf7abababab87d5e2e9d725304d57ebcdeac36b69ecba699ce78ffbba632ba9abd977426c9e1e61d869e3a172f0c5fd6a7dfbfea72678d59ce86e9dabd752ed6487eb5d773c8a97d5e697c5cf9bcf0b16878369e102be98d8bfe0d649b583ea7814338859f237632d28a97a84d823901bc05088d25a0811dd5790c86208e0c6daf51f8109542fa9c3206e178b7f03f5ffb1be4a4f853287efa5a7dab2da415d14c8ffcf8c55455c39cf9dc710c4e1803660c9cc91ff6ced3f81a44bdce54bcce08eddbe0c75cff0c03a590c3048322d8618c4dd6afd0a1dd703ebe9385f85344c87984dda687401b6d8b2c7f1e50d75c5928add3e7f074e5e210486d8cb086f089ae9cb0884a8213278ac34bf9165a9b37b86a47a312b154e29538549db29ddd05fd21a2d2302270fa712a8c1ca3dfa224cc790873861a2e85c4ffa4e1e1e9b862aef55340a2a86666ba891ce89d1f6d23a435872a4db81d47a54799c7f2b43ff294cc94aa18fa6354a460ce2ecd3c2204659abaaf53cdc4c5b7326873abfd413291e06a458944a545e6d6b48fa3d188277ceb34e2a1aa6777954bc16331877ecf7e5e3f3cd05cec57e30a44b815c3e32ccebf2cb3a9b084a126c11022241ee0838c560f4e87ec514a521f465836f178bcdcd942dc4f2c37af5db12be9ecfe79f6c79309d97b98fb3577c22caf6b80c947bbf7b585c141893f0bbcb8364183fa2badcfc1d0000ffffc85e53a620050000",
 		"4e577aceb26efd4aa3e9ef3ab5ae5884": "1f8b08000000000000ff9c55df8be336107ef75f311504649a53ee36f4a1ee65e176cb9642f70877d7f6611b0ec5961d114b32929c0b2cf9dfcb48b2e3dcfe80f625966646df37f34933e978b9e78d00c5a5ce32a93a633dd00c80d4ca13fcb6a6095fe3d267218ea20c6b2f952019ae1ae977fd9695462d14b7fb2df7c22d1a2b6b1f7fc977418dd9f675cd5bb318beb6d7110ee02b90f7b31598ce3bb68ef9adf70dccae17fc7bf787d24ba35d74a3133db2061abc7f4bbf5b9b2e8747985dbf98014a601787ab9773ec4cb738fc14fc23f3bda9447b410ca7c8f22485df5001376631cd3fba9ea2e45956f7ba04a9a5a7393c667e0ec25a2856802ab135b74ed0b0fc7477bb5c2e7f9e47d46d2fdbea8b540201f30c30133cf8c30ab46ce1310300a895676b2bb56f3515d662d829034857c03e0b7f8330743084ddefba3678fc2f619d34ba98f0251352ce0301265080c7cd29cf4ea9187c63a118006e1b87c518c73ed8c66500076ec158d948cd5b34c1c3c6792b759301d4c6829ce3213c63b96e444488e5c83ab8562b206fde9064844bb415f0ae13baa203ec23023cbcdd9c02ae7b903fbe2b368cb13c9de6e914fa0ab949d6ad157c1fd6a7249aaca1159a625c8e29bc3b2785f6691239dec2db737eb176585d643a829f0bb80fba059315beb73a5197a84648f01de6e7be495feea00c04aff641c99d00a26463b917a408c8691778ce6f39461ee2fda6c80e5f4ebaf2101e833c777b3207e2c30f777b97e22f147a0fcb5180d634ec8e7bde52a28d07a14ddfecb0a05e09ed1d74dc3951813710b0f38934a1f43059d847f1edd6682f8e3e503c5c6df2a7b4d77035d29683ec217c596c26b8a9c722f2a75e0f90732847d427ed34ad24b553c4ab44cdfbd68f327c1d9b184728fbc398fd9afb1d2569d090fc97e7d09fe77c9675a823a9a4aa91ecd628c57575e64aef7efaea4b55b1cfbe921a426786e5d4617a3f7a4cefa72e4c7070096ba76262044af93f043c8db3e3f2d18573e314abe979a07ee44ab02fd2b782e630bb86c3309adc3f9acce162a2d13ccca6575a258eada13302ebd61cc75bec4c87cfef3e0448a36fcc91867f13b452c2bbae5083cf615bb0c5649fcf41853f11f6ebcd4b937ad4a5a6e48ecb36b643af9105ce5805cc107f32cbe37d6ccd91fdd9d1ff866e7bfd0af4291ba6c3bf010000ffff364833083b080000",
 		"50d3e266d6148ce655a2a7ff90ce1dd7": "1f8b08000000000000ffbc92414b03311085effb2b1e2b85f552a878743d78d793b7b2946967acc126914cc2e2bf9760060b2a56058f99f95ee6bd4cd66bdd49a0e4e2347581bc60447f8859111f303bde4bd6beeb80777099697b9069ea00c024c7e8477899e2dc0480e32ab85a8c28c5f11d79e1a1e9fb732caefbc6d9d5f78f4ee1b4b9c1d9ca806de4970a68f462dd5ab3fe2e0965e10d651b18e23c1c8f28cffc25f1d320c329de2ffecdfb37fb2a2ae917dbfa34e42da527dc5016b50eb1770123722a62a57d652f57edf8167973ea5ff8e373bc060000fffff48dcecee6020000",
diff --git a/route_mappings.go b/route_mappings.go
index 52f66a73..6f663111 100644
--- a/route_mappings.go
+++ b/route_mappings.go
@@ -295,21 +295,35 @@ func (a *App) buildRouteName(p string) string {
 
 	for index, part := range parts {
 
-		if strings.Contains(part, "{") || part == "" {
+		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
 		}
 
-		shouldSingularize := (len(parts) > index+1) && strings.Contains(parts[index+1], "{")
-		if shouldSingularize {
+		if strings.Contains(nextPart, "{") {
 			part = flect.Singularize(part)
 		}
 
-		if parts[index] == "new" || parts[index] == "edit" {
+		if originalPart == "new" || originalPart == "edit" {
 			resultParts = append([]string{part}, resultParts...)
 			continue
 		}
 
-		if index > 0 && strings.Contains(parts[index-1], "}") {
+		if strings.Contains(previousPart, "}") {
 			resultParts = append(resultParts, part)
 			continue
 		}
diff --git a/runtime/version.go b/runtime/version.go
index 5286deb5..d2b7e180 100644
--- a/runtime/version.go
+++ b/runtime/version.go
@@ -1,4 +1,4 @@
 package runtime
 
 // Version is the current version of the buffalo binary
-var Version = "v0.16.4"
+var Version = "v0.16.5"


Test patch:
diff --git a/default_context_test.go b/default_context_test.go
index 72e88920..2823828c 100644
--- a/default_context_test.go
+++ b/default_context_test.go
@@ -60,7 +60,7 @@ func Test_DefaultContext_Redirect_Helper(t *testing.T) {
 			return c.Render(http.StatusOK, render.String(c.Param("bar")))
 		})
 		a.GET("/", func(c Context) error {
-			return c.Redirect(http.StatusPermanentRedirect, "fooPath()", tt.I)
+			return c.Redirect(http.StatusPermanentRedirect, "fooBarPath()", tt.I)
 		})
 		a.GET("/nomap", func(c Context) error {
 			return c.Redirect(http.StatusPermanentRedirect, "rootPath()")
diff --git a/router_test.go b/router_test.go
index 0607f1f9..11fca3f7 100644
--- a/router_test.go
+++ b/router_test.go
@@ -428,6 +428,9 @@ func Test_App_NamedRoutes(t *testing.T) {
 			11. <%= rootPath({"special/":"12=ss"}) %>
 			12. <%= resourcePath({resource_id: 1}) %>
 			13. <%= editResourcePath({resource_id: 1}) %>
+			14. <%= testPath() %>
+			15. <%= testNamePath({name: "myTest"}) %>
+			16. <%= paganoPath({id: 1}) %>
 		`))
 	}
 
@@ -437,6 +440,9 @@ func Test_App_NamedRoutes(t *testing.T) {
 	a.GET("/peeps", sampleHandler).Name("myPeeps")
 	a.Resource("/car", carsResource)
 	a.Resource("/resources", resourcesResource)
+	a.GET("/test", sampleHandler)
+	a.GET("/test/{name}", sampleHandler)
+	a.GET("/pagano/{id}", sampleHandler)
 
 	w := httptest.New(a)
 	res := w.HTML("/").Get()
@@ -454,6 +460,9 @@ func Test_App_NamedRoutes(t *testing.T) {
 	r.Contains(res.Body.String(), "11. /?special%2F=12%3Dss")
 	r.Contains(res.Body.String(), "12. /resources/1")
 	r.Contains(res.Body.String(), "13. /resources/1/edit")
+	r.Contains(res.Body.String(), "14. /test")
+	r.Contains(res.Body.String(), "15. /test/myTest")
+	r.Contains(res.Body.String(), "16. /pagano/1")
 }
 
 func Test_App_NamedRoutes_MissingParameter(t *testing.T) {
@@ -719,9 +728,13 @@ func Test_buildRouteName(t *testing.T) {
 		"/users/{user_id}/children/{child_id}": "userChild",
 		"/users/{user_id}/children/new":        "newUserChildren",
 		"/users/{user_id}/children/{child_id}/build": "userChildBuild",
-		"/admin/planes":                 "adminPlanes",
-		"/admin/planes/{plane_id}":      "adminPlane",
-		"/admin/planes/{plane_id}/edit": "editAdminPlane",
+		"/admin/planes":                         "adminPlanes",
+		"/admin/planes/{plane_id}":              "adminPlane",
+		"/admin/planes/{plane_id}/edit":         "editAdminPlane",
+		"/test":                                 "test",
+		"/tests/{name}":                         "testName",
+		"/tests/{name_id}/cases/{case_id}":      "testNameIdCase",
+		"/tests/{name_id}/cases/{case_id}/edit": "editTestNameIdCase",
 	}
 
 	a := New(Options{})