英文:
Fileserver returns 404 for all files
问题
每当我尝试访问静态子目录中的任何文件时,都会收到404错误,而访问Home/则正常工作,但是我从home文件中调用的图片却无法显示。所以我想知道要更改什么,以便我既可以提供文件,又可以同时重定向我的根目录。
我的路径结构如下:
root/
->html
->static
->entry.go
我看到其他帖子上都建议我使用r.PathPrefix("/")。Handler(...),但是这样做会导致访问静态文件夹外的任何文件返回NIL,包括我的html文件,它们位于项目根目录的一个单独的html文件中,此外,重定向到其中任何一个都会返回404错误。
以下是代码:
package main
import (
"fmt"
"net/http"
"html/template"
"github.com/gorilla/mux"
"os"
)
func IfError(err error, quit bool) {
if err != nil {
fmt.Println(err.Error())
if(quit) {
os.Exit(1);
}
}
}
func NotFound(w http.ResponseWriter, r *http.Request) {
w.WriteHeader(404)
t, _ := template.ParseFiles("html/404")
err := t.Execute(w, nil)
IfError(err, false)
}
func Home(w http.ResponseWriter, r *http.Request) {
t, _ := template.ParseFiles("html/home")
err := t.Execute(w, nil)
IfError(err, false)
}
func RedirectRoot(servefile http.Handler) http.Handler {
return http.HandlerFunc(func (w http.ResponseWriter, r *http.Request) {
if r.URL.Path == "/" {
redirect := r.URL.Host+"/home"
http.Redirect(w, r, redirect, http.StatusSeeOther)
} else {
servefile.ServeHTTP(w, r)
}
})
}
func main() {
r := mux.NewRouter()
ServeFiles := http.StripPrefix("/", http.FileServer(http.Dir("static/")))
r.Handle("/", RedirectRoot(ServeFiles))
r.HandleFunc("/home", Home)
r.NotFoundHandler = http.HandlerFunc(NotFound)
fmt.Printf("Listening ...")
IfError(http.ListenAndServe(":8081", r), true)
}
非常感谢!
英文:
So whenever I try to access any files in my static sub-directory, I just get a 404, Not Found, Accessing Home/ on the other hand works just fine, but a picture that I call from the home file is simply broken :(, So I'd like to know what to change so that I can serve files and redirect my root directory at the same time.
My Path structure:
root/
->html
->static
->entry.go
I saw the other threads on here, they all recommend that I do r.PathPrefix("/").Handler(...), but doing that makes it so accessing any file outside static returns NIL, including my html files which are in a separate html file in the root of my project, furthermore, redirecting to any of them returns 404, Not Found.
Here's the code:
package main
import (
"fmt"
"net/http"
"html/template"
"github.com/gorilla/mux"
"os"
)
func IfError(err error, quit bool) {
if err != nil {
fmt.Println(err.Error())
if(quit) {
os.Exit(1);
}
}
}
func NotFound(w http.ResponseWriter, r *http.Request) {
w.WriteHeader(404)
t, _ := template.ParseFiles("html/404")
err := t.Execute(w, nil)
IfError(err, false)
}
func Home(w http.ResponseWriter, r *http.Request) {
t, _ := template.ParseFiles("html/home")
err := t.Execute(w, nil)
IfError(err, false)
}
func RedirectRoot(servefile http.Handler) http.Handler {
return http.HandlerFunc(func (w http.ResponseWriter, r *http.Request) {
if r.URL.Path == "/" {
redirect := r.URL.Host+"/home"
http.Redirect(w, r, redirect, http.StatusSeeOther)
} else {
servefile.ServeHTTP(w, r)
}
})
}
func main() {
r := mux.NewRouter()
ServeFiles := http.StripPrefix("/", http.FileServer(http.Dir("static/")))
r.Handle("/", RedirectRoot(ServeFiles))
r.HandleFunc("/home", Home)
r.NotFoundHandler = http.HandlerFunc(NotFound)
fmt.Printf("Listening ...")
IfError(http.ListenAndServe(":8081", r), true)
}
Thank you very much
答案1
得分: 0
我在你的代码中看到的问题是:
r.Handle("/", RedirectRoot(ServeFiles))
这个路由会匹配所有的路径,可能会产生意想不到的结果。相反,你应该清晰明确地映射你的路由,这样它才能按照你的期望工作。
例如:让我们根据你的目录结构来映射处理程序。这种方法只会通过文件服务器公开static
目录,其他文件和根目录是安全的。
func main() {
r := mux.NewRouter()
r.Handle("/static/", http.StripPrefix("/static/", http.FileServer(http.Dir("static"))))
r.HandleFunc("/home", Home)
r.NotFoundHandler = http.HandlerFunc(NotFound)
fmt.Printf("Listening ...")
IfError(http.ListenAndServe(":8081", r), true)
}
对于你的目的,可能不需要RedirectRoot
。
现在,/static/*
由http.FileServer
提供,/home
由Home
处理。
编辑:
根据评论中的要求,将根路径/
映射到Home
处理程序,并添加以下内容来处理/favicon.ico
。
func favIcon(w http.ResponseWriter, r *http.Request) {
http.ServeFile(w, r, "static/favicon.ico")
}
r.HandleFunc("/favicon.ico", favIcon)
r.HandleFunc("/", Home)
favicon.ico
从static
目录中提供。
英文:
The issue I see in your code
r.Handle("/", RedirectRoot(ServeFiles))
It will match every route, may produce unexpected results. Instead map your routes clearly and explicitly then it will work as you expect.
For eg.: Let's maps the handler with responsibility. This approach based on your directory structure.
It will only expose static
directory via file server, remaining files and root directory is safe.
func main() {
r := mux.NewRouter()
r.Handle("/static/", http.StripPrefix("/static/", http.FileServer(http.Dir("static"))))
r.HandleFunc("/home", Home)
r.NotFoundHandler = http.HandlerFunc(NotFound)
fmt.Printf("Listening ...")
IfError(http.ListenAndServe(":8081", r), true)
}
RedirectRoot
may not be needed for your purpose.
Now, /static/*
served by http.FileServer
and /home
handled by Home
.
EDIT:
As asked in the comment. To map root /
to home handler and /favicon.ico
, add following in-addition to above code snippet.
func favIcon(w http.ResponseWriter, r *http.Request) {
http.ServeFile(w, r, "static/favicon.ico")
}
r.HandleFunc("/favicon.ico", favIcon)
r.HandleFunc("/", Home)
favicon.ico
served from static
directory.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论