php小编百草介绍,当在nixOS上使用Nginx反向代理时,有时会遇到一个问题:尝试加载css/js时返回404错误。这个问题可能会导致网站的样式和功能无法正常显示。为了解决这个问题,我们需要检查Nginx的配置和文件路径是否正确,并确保代理服务器能够正确访问和加载所需的静态资源。通过仔细排查和调试,我们可以解决这个问题,确保网站的正常运行。
问题内容
我已经设置了 nixos
来运行 nginx
作为 docker 容器的反向代理。在docker容器中运行一个golang
服务器,它使用函数处理/
,并从两个文件夹static
和js
返回文件。它在端口 8181 上运行。其代码如下所示:
func main() {
static := http.fileserver(http.dir("static"))
js := http.fileserver(http.dir("js"))
http.handle("/static/", http.stripprefix("/static/", static))
http.handle("/js/", http.stripprefix("/js/", js))
// register function to "/"
http.handlefunc("/", indexhandler)
fmt.println("server is starting...")
err := http.listenandserve("0.0.0.0:8181", nil)
if err != nil {
log.fatal("cannot listen and server", err)
}
}
func indexhandler(w http.responsewriter, r *http.request) {
wd, err := os.getwd()
var static = filepath.join(wd, "static")
var index = filepath.join(static, "index.html")
if err != nil {
log.fatal("cannot get working directory", err)
}
// check if the request is an options preflight request
if r.method == "options" {
// respond with status ok to preflight requests
w.writeheader(http.statusok)
return
}
// post-request
if r.method == http.methodpost {
// do something
} else {
// loading the index.html without any data
tmpl, err := template.parsefiles(index)
err = tmpl.execute(w, nil) // write response to w
if err != nil {
http.error(w, err.error(), http.statusinternalservererror)
log.fatal("problem with parsing the index template ", err)
}
}
}
我的应用程序的结构如下所示。
├── web
│ ├── dockerfile
│ ├── go.mod
│ ├── server.go
│ └── static
│ │ ├── index.html
│ │ ├── style.css
│ │ └── table.html
│ └── js
│ └── htmx.min.js
configuration.nix
中 nginx
部分的配置如下所示。
services.nginx = {
enable = true;
recommendedGzipSettings = true;
recommendedOptimisation = true;
recommendedProxySettings = true;
recommendedTlsSettings = true;
virtualHosts."myapp" = {
sslCertificate = "/etc/ssl/nginx/ssl.cert";
sslCertificateKey = "/etc/ssl/nginx/ssl.key";
sslTrustedCertificate = "/etc/ssl/nginx/ssl.chain";
forceSSL = true; # Redirect HTTP to HTTPS
locations = {
"/myapp" = { proxyPass = "http://localhost:8181/"; };
};
extraConfig = ''
proxy_set_header Host $host;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
'';
};
};
当我寻址 https://server/myapp
时,index.html
将加载,但 style.css
和 htmx.min.js
将返回 404。
当使用端口 8181 而不是 url (http://server:8181
) 寻址容器时,一切都会照常加载。
我希望nginx将加载css和js的请求重定向到容器。
编辑:
确切的错误是: get https://server.name/static/style.css net::err_aborted 404
即使我正在访问 https://server.name/myapp
。
另一个重要信息是,我想通过同一个反向代理以这种方式运行多个容器。因此,将 als css
- 或 js
-files 定向到同一位置将不起作用。
解决方法
请检查 index.html
文件中的 css/js 引用。您很可能通过绝对路径引用它们,如下所示:
<html>
<head>
<link rel="stylesheet" type="text/css" href="/static/style.css" />
</head>
</html>
快速修复方法是将它们替换为相对路径:
<html>
<head>
<link rel="stylesheet" type="text/css" href="./static/style.css" />
</head>
</html>
这种方法很容易出错。更好的方法是修改应用程序以在 /myapp
处提供内容:
http.handle("/myapp/static/", http.stripprefix("/myapp/static/", static))
http.handle("/myapp/js/", http.stripprefix("/myapp/js/", js))
http.handlefunc("/myapp/", indexhandler)
并修改index.html
文件中的引用路径:
<html>
<head>
<link rel="stylesheet" type="text/css" href="/myapp/static/style.css" />
</head>
</html>
然后修改nginx配置:
locations = {
"/myapp/" = { proxyPass = "http://localhost:8181/myapp/"; };
};
通过这种方法,无论是否使用反向代理,web 应用程序将始终在 uri /myapp/
上提供服务,这应该使其易于维护。