mirror of
https://github.com/gin-gonic/gin.git
synced 2025-10-16 05:16:35 +08:00
Merge 7010af371d4b01e29ce4b1bf06afbab2f7955069 into 61fae4997db3dc0011e9015f4f69f57c81e9ce4a
This commit is contained in:
commit
27a633365e
27
function.go
Normal file
27
function.go
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
package gin
|
||||||
|
|
||||||
|
import (
|
||||||
|
"reflect"
|
||||||
|
"runtime"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Function struct {
|
||||||
|
Name string
|
||||||
|
File string
|
||||||
|
Line int
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseFunction(f interface{}) Function {
|
||||||
|
ptr := reflect.ValueOf(f).Pointer()
|
||||||
|
fu := runtime.FuncForPC(ptr)
|
||||||
|
file, line := fu.FileLine(ptr)
|
||||||
|
return Function{
|
||||||
|
Name: fu.Name(),
|
||||||
|
File: file,
|
||||||
|
Line: line,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func nameOfFunction(f interface{}) string {
|
||||||
|
return parseFunction(f).Name
|
||||||
|
}
|
23
function_test.go
Normal file
23
function_test.go
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
package gin
|
||||||
|
|
||||||
|
import (
|
||||||
|
"path/filepath"
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
)
|
||||||
|
|
||||||
|
func someFunction() {
|
||||||
|
// this empty function is used by TestFunctionName()
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestParseFunction(t *testing.T) {
|
||||||
|
f := parseFunction(someFunction)
|
||||||
|
assert.Equal(t, "github.com/gin-gonic/gin.someFunction", f.Name)
|
||||||
|
assert.Equal(t, "function_test.go", filepath.Base(f.File))
|
||||||
|
assert.Equal(t, 12, f.Line)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestFunctionName(t *testing.T) {
|
||||||
|
assert.Equal(t, nameOfFunction(someFunction), "github.com/gin-gonic/gin.someFunction")
|
||||||
|
}
|
7
gin.go
7
gin.go
@ -38,6 +38,8 @@ type (
|
|||||||
Method string
|
Method string
|
||||||
Path string
|
Path string
|
||||||
Handler string
|
Handler string
|
||||||
|
File string
|
||||||
|
Line int
|
||||||
}
|
}
|
||||||
|
|
||||||
// Engine is the framework's instance, it contains the muxer, middleware and configuration settings.
|
// Engine is the framework's instance, it contains the muxer, middleware and configuration settings.
|
||||||
@ -213,10 +215,13 @@ func (engine *Engine) Routes() (routes RoutesInfo) {
|
|||||||
func iterate(path, method string, routes RoutesInfo, root *node) RoutesInfo {
|
func iterate(path, method string, routes RoutesInfo, root *node) RoutesInfo {
|
||||||
path += root.path
|
path += root.path
|
||||||
if len(root.handlers) > 0 {
|
if len(root.handlers) > 0 {
|
||||||
|
funcInfo := parseFunction(root.handlers.Last())
|
||||||
routes = append(routes, RouteInfo{
|
routes = append(routes, RouteInfo{
|
||||||
Method: method,
|
Method: method,
|
||||||
Path: path,
|
Path: path,
|
||||||
Handler: nameOfFunction(root.handlers.Last()),
|
Handler: funcInfo.Name,
|
||||||
|
File: funcInfo.File,
|
||||||
|
Line: funcInfo.Line,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
for _, child := range root.children {
|
for _, child := range root.children {
|
||||||
|
40
gin_test.go
40
gin_test.go
@ -5,6 +5,7 @@
|
|||||||
package gin
|
package gin
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"path/filepath"
|
||||||
"reflect"
|
"reflect"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
@ -214,31 +215,20 @@ func TestListOfRoutes(t *testing.T) {
|
|||||||
list := router.Routes()
|
list := router.Routes()
|
||||||
|
|
||||||
assert.Len(t, list, 7)
|
assert.Len(t, list, 7)
|
||||||
assert.Contains(t, list, RouteInfo{
|
assertRoute(t, list, "GET", "/favicon.ico", "github.com/gin-gonic/gin.handler_test1", "gin_test.go")
|
||||||
Method: "GET",
|
assertRoute(t, list, "GET", "/", "github.com/gin-gonic/gin.handler_test1", "gin_test.go")
|
||||||
Path: "/favicon.ico",
|
assertRoute(t, list, "GET", "/users/", "github.com/gin-gonic/gin.handler_test2", "gin_test.go")
|
||||||
Handler: "github.com/gin-gonic/gin.handler_test1",
|
assertRoute(t, list, "GET", "/users/:id", "github.com/gin-gonic/gin.handler_test1", "gin_test.go")
|
||||||
})
|
assertRoute(t, list, "POST", "/users/:id", "github.com/gin-gonic/gin.handler_test2", "gin_test.go")
|
||||||
assert.Contains(t, list, RouteInfo{
|
}
|
||||||
Method: "GET",
|
|
||||||
Path: "/",
|
func assertRoute(t *testing.T, list RoutesInfo, method, path, handler, filename string) {
|
||||||
Handler: "github.com/gin-gonic/gin.handler_test1",
|
for _, r := range list {
|
||||||
})
|
if r.Method == method && r.Path == path && r.Handler == handler && filepath.Base(r.File) == filename {
|
||||||
assert.Contains(t, list, RouteInfo{
|
return
|
||||||
Method: "GET",
|
}
|
||||||
Path: "/users/",
|
}
|
||||||
Handler: "github.com/gin-gonic/gin.handler_test2",
|
t.Fatalf("Routes info doesn't include route information: [%s] %s: %s at %s\n%v", method, path, handler, filename, list)
|
||||||
})
|
|
||||||
assert.Contains(t, list, RouteInfo{
|
|
||||||
Method: "GET",
|
|
||||||
Path: "/users/:id",
|
|
||||||
Handler: "github.com/gin-gonic/gin.handler_test1",
|
|
||||||
})
|
|
||||||
assert.Contains(t, list, RouteInfo{
|
|
||||||
Method: "POST",
|
|
||||||
Path: "/users/:id",
|
|
||||||
Handler: "github.com/gin-gonic/gin.handler_test2",
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func handler_test1(c *Context) {}
|
func handler_test1(c *Context) {}
|
||||||
|
5
utils.go
5
utils.go
@ -10,7 +10,6 @@ import (
|
|||||||
"os"
|
"os"
|
||||||
"path"
|
"path"
|
||||||
"reflect"
|
"reflect"
|
||||||
"runtime"
|
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -114,10 +113,6 @@ func lastChar(str string) uint8 {
|
|||||||
return str[size-1]
|
return str[size-1]
|
||||||
}
|
}
|
||||||
|
|
||||||
func nameOfFunction(f interface{}) string {
|
|
||||||
return runtime.FuncForPC(reflect.ValueOf(f).Pointer()).Name()
|
|
||||||
}
|
|
||||||
|
|
||||||
func joinPaths(absolutePath, relativePath string) string {
|
func joinPaths(absolutePath, relativePath string) string {
|
||||||
if len(relativePath) == 0 {
|
if len(relativePath) == 0 {
|
||||||
return absolutePath
|
return absolutePath
|
||||||
|
@ -77,14 +77,6 @@ func TestFilterFlags(t *testing.T) {
|
|||||||
assert.Equal(t, result, "text/html")
|
assert.Equal(t, result, "text/html")
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestFunctionName(t *testing.T) {
|
|
||||||
assert.Equal(t, nameOfFunction(somefunction), "github.com/gin-gonic/gin.somefunction")
|
|
||||||
}
|
|
||||||
|
|
||||||
func somefunction() {
|
|
||||||
// this empty function is used by TestFunctionName()
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestJoinPaths(t *testing.T) {
|
func TestJoinPaths(t *testing.T) {
|
||||||
assert.Equal(t, joinPaths("", ""), "")
|
assert.Equal(t, joinPaths("", ""), "")
|
||||||
assert.Equal(t, joinPaths("", "/"), "/")
|
assert.Equal(t, joinPaths("", "/"), "/")
|
||||||
|
Loading…
x
Reference in New Issue
Block a user