主题
CatchAdmin 部署指南
详细的 CatchAdmin 生产环境部署教程和最佳实践
WARNING
很多开发者在部署 CatchAdmin 时遇到问题,这里提供了完整详细的部署文档。本文档包含了从前端构建到服务器配置的全部步骤,基本涵盖了所有部署场景。
请仔细阅读文档,大部分问题都能在这里找到解决方案。如果遇到特殊情况确实需要协助,目前提供付费部署支持服务,收费标准为 100
元/次。先付费后服务,感谢理解 🙏
前端项目
在构建 CatchAdmin 前端项目前,需要先配置生产环境的 API 地址。在前端项目根目录下创建或编辑 .env.production
文件:
# base api
// 例如 https://api.catchadmin.com/api/
VITE_BASE_URL = '正式环境的 API 地址'
配置完成后,使用以下命令构建 CatchAdmin 前端项目:
bash
yarn run build
# 或者使用 npm
npm run build
打包出现报错
如果打包出现 ts 过多的类型错误,而你对类型又不太敏感的话,对应用没有影响。一个快速的解决办法就是修改 package.json 文件
build 命令
json
{
"scripts": {
"dev": "vite",
"build": "vue-tsc --noEmit && vite build",
"build": "vite build",
"preview": "vite preview"
}
}
构建完成后,前端项目根目录会生成 dist
目录,这是 CatchAdmin 前端的生产版本,包含经过优化的静态资源文件,可直接部署到 Web 服务器。
性能优化建议
- 建议在 Web 服务器上启用
Gzip
压缩,可显著提升页面加载速度 - 配置静态资源缓存策略,提升用户体验
- 使用 CDN 加速静态资源访问
后端
CatchAdmin 后端基于 PHP 开发,部署相对简单。将 PHP 项目代码上传到服务器即可。
推荐部署方式:
- 上传源代码到服务器,不包含
vendor
目录 - 在服务器上执行
composer install --no-dev
安装生产环境依赖 - 配置正确的文件权限和目录结构
如果遇到依赖安装的网络问题,请参考 使用镜像 解决方案。
重要提醒
如果使用了 CatchAdmin 脚手架初始化项目,部署时需要注意:
- 排除
web
目录:这是前端开发目录,不需要与后端一起上传 - 前端部署:只需要上传构建后的
dist
目录 - 分离部署:前后端建议分开部署,便于维护和扩展
上线注意点
.env
环境文件是否配置好?- 数据库表是否同步?
- 数据表的数据是否同步,主要是权限菜单表
permissions
里是否同步 - 模块是否开启? 模块如果没有开启,整个项目都会无法正常运行 (
这个步骤只针对 Laravel 主项目
)TIP
一定要检查线上项目
storage/app/modules.json
是否存在。如果不存在,要将本地项目storage/app/modules.json
上传到服务器 - 模块如果正常开启的状态下,路由还是无法正常工作 (
这个步骤只针对 Laravel 主项目
)TIP
- 首先是用 php artian route:clear
- 然后查看路由 php artisan route:list
- 最后缓存路由 php artisan route:cache
部署
WARNING
如果你使用的是宝塔相关的,一定不要完全复制下面的配置。因为宝塔有很多预配置项,例如 https ssl 配置是不需要你自己手动配置
分开部署(双域名)
推荐的 CatchAdmin 部署方式是前后端分离部署,分别使用不同的域名或子域名:
部署架构示例:
- 前端项目:
admin.yourdomain.com
→/www/admin
目录 - 后端 API:
api.yourdomain.com
→/www/api
目录
部署建议
- 目录路径可根据实际服务器环境调整
- 分离部署便于独立维护和扩容
- 支持前后端独立更新,降低部署风险
/www/admin
上传dist
目录内容到 admin 目录中/www/api
上传后端项目到 api 目录中
php
server
{
listen 80;
server_name admin.catchadmin.com;
return 301 https://admin.catchadmin.com$request_uri;
}
server
{
listen 443 ssl http2;
server_name admin.catchadmin.com;
index.html index.php index.htm default.php default.htm default.html;
ssl_certificate # pem文件的路径
ssl_certificate_key # key文件的路径
# ssl验证相关配置
ssl_session_timeout 5m; #缓存有效期
ssl_ciphers ECDHE-RSA-AES128-GCM-SHA256:ECDHE:ECDH:AES:HIGH:!NULL:!aNULL:!MD5:!ADH:!RC4;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;
root /www/admin;
location / {
try_files $uri $uri/ /index.html =404;
}
}
php
server
{
listen 80;
server_name api.catchadmin.com;
return 301 https://api.catchadmin.com$request_uri;
}
server
{
listen 443 ssl http2;
server_name api.catchadmin.com;
index index.html index.php index.htm default.php default.htm default.html;
root /www/api/public;
ssl_certificate /etc/nginx/acme/catchadmin.com/catchadmin.com.cer; # pem文件的路径
ssl_certificate_key /etc/nginx/acme/catchadmin.com/catchadmin.com.key; # key文件的路径
ssl_session_timeout 5m; #缓存有效期
ssl_ciphers ECDHE-RSA-AES128-GCM-SHA256:ECDHE:ECDH:AES:HIGH:!NULL:!aNULL:!MD5:!ADH:!RC4;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;
location / {
if (!-e $request_filename) {
rewrite ^(.*)$ /index.php?s=/$1 last;
break;
}
}
# PHP 支持
location ~ \.php$ {
try_files $uri /index.php =404;
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params;
}
## nginx log 自己配置
access_log;
error_log;
}
合并部署(单域名)
如果只有一个域名或希望简化部署架构,可以将 CatchAdmin 前后端部署在同一域名下:
部署结构:
- 后端项目:
yourdomain.com/api
→ PHP 项目根目录 - 前端项目:
yourdomain.com/
→ 放置在后端项目的public/admin
目录下
这种方式适合小型项目或资源有限的场景。
php
server
{
listen 80;
server_name api.catchadmin.com;
return 301 https://api.catchadmin.com$request_uri;
}
server
{
listen 443 ssl http2;
server_name api.catchadmin.com;
index index.html index.php index.htm default.php default.htm default.html;
root /www/api/public;
ssl_certificate # pem文件的路径
ssl_certificate_key # key文件的路径
ssl_session_timeout 5m; #缓存有效期
ssl_ciphers ECDHE-RSA-AES128-GCM-SHA256:ECDHE:ECDH:AES:HIGH:!NULL:!aNULL:!MD5:!ADH:!RC4;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;
# 因为接口都是以 api.catchadmin.com/api 开头,所以可以很好的使用 location
# 如果访问 api.catchadmin.com/api 目录 则用 php 解释下
location /api {
if (!-e $request_filename) {
rewrite ^(.*)$ /index.php?s=/$1 last;
break;
}
}
# 如果访问根目录 api.catchadmin.com/, 则直接访问前端项目
location / {
root /www/api/public/admin;
try_files $uri $uri/ /index.html;
}
# 上传的静态目录 location
location /uploads/ {
alias /www/api/storage/uploads/;
autoindex on;
}
#PHP 支持
location ~ \.php$ {
try_files $uri /index.php =404;
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params;
}
}
如果使用宝塔部署,location
配置静态目录的可能会无法工作,这是由于宝塔的预配置导致的,目前我个人使用下面如图得方法解决了
Octane 高性能部署
对于需要高性能的 CatchAdmin 项目,可以使用 Laravel Octane 提升并发处理能力:
Octane 优势:
- 显著提升 API 响应速度
- 更好的内存利用率
- 支持 WebSocket 等高级特性
适用场景:高并发访问、实时数据处理、大量 API 调用的企业级应用
php
map $http_upgrade $connection_upgrade {
default upgrade;
'' close;
}
server
{
listen 80;
server_name api.catchadmin.com;
return 301 https://api.catchadmin.com$request_uri;
}
server
{
listen 443 ssl http2;
server_name api.catchadmin.com;
index index.html index.php index.htm default.php default.htm default.html;
root /www/api/public;
ssl_certificate # pem文件的路径
ssl_certificate_key # key文件的路径
ssl_session_timeout 5m; #缓存有效期
ssl_ciphers ECDHE-RSA-AES128-GCM-SHA256:ECDHE:ECDH:AES:HIGH:!NULL:!aNULL:!MD5:!ADH:!RC4;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;
# 因为接口都是以 api.catchadmin.com/api 开头,所以可以很好的使用 location
# 如果访问 api.catchadmin.com/api 目录 则用 php 解释下
location /api {
if (!-e $request_filename) {
rewrite ^(.*)$ /index.php?s=/$1 last;
break;
}
}
# 如果访问根目录 api.catchadmin.com/, 则直接访问前端项目
location / {
root /www/api/public/admin;
try_files $uri $uri/ /index.html;
}
# 上传的静态目录 location
location /uploads/ {
alias /www/api/public/storage/uploads/;
autoindex on;
}
location @octane {
set $suffix "";
if ($uri = /index.php) {
set $suffix ?$query_string;
}
proxy_http_version 1.1;
proxy_set_header Host $http_host;
proxy_set_header Scheme $scheme;
proxy_set_header SERVER_PORT $server_port;
proxy_set_header REMOTE_ADDR $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_pass http://172.18.0.2:9800$suffix;
}
}