# KyCMS 博客版 **Repository Path**: bloginc/kycms-blog ## Basic Information - **Project Name**: KyCMS 博客版 - **Description**: KyCMS 博客版 是一个单二进制交付、全代码开源的博客/内容管理系统。 - **Primary Language**: Unknown - **License**: AGPL-3.0 - **Default Branch**: main - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 1 - **Forks**: 0 - **Created**: 2026-11-07 - **Last Updated**: 2026-11-09 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # KyCMS 博客版(KyCMS Blog) [![License: AGPL-3.0](https://img.shields.io/badge/License-AGPL--3.0-blue)](LICENSE) ![Go 1.26+](https://img.shields.io/badge/Go-1.26%2B-00ADD8?logo=go) ![Vue 3](https://img.shields.io/badge/Vue-3-42B883?logo=vuedotjs) ![MySQL 8](https://img.shields.io/badge/MySQL-8-4479A1?logo=mysql) 一个内容管理站点:Go 后端(Gin + GORM + MySQL)同时托管**公开站点**(服务端渲染模板)与**管理后台 API**,管理后台是一个 Vue 3 + TypeScript 单页应用(SPA),在编译期通过 `//go:embed` 打进同一个二进制,部署时只需一个可执行文件 + 一份 `.env`。 ## 功能特性 - **单文件交付**:公开站点模板、后台 SPA 与 `cwebp` 全部编译期嵌入,生产环境无需额外静态目录 - **前后端一体**:Go(Gin + GORM)与 Vue 3 + TypeScript + TDesign 同仓,`./backend/dev.sh` 一条命令构建并运行 - **多种部署形态**:Docker Compose 一键、裸机 systemd、宝塔 / 1Panel 面板,管理工具自动识别 - **后台入口可改**:`ADMIN_PATH` 运行期注入,改路径无需重建前端;改错也有命令行自救 - **登录安全**:TOTP 二次验证(RFC 6238)、首次登录强制改密、审计日志、限流与反垃圾 - **内置图片处理**:静态 `cwebp` 随二进制分发,服务器无需另装依赖 - **全部开源**:AGPL-3.0 + 主题附加许可,无授权码、无功能门槛、无隐藏闭源模块 - **主题自由**:第三方主题可自选许可证(含收费),契约见 [docs/THEME-API.md](docs/THEME-API.md) ## 目录 - [快速开始](#快速开始) - [环境要求](#环境要求) - [关于项目](#关于项目) - [技术架构](#技术架构) - [项目结构](#项目结构) - [本地开发](#本地开发) - [部署与运维](#部署与运维) - [常见问题与故障处理](#常见问题与故障处理) - [文档索引](#文档索引) - [测试](#测试) - [备注](#备注) - [贡献与反馈](#贡献与反馈) - [许可证](#许可证) ## 快速开始 ### Docker(推荐) 只需 Docker + Compose v2,一行命令完成部署(应用与 MySQL 8.4 均自动就绪): ```bash curl -fsSL https://gitee.com/bloginc/kycms-blog/raw/main/install.sh | bash ``` 完成后按脚本输出访问:公开站在 `/`,后台入口是脚本随机生成的 `/adm-xxxxxxxx`(会打印在部署完成的提示里,也可在 `.env` 查看或用 `kycms 2` 重置)。初始账号 `admin / admin`,首次登录强制改密。 不想直接执行远程脚本,可先下载检查再运行,见 [部署指南](docs/deployment.md)。 ### 源码本地运行 ```bash # 在仓库根目录执行 mysql -u root -p kycms < sql/schema.sql # 1. 建库建表 cd backend cp .env.example .env # 2. 填写 JWT_SECRET 与数据库连接 ./backend/dev.sh # 3. 构建前端 → 编译 Go → 前台运行 ``` - 公开站:`http://localhost:8080/` - 后台:`http://localhost:8080/`(默认 `/admin`) > 完整配置项见[本地开发](#本地开发),其他部署形态见[部署与运维](#部署与运维)。 ## 环境要求 - Docker 部署:仅 Docker + Compose v2(见 [部署指南](docs/deployment.md)) - 源码构建:Go ≥ 1.26、Node.js ≥ 22.12(仅构建前端时需要) - MySQL 8.0/8.4(导入 `sql/schema.sql` 建库建表;MariaDB 等分支未验证) ## 关于项目 本项目的规范名称是 **KyCMS 博客版**,英文简称 **KyCMS Blog**(下文简称本项目)。仓库、二进制、文档统一使用这两个写法。 本项目是独立开源项目,**全部代码开源**:AGPL-3.0 + 主题附加许可。 自身代码不设授权码、不设功能门槛,也没有隐藏的闭源模块 —— 克隆下来就是完整实现,构建出来的就是完整功能。 欢迎开发者一起完善:功能建议与缺陷反馈走仓库 issue,代码贡献走 Pull Request。 不需要签署 CLA,也不要求 `Signed-off-by`,提交即以 AGPL-3.0 授权,著作权仍归贡献者。详见 [CONTRIBUTING.md](CONTRIBUTING.md)。 许可边界:本项目自身代码被修改并分发时,须同样以 AGPL-3.0 开源;第三方主题可自行选择许可证(含收费与专有许可),见 [LICENSE-EXCEPTION.md](LICENSE-EXCEPTION.md)。 ## 技术架构 - 后端:Go 1.26+(gin、gorm、gorm.io/driver/mysql),单二进制、零外部依赖运行 - 管理后台:`admin/`(Vue 3 + TypeScript + TDesign + Vite + Pinia + vue-i18n) - 数据库:MySQL(建表语句见 `sql/schema.sql`) - 图片处理:Google `cwebp` 静态二进制(编译期嵌入,见 `backend/internal/imgconv/bin/README.md`) ```mermaid flowchart LR B["浏览器"] --> G["Go 服务 · Gin"] G --> T["公开站点 HTML 模板"] G --> A["管理后台 SPA · Vue 3"] G --> W["cwebp 静态二进制"] G -->|GORM| M["MySQL 8.0 / 8.4"] G --> U["uploads/ 运行时文件"] T -.->|go:embed| X["单个可执行文件"] A -.->|go:embed| X W -.->|go:embed| X ``` 设计背景与取舍按主题归档在 [docs/design/](docs/design/README.md)。 ## 项目结构 ``` . ├── admin/ 管理后台前端源码(Vue3 + TS + Vite) │ └── src/ 页面 / 组件 / API 封装 ├── backend/ Go 服务 │ ├── cmd/server/ 程序入口 main.go │ ├── internal/ config / handler / service / model / middleware / router / imgconv / util │ ├── templates/ 公开站点 HTML 模板(编译期嵌入) │ ├── web/admin/dist/ 前端构建产物(编译期嵌入,由 admin/ 构建生成) │ ├── uploads/ 运行时上传文件(git 忽略) │ ├── tmp/ 本地构建 / air 热重载输出(git 忽略) │ ├── dev.sh 本地编译+运行(含前端产物新鲜度检查) │ ├── deploy-dev.sh 交叉编译并上传到 Linux 服务器 │ ├── setup-wsl.sh WSL 一次性装 Go / air / 环境变量 │ ├── setup-ssh.sh SSH 部署前置 │ └── .env.example 后端配置样例 ├── docs/ 部署、运维、设计与主题文档 │ ├── deployment.md Docker / 面板 / 裸机部署、构建与升级 │ ├── operations.md 管理工具、TOTP 恢复、常见问题 │ ├── design/ 设计背景归档 │ ├── THEME-API.md 主题对外契约 │ └── COMMENT-STYLE.md 代码注释约定 ├── scripts/ CI 自检与运维脚本 ├── sql/schema.sql 数据库建表语句 └── build-linux.ps1 Windows 下交叉编译 Linux 二进制 ``` ## 本地开发 ### 1. 准备数据库 ```bash mysql -u root -p kycms < sql/schema.sql ``` ### 2. 后端配置 ```bash cd backend cp .env.example .env ``` 必填项(留空会导致服务拒绝启动): - `JWT_SECRET`:≥ 32 位随机串,生成方式见 `.env.example` - `DB_HOST` / `DB_PORT` / `DB_USER` / `DB_PASSWORD` / `DB_NAME`:数据库连接 初始管理员(仅首次启动、库中无管理员时生效): - `ADMIN_USER`:默认 `admin` - `ADMIN_PASS`:**留空(推荐)** → 创建 `admin / admin`,客户首次登录后系统强制要求修改密码, 改掉之前除改密外的一切后台功能不可用;显式填写则按强口令校验(≥ 8 位,弱口令拒绝启动) 其余常用项:`APP_PORT`(默认 8080)、`ADMIN_PATH`(后台入口,默认 `/admin`,建议改成不易猜的路径)、`ADMIN_API_PREFIX`(后台接口前缀,默认 `/api/admin`)、`TRUSTED_PROXIES`(限流/反垃圾的客户端 IP 来源,按部署形态填写)。 ### 3. 前端配置 不创建 `admin/.env` 时,前端以占位符构建,后台入口路径由服务端在运行期注入 (来自 `.env` 或后台设置),改路径无需重新构建前端,部署后也能在后台修改。 若在 `admin/.env` 写死真实路径(旧模式),则产物与路径绑定,必须保持两边同步, 否则会出现“页面能打开但 JS 全 404 白屏”: | 后端 `.env` | 前端 `admin/.env` | | ------------------ | ------------------------ | | `ADMIN_PATH` | `VITE_BASE_URL` | | `ADMIN_API_PREFIX` | `VITE_API_URL_PREFIX` | > 旧模式下改完任一边都要重新构建前端(Vite `base` 在编译期写进产物)。 ### 4. 启动(前后端一体) ```bash cd backend ./backend/dev.sh # 检查并构建前端产物 → 编译 Go → 前台运行 ``` - 公开站:`http://localhost:8080/` - 后台:`http://localhost:8080/`(如 `/admin` 或 `.env` 中自定义路径) `./backend/dev.sh` 会在编译前比对前端源码与 `web/admin/dist` 的时间戳,产物陈旧时自动先跑一次 `npm run build`,避免“改了代码没生效”。 其他参数: - `./backend/dev.sh --watch`:用 `air` 热重载(改 Go 代码自动重编译重启,需先 `./backend/setup-wsl.sh`) - `./backend/dev.sh --force-web`:强制重建前端 - `./backend/dev.sh --skip-web`:跳过前端构建(明确接受可能用旧产物) ### 5. 前端热更新(可选) ```bash cd admin npm install npm run dev # Vite 开发服务器 :3002,已配置代理把 /api 与 /uploads 转发到后端 :8080 ``` 后端需单独运行(`go run ./cmd/server` 或 `./backend/dev.sh --skip-web`)。注意 `go:embed all:web/admin/dist` 要求 `dist` 目录存在,首次请先构建一次前端。 ## 部署与运维 发布形态是单个二进制 / 单个镜像(应用与全部静态资源已编译期嵌入),详细步骤按场景拆到两篇文档: | 场景 | 文档 | | --- | --- | | Docker 一键部署、MySQL 内存档位、升级与备份 | [docs/deployment.md](docs/deployment.md) | | 宝塔 / 1Panel 面板源码部署、端口域名与反向代理 | 同上 | | 交叉编译 Linux 二进制、`deploy-dev.sh`、`systemd` 托管 | 同上 | | 下载预编译二进制发行版(Gitee Release)与校验 | 同上,见“二进制发行版” | | Docker 一行命令升级(`kycms 6` / `update.sh`) | 同上,见“升级与备份” | | `kycms` 管理工具(状态 / 重启 / 备份 / 改端口) | [docs/operations.md](docs/operations.md) | | TOTP 丢失、后台入口自救、常见故障排查 | 同上 | ## 常见问题与故障处理 | 问题 | 处理 | | --- | --- | | **二次验证(TOTP)恢复**:唯一超管丢了动态码 | 用 `reset-admin-totp` 子命令自救,见 [运维与故障处理](docs/operations.md) | | 后台入口改错进不去 | `reset-admin-path` 清除自定义路径,见 [部署指南](docs/deployment.md) | | 后台页面能打开但 JS 全 404 白屏 | 旧模式下前后端路径变量不同步,见[前端配置](#本地开发) | | 服务拒绝启动 / 前端产物没更新 | 检查 `JWT_SECRET`、弱口令与 `dev.sh` 产物新鲜度,见[本地开发](#本地开发) | 完整排障清单见 [docs/operations.md](docs/operations.md) 的“常见问题”。 ## 文档索引 | 文档 | 内容 | | --- | --- | | [docs/deployment.md](docs/deployment.md) | 部署形态、构建、升级备份、端口与反代 | | [docs/operations.md](docs/operations.md) | 管理工具、TOTP 恢复、常见问题 | | [docs/design/README.md](docs/design/README.md) | 设计背景与取舍归档(路由、静态资源、反垃圾等) | | [docs/THEME-API.md](docs/THEME-API.md) | 主题包结构、模板函数与对外契约 | | [docs/COMMENT-STYLE.md](docs/COMMENT-STYLE.md) | 代码注释约定 | | [CONTRIBUTING.md](CONTRIBUTING.md) | 授权条款、分支与合并、提交规范、本地自检、PR 建议 | | [docs/RELEASING.md](docs/RELEASING.md) | 维护者发版流程:本地构建镜像与发行包、推送顺序、实测 | | [SECURITY.md](SECURITY.md) | 漏洞报告流程与站点管理员自查清单 | | [CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md) | 社区行为准则 | | [CHANGELOG.md](CHANGELOG.md) | 版本变更记录 | ## 测试 后端有较完整的单元测试,覆盖路由、中间件、服务层等: ```bash cd backend go test ./... ``` 前端目前没有自动化测试(`admin/package.json` 的 `test` 为占位)。 提交前的完整自检见 [CONTRIBUTING.md](CONTRIBUTING.md) 中的 `./scripts/ci.sh`。 ## 备注 - 所有静态资源(后台 SPA、公开站点模板、cwebp 二进制)均在**编译期**嵌入,生产环境无需额外静态目录。 - `backend/uploads/`、`backend/tmp/`、`admin/node_modules/`、`admin/dist/`、`*.exe`、`*.log` 等已被 `.gitignore` 忽略,不会进版本库。 ## 贡献与反馈 欢迎提交 issue 与 PR。本项目**不需要签署 CLA,也不要求 `Signed-off-by`** —— 提交即表示该贡献 以 AGPL-3.0 授权,著作权仍归你。细节与本地自检命令见 [CONTRIBUTING.md](CONTRIBUTING.md)。 - 功能建议与缺陷反馈:仓库 issue - 代码贡献:Pull Request,流程与提交规范见 [CONTRIBUTING.md](CONTRIBUTING.md) - 安全漏洞:**不要公开提 issue**,按 [SECURITY.md](SECURITY.md) 私下报告 - 社区交流的行为准则:见 [CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md) ## 许可证 本项目以 [GNU Affero 通用公共许可证第 3 版](LICENSE)(AGPL-3.0)发布,并附 [主题与模板附加许可](LICENSE-EXCEPTION.md)。 Copyright (c) 2026 广州锦杨科技有限公司 (Guangzhou Kamyang Technology Co., Ltd.) ### 简单说,能做什么 以下是便于理解的概括,**以许可证正文为准**: | 你想做的事 | 是否允许 | | --- | --- | | 给自己搭个人博客、公司官网、内部站点 | ✅ 免费,无需告知我们 | | 修改代码自用 | ✅ | | 把改动开源,或提交 PR 回上游 | ✅ 欢迎 | | 为主题写样式、发布主题(含**收费主题**) | ✅ 见主题例外条款 | | 分发修改版(含对外提供的托管服务) | ⚠️ 可以,但修改后的核心代码须以 AGPL-3.0 公开 | | 做成闭源商业发行版 / 闭源 SaaS | ❌ 与 AGPL-3.0 冲突 | 核心结论是“**主题自由,核心开源**”:第三方主题不因使用本项目的主题接口而被视为衍生作品, 可自行选择许可证;但本项目自身的代码(含 `backend/`、`admin/` 与内置默认主题 `templates/`) 被修改并分发时,必须同样以 AGPL-3.0 开源。 还有一条重要的边界:**未修改的版本自用不受任何约束**(AGPL 第 13 条只约束修改版), 所以个人博主、公司内部站点都可以直接跑,不必公开任何东西。 ### 第三方组件 随附二进制的授权说明见 [THIRD-PARTY-NOTICES.md](THIRD-PARTY-NOTICES.md),其中包括内置的 `cwebp`(Google libwebp,BSD-3-Clause)、前端脚手架 `tdesign-starter-cli` 以及全部依赖的许可证清单。 AGPL-3.0 只覆盖本项目自身创作的代码,不会改变这些组件的原有许可。 ### 随二进制下发 上述文件都编译进了可执行文件,只拿到二进制的人也能读到(无需仓库): - `GET /license.txt` - `GET /license-exception.txt` - `GET /third-party-notices.txt` > 三个文件在仓库根目录与 `backend/` 下各存一份:托管平台通常只在仓库根目录识别 LICENSE 并展示许可徽章, > 而 `go:embed` 不允许 `..` 跨目录引用。**修改时必须同步两份**,`go test ./...` 会逐字节比对, > 漏改会直接测试失败,避免出现“仓库里写 AGPL、发出去的二进制里是旧内容”的静默漂移。