gin-gonic / gin

Gin is a HTTP web framework written in Go (Golang). It features a Martini-like API with much better performance -- up to 40 times faster. If you need smashing performance, get yourself some Gin.
https://gin-gonic.com/
MIT License
79.17k stars 8.03k forks source link

File server *and* api on same router #3417

Open seal opened 2 years ago

seal commented 2 years ago

Description

I want to be able to have a fileserver providing my JS files & my api on the same router

How to reproduce

package main

import (
    "github.com/gin-gonic/gin"
)
func GetRouterGorm() *gin.Engine {
    r := gin.Default()
    workDir, _ := os.Getwd()
    filesDir := http.Dir(filepath.Join(workDir, "dist"))
    r.GET("/api/ping", func(c *gin.Context) {
        c.String(http.StatusOK, "pong")
    })

    r.StaticFS("/", filesDir)
    return r
}
func main() {
    r := api.GetRouterGorm()
    r.Run(":9000")
}

Expectations

Wanted it to serve the pre-defined routes for api and anything else, js

Actual result

 - using env:   export GIN_MODE=release
 - using code:  gin.SetMode(gin.ReleaseMode)

[GIN-debug] GET    /api/ping                 --> github.com/seal/scansearch/pkg/api.GetRouterGorm.func1 (3 handlers)
[GIN-debug] GET    /*filepath                --> github.com/gin-gonic/gin.(*RouterGroup).createStaticHandler.func1 (3 handlers)
panic: catch-all wildcard '*filepath' in new path '/*filepath' conflicts with existing path segment 'api' in existing prefix '/api'

goroutine 1 [running]:
github.com/gin-gonic/gin.(*node).insertChild(0x1?, {0xc00036b6d1?, 0xc00006a0d8?}, {0xc00036b6d0, 0xa}, {0xc00000e930, 0x3, 0x3})
        /root/go/pkg/mod/github.com/gin-gonic/gin@v1.8.1/tree.go:353 +0xcc9
github.com/gin-gonic/gin.(*node).addRoute(0x82ac1e?, {0xc00036b6d0, 0xa}, {0xc00000e930, 0x3, 0x3})
        /root/go/pkg/mod/github.com/gin-gonic/gin@v1.8.1/tree.go:252 +0xa39
github.com/gin-gonic/gin.(*Engine).addRoute(0xc000382820, {0x82ac1e, 0x3}, {0xc00036b6d0, 0xa}, {0xc00000e930, 0x3, 0x3})
        /root/go/pkg/mod/github.com/gin-gonic/gin@v1.8.1/gin.go:331 +0x226
github.com/gin-gonic/gin.(*RouterGroup).handle(0xc000382820, {0x82ac1e, 0x3}, {0xc00036b690?, 0xc000367e50?}, {0xc000010d00, 0x1, 0xc000367e50?})
        /root/go/pkg/mod/github.com/gin-gonic/gin@v1.8.1/routergroup.go:88 +0x145
github.com/gin-gonic/gin.(*RouterGroup).GET(...)
        /root/go/pkg/mod/github.com/gin-gonic/gin@v1.8.1/routergroup.go:116
github.com/gin-gonic/gin.(*RouterGroup).StaticFS(0xc000382820, {0x82a510, 0x1}, {0x8e2560, 0xc000367e50})
        /root/go/pkg/mod/github.com/gin-gonic/gin@v1.8.1/routergroup.go:200 +0x17e
github.com/seal/scansearch/pkg/api.GetRouterGorm()
        /root/scansearch/pkg/api/api.go:45 +0xec
main.main()
        /root/scansearch/main.go:17 +0x1d
exit status 2

Environment

Cookiery commented 1 year ago

Hi @seal , You can use r.StaticFS("/static", filesDir) . Beacuse if you use "/", you don't get [api] file in the file system. So you can't use "/" to visit your dist floder.