我刚刚进入Laravel/Vue3,所以我正在学习基础知识。然而,我有一个现有的Docker生态系统,用于本地开发和nginx反向代理,以将我的许多项目分开。
我很难让HMR工作,更难找到关于如何配置Vite和Nginx的适当文档,这样我就可以在Nginx中有一个HTTPS入口点,并代理回Laravel和Vite。
构建基于https://github.com/laravel-presets/inertia/tree/boilerplate.
为了完整起见,这是package.json,以备更改:
{
"private": true,
"scripts": {
"dev": "vite",
"build": "vite build"
},
"devDependencies": {
"@vitejs/plugin-vue": "^2.3.1",
"@vue/compiler-sfc": "^3.2.33",
"autoprefixer": "^10.4.5",
"postcss": "^8.4.12",
"tailwindcss": "^3.0.24",
"vite": "^2.9.5",
"vite-plugin-laravel": "^0.2.0-beta.10"
},
"dependencies": {
"vue": "^3.2.31",
"@inertiajs/inertia": "^0.11.0",
"@inertiajs/inertia-vue3": "^0.6.0"
}
}
为了简单起见,我将尝试让它只在HTTP下工作,稍后再处理HTTPS。
因为我在容器中运行dev服务器,所以在vite.config.ts中将server.host设置为0.0.0.0
,将server.hmr.clientPort设置为80。这将允许从容器外部连接到dev服务器,并有望实现公共端口是80,而不是默认的3000。
我已经尝试将DEV_SERVER_URL设置为与APP_URL相同,以便来自公共站点的所有流量都能到达相同的位置。但我不确定nginx方面应该是什么样子。
我还尝试将DEV_SERVER_URL设置为http://0.0.0.0:3000/这样我就可以看到试图产生什么流量。这几乎奏效,但大错特错。当涉及到ws://0.0.0.0/通信时,它会失败,当涉及到HTTPS时,它将不合适。
我注意到对/__vite_plugin
的调用,我假设它是通常在config/vite.php
中设置的默认ping_url。
寻找关于哪些nginx位置应该转发到Laravel端口,哪些位置应该转发给Vite端口的指导,以及应该是什么样子,这样网络套接字通信也可以得到满足。
我看到有人讨论过Vite 3可能会让这个设置更容易,但我想谈谈现在可用的东西。
答案似乎是知道要代理到Vite的目录,并能够隔离用于HMR的web套接字。
为此,您需要执行以下操作:
- 确保您的
.env
APP_URL
和DEV_SERVER_URL
匹配 - 在
vite.config.ts
中,确保server.host
为"0.0.0.0",以便可以接受来自容器外部的连接 - 在
vite.config.ts
中指定base
(如'/app/'
),以便在运行npm run dev
时可以隔离所有HMR流量并将其重定向到Vite服务器。如果该路径可能与Laravel或Vite应用程序中的真实路径(如/_dev/
或/_vite'
)冲突,您可能希望使用其他路径 - 在
config/vite.php
中,将ping_url
的值设置为http://localhost:3000
。这允许Laravel在本地ping Vite服务器,这样就不应该使用清单,而是使用Vite服务器。这也假定CCD_ 18被设置为CCD_ - 最后,您需要配置nginx代理,以便将许多位置专门代理到Vite服务器,其余位置则代理到Laravel服务器
我不是Nginx专家,所以可能有一种方法可以简洁地声明以下内容。
Nginx服务器条目示例
# Some standard proxy variables
map $http_x_forwarded_proto $proxy_x_forwarded_proto {
default $http_x_forwarded_proto;
'' $scheme;
}
map $http_x_forwarded_port $proxy_x_forwarded_port {
default $http_x_forwarded_port;
'' $server_port;
}
map $http_upgrade $proxy_connection {
default upgrade;
'' close;
}
map $scheme $proxy_x_forwarded_ssl {
default off;
https off;
}
server {
listen *:80;
server vite-inertia-vue-app.test;
/* abridged version that does not include gzip_types, resolver, *_log and other headers */
location ^~ /resources/ {
proxy_pass http://198.18.0.1:3000;
include /etc/nginx/vite-inertia-vue-app.test.include;
}
location ^~ /@vite {
proxy_pass http://198.18.0.1:3000;
include /etc/nginx/vite-inertia-vue-app.test.include;
}
location ^~ /app/ {
proxy_pass http://198.18.0.1:3000;
include /etc/nginx/vite-inertia-vue-app.test.include;
}
location / {
proxy_pass http://198.18.0.1:8082;
include /etc/nginx/vite-inertia-vue-app.test.include;
}
}
vite-inertia-vue-app.test.include
包括通用代理设置
proxy_read_timeout 190;
proxy_connect_timeout 3;
proxy_redirect off;
proxy_http_version 1.1;
proxy_set_header Host $host;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $proxy_connection;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $proxy_x_forwarded_proto;
proxy_set_header X-Forwarded-Ssl $proxy_x_forwarded_ssl;
proxy_set_header X-Forwarded-Port $proxy_x_forwarded_port;
proxy_set_header Proxy "";
我的Nginx实例在本地Docker Swarm中运行,我使用环回接口(198.18.0.1)来访问我机器上的开放端口。您的里程数可能有所不同。端口3000用于Vite服务器。端口9082用于Laravel服务器。
在某个时候,我可能会研究使用docker-compose
堆栈中声明的主机名,尽管我不太确定在Docker Swarm和常规容器堆栈之间进行通信时,主机名的效果如何。重点是,如果我最终同时运行多个项目,就不必为Laravel和Vite服务器分配唯一的端口。
入口点/@vite
和/resources
用于应用程序最初启动时,这些入口点由标头中的脚本和链接标签使用。之后,所有HMR活动都使用/app/
。
下一个挑战将是添加一个自签名证书,因为我计划集成一些Azure B2C登录,但我认为这可能只涉及更新Nginx配置以满足TLS,并更新.env
中的APP_URL
和DEV_SERVER_URL
以匹配。