先来介绍一下项目的基本情况
- 项目遵循 AGPL 3.0 开源协议
- 项目为 Node.js 技术栈,使用的框架为 Next.js,建议使用的 Node.js 版本为 Node 22
- 建议在服务器安装 NVM 以管理 Node.js 的版本,必须使用 pnpm
- 项目使用 PostgreSQL 作为数据库,需要安装 PostgreSQL
- 项目使用 PM2 作为部署手段,需要安装 PM2
- 项目使用 Redis 作为缓存,需要安装 Redis
- 项目的文档/博客内容(/doc)在项目的 /posts 文件夹中,你需要用 MDX 格式来编写文章
接下来就是安装的具体步骤,演示中的服务器安装的是 Debian12 系统,如果你使用的是其他的发行版请自行替换部分安装命令
安装 Node.js 环境
-
首先先更新一下软件包列表,更新一下软件
1
sudo apt update && sudo apt upgrade -y
-
然后安装一下必要依赖
1
sudo apt install curl wget git -y
-
用官方脚本安装 nvm
1
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.7/install.sh | bash
-
安装完之后重载一下 shell 配置
1
source ~/.bashrc
-
验证一下安装,如果有输出版本号就说明安装完成
1
nvm --version
-
用 nvm 安装 Node.js 22 版本,安装完成后会自动使用 Node.js 22,安装完成之后你可以用
node -v
查看版本号验证一下安装。注意本项目一定要使用 Node.js 22及以上版本,使用低于22版本的 Node.js 可能会有不可预见的问题1
nvm install 22
-
执行
npm i -g pnpm
来安装 pnpm,然后使用pnpm self-update
来将 pnpm 更新到最新版,然后可以使用pnpm --version
来查看 pnpm 的版本,只要是大版本 9 以上都可以
安装 Redis 环境
-
使用包管理器安装 redis
1
sudo apt install redis-server
-
启动 redis 并设置开机自启
1 2
sudo systemctl start redis-server sudo systemctl enable redis-server
-
执行
redis-cli ping
来验证安装,如果返回 PONG 则说明安装正确
安装 PM2 环境
-
由于服务器上已经安装了 Node.js+pnpm 环境,所以可以直接用pnpm安装 pm2
1
pnpm i -g pm2
- 执行
pm2 -v
来验证安装
安装 PostgreSQL 环境
-
使用包管理器安装 PostgreSQL,安装完成后 PostgreSQL 会自动启动
1
sudo apt install postgresql postgresql-client
-
切换到 postgres 用户
1
sudo -i -u postgres
-
启动 PostgreSQL 命令行客户端
1
psql
-
修改管理密码,改好之后执行
quit
再按 Ctrl+D 退出1 2
# 这里的 your_password 要改成你自己的密码 ALTER USER postgres WITH PASSWORD 'your_password';
-
PostgreSQL 安装完成之后默认使用的是 peer 验证,也就是需要切换到 postgres 用户才能登录 PostgreSQL,这对我这种用惯了 MySQL 的有点不习惯。如果你也不习惯这种操作方式,你可以到
/etc/postgresql/15/main/pg_hba.conf
中将验证方式改为scram-sha-256
,当然这并不会影响程序的运行,所以这一步是可选的。改完之后执行sudo systemctl restart postgresql
重启 PostgreSQL 应用修改
-
执行
psql -U postgres
输入密码启动 PostgreSQL 命令行客户端 -
创建数据库,这里的数据库的名称
touchgal
可以随便改1
CREATE DATABASE touchgal;
-
执行
\l
命令来查看当前服务器中所有的数据库,以确认 touchgal 数据库存在(\l
命令使用后按下 q 键退出)。 也可以执行\c touchgal
切换到 touchgal 数据库,因为项目使用的数据库名为 touchgal,以确认 touchgal 数据库被创建成功
- 使用
\q
命令退出 PostgreSQL
安装 Nginx 环境
-
使用包管理器安装 nginx
1
sudo apt install nginx
-
执行
sudo nano /etc/nginx/sites-available/touchgal.conf
编写nginx配置文件,这里的文件名可以随便修改。在配置文件里写一个简单的反向代理即可,因为项目默认监听127.0.0.1:3000
,所以我们将反代目标地址设置为127.0.0.1:3000
。这里默认你会在设置好后使用 cloudflare 反代,否则的话你需要在nginx中设置好 SSL1 2 3 4 5 6 7 8 9 10 11 12
server { listen 80; server_name www.touchgal.io; location ^~ / { proxy_pass http://127.0.0.1:3000; proxy_set_header Host www.touchgal.io; } }
-
创建软链接来启用网站
1
sudo ln -s /etc/nginx/sites-available/touchgal.conf /etc/nginx/sites-enabled/
-
测试并应用配置
1 2
nginx -t nginx -s reload
从 GitHub clone 项目并初始化项目
-
将 GitHub 仓库 clone 到服务器的当前文件夹,进入项目根目录并安装项目依赖
1 2 3
git clone https://github.com/KUN1007/kun-touchgal-next cd kun-touchgal-next pnpm i
-
复制一份环境参数设置文件
1
cp .env.example .env
-
用nano或者其他编辑器修改
.env
的内容
|
|
-
保存好
.env
后运行项目初始化脚本1
pnpm deploy:install
-
运行完成后执行
ls -lh
命令查看当前的文件夹,理论上应该有一个完全公开权限的文件夹 uploads,这个文件夹会缓存用户的上传文件 -
执行
psql -U postgres
,然后输入密码,可以进入 PostgreSQL。输入\c touchgal
切换到 touchgal 数据库。使用 \dt 查看数据库 touchgal 中有哪些表,确认刚才运行项目初始化脚本的时候已经将表创建成功了。使用\q
命令退出 PostgreSQL -
运行生产环境的构建脚本,构建完成后项目会运行在服务器本地的 127.0.0.1:3000 端口,因为之前我们已经设置好了 Nginx 反向代理,所以现在你应该已经可以打开网站了
1
pnpm deploy:build
-
到网站的注册页面注册一个用户,第一个注册的用户的UID为1,建议给 UID 为 1 的用户超级管理员
-
回到到服务器中,执行
psql -U postgres
启动 PostgreSQL 命令行客户端,然后输入密码进入 PostgreSQL。输入\c touchgal
切换到 touchgal 数据库。执行UPDATE "user" SET role = 4 WHERE id = 1;
这个 SQL 语句的作用是将 ID 为 1 的用户设置为超级管理员。系统规定,role 字段为 1 的用户是普通用户,2 为创作者,3 为管理员,4 超级管理员
注意,这里的 UID 为 1 的用户就是上面注册的那个用户
-
重新进入网站刷新页面,应该已经可以在用户 1 的主页看到用户 1 变为了超级管理员
到这里整个项目已经部署完毕,接下来是一些模块的使用教程和注意事项
如何编写项目 /doc 目录的 MDX 文件
-
本项目使用 MDX 作为网站 Blog 编写格式,区别于 Markdown 的地方就是可以在 MDX 文件里面写 tsx / jsx,如果用不到这些高级功能可以不用管
-
本项目的 matter 属性如下
1 2 3 4 5 6 7 8 9 10 11
--- title: 鲲 Galgame 补丁开发文档 banner: '/posts/dev/documentation/banner.avif' description: '鲲 Galgame 补丁的开发技术栈为 Next.js 15 + Prisma + PostgreSQL + PM2 + Cloudflare Tunnel + S3 Object Storage' date: 2024-12-08 authorUid: 2 authorName: '鲲' authorAvatar: 'https://image.moyu.moe/user/avatar/user_2/avatar-mini.avif' authorHomepage: 'https://github.com/KUN1007' pin: false ---
banner 属性的文章的头图,可以使用 https url 的链接,也可以使用相对路径静态文件资源的链接,将图片文件托管在项目的目录中。我这里,会将项目的 public 目录解析为文章中静态资源的根目录,这里的 ‘/posts/dev/documentation/banner.avif’ 的位置就在项目的 public 文件夹下对应的位置
description 属性严重设计到 /doc 目录的 SEO,建议填写 170 字左右
date 是文字发布的日期,authorUid 就是文章发布者的 UID,就是用户主页路径里的数字,一般填写你自己的就可以,下面两个也是一样的
pin 属性指明了这个文章是否会被在主页的走马灯(轮播图)组件中置顶
-
项目的 posts 目录存放了当前所有的文章,posts 目录的结构就对应着 /doc 页面的目录结构
然后页面的路径就是这样的
页面中的目录映射了 posts 文件夹的目录结构
-
目录的名称映射文件在项目的
contants/doc.ts
文件中,当你新建目录的时候应该同步更新这个文件的目录名称映射
如何添加友情链接
在项目的 config/friend.json
文件中编写对应的信息即可
如何配置网站的信息
网站的信息目前已经配置好,如果需要更改,则必须更改 config/moyu-moe.ts
文件
|
|
暂时仅建议更改这里的信息,如非必要不要更改这个文件,这涉及到网站全部的名称、链接配置与 SEO 优化
关于项目的构建
- 每次当你对项目做了任何更改,必须重新在服务器的项目根目录运行一遍
pnpm deploy:build
命令,这会将你的更改应用到项目中,并重新构建项目 - 构建过程一般在 1 ~ 2 分钟,这个期间网站会有部分功能不可用,正在访问网站的用户不会受到影响
- 构建完毕之后服务器需要将新生成的文件读取到到内存,CDN 和用户浏览器的缓存也需要刷新,网站速度会短暂变慢直到 CDN 和用户浏览器的缓存与服务器同步
严重警告
如果你在运行 pnpm deploy:build
或者运行任何其它命令的时候,看到下面的提示消息
|
|
这时,必须连按两下 Ctrl + c 中断操作,或者输入 n
以取消操作
千万不要按 y 或者回车,否则,数据库中的所有数据会被全部重置,不可能还原,如果没有备份将会倾家荡产,非常严重
这个是使用 prisma 造成了对数据库不可逆的更改造成的,一般不会有这种情况,如果有会明确告知
几个重要的地方说明
-
自行修改项目代码造成的任何不良后果需要自行承担
-
网站的 NSFW 文章,用户主页等已经彻底阻止搜索引擎索引,这些文章将会 0 SEO 甚至反 SEO,不会对其它页面产生影响
-
项目的 uploads 文件夹是用户上传的临时文件,因为怕有的用户上传一半不传了或者传了不发布产生死文件。项目没过 1h 会自动扫描一遍项目中的 uploads 文件夹,删除超过 1 天的死文件
-
项目占用服务器的内存取决于网站的访问量以及项目的实例数,理论上 300k ~ 400k 月独立 ip 数的网站,使用 pm2 部署,按照目前的配置可以流畅运行,内存占用在 700MB 左右
-
如果觉得网站速度还是不够,可以多开几个实例,实例数取决于服务器的核数,pm2 会利用服务器的核数自动负载均衡,目前只开了一个实例。例如 16 核服务器可建议开 16 个实例,项目会自动进行负载均衡,但是同时项目对服务器的内存占用也会变成 700MB * 16
开多实例的方法就是更改项目根目录的
ecosystem.config.js
文件1 2 3 4 5 6 7 8 9 10 11 12 13 14
module.exports = { apps: [ { name: 'kun-touchgal-next', port: 3000, cwd: '.', instances: 1, autorestart: true, watch: false, max_memory_restart: '1G', script: './.next/standalone/server.js' } ] }
你可以把这里的 instances 数量改为对应你服务器核数的数字,比如你划出了一个 4c8g 的小鸡,可以把 instances 改为 4,6c12g 则可以把 instances 改为 6