fix
This commit is contained in:
@@ -11,10 +11,7 @@ OPS 是面向医院信息化场景的开发运维一体化平台,首期交付
|
||||
| `docs/integrated-ops-platform-blueprint-design.md` | 平台蓝图、分期路线和审查结论。 |
|
||||
| `docs/首期验收矩阵.md` | OPS 需求到演示路径、数据准备、通过标准和证据的映射。 |
|
||||
| `docs/首期数据模型与状态机.md` | 第 1 阶段核心模型、状态机和存储分工。 |
|
||||
| `docs/首期项目架构数据模型与接口设计.md` | 第 1 阶段可编码的项目架构、数据模型和 REST API 设计。 |
|
||||
| `docs/首期UI状态覆盖.md` | 第 1 阶段页面状态覆盖要求。 |
|
||||
| `docs/P1故障救援策略.md` | 采集、解析、通知、派单失败的救援策略。 |
|
||||
| `docs/P1测试计划.md` | 第 1 阶段后端、前端和端到端测试计划。 |
|
||||
| `docs/本地开发与验收部署说明.md` | 本地开发、联调验收和 Linux/麒麟部署边界。 |
|
||||
| `docs/H3C华三首批接入调研.md` | H3C/华三首批接入基线和现场确认表。 |
|
||||
| `docs/国产时序数据库选型验证.md` | TDengine、Apache IoTDB、openGemini 选型验证。 |
|
||||
|
||||
15
TODOS.md
15
TODOS.md
@@ -30,33 +30,30 @@
|
||||
|
||||
## P1
|
||||
|
||||
- [x] 定义采集失败、Trap/Syslog 解析失败、通知失败、派单失败的错误与救援策略。
|
||||
- [] 定义采集失败、Trap/Syslog 解析失败、通知失败、派单失败的错误与救援策略。
|
||||
- 原因:一体化运维平台自身故障不能静默,否则验收时无法证明平台可靠性。
|
||||
- 验收:每类失败都有重试、降级、用户提示、日志、审计和测试要求。
|
||||
- 产物:`docs/P1故障救援策略.md`。
|
||||
|
||||
- [x] 为第 1 阶段建立后端与前端测试计划。
|
||||
- [] 为第 1 阶段建立后端与前端测试计划。
|
||||
- 原因:当前仓库尚无实际 `server/`、`web/` 工程,测试策略需要先指导实现。
|
||||
- 验收:后端包含单元、接口、SQLite 内存库测试;前端包含类型检查、状态渲染和核心 E2E。
|
||||
- 产物:`docs/P1测试计划.md`。
|
||||
|
||||
- [x] 使用 gstack 工程评审口径梳理首期架构、数据模型和接口设计。
|
||||
- [] 使用 gstack 工程评审口径梳理首期架构、数据模型和接口设计。
|
||||
- 原因:P0/P1 文档已形成验收、状态机、UI 状态、救援和测试计划,但后续初始化 `server/`、`web/` 前还需要一份可编码的模块边界和 REST API 规格。
|
||||
- 验收:文档包含后端/前端模块划分、核心数据流、数据模型、统一响应、错误码、API 路由、前端状态映射和实施顺序。
|
||||
- 产物:`docs/首期项目架构数据模型与接口设计.md`。
|
||||
|
||||
- [x] 区分本地开发命令和验收部署说明。
|
||||
- [] 区分本地开发命令和验收部署说明。
|
||||
- 原因:本地开发和调试使用 Windows PowerShell;会议已确认验收部署需要面向 Linux 与麒麟系统,模板 README 不能直接成为交付文档。
|
||||
- 验收:实际 `server/`、`web/` 文档提供 Windows PowerShell 本地开发路径;`deploy/` 提供 Linux/麒麟部署、迁移、回滚和烟测说明,且不包含真实凭据。
|
||||
- 产物:`docs/本地开发与验收部署说明.md`、`deploy/README.md`。
|
||||
|
||||
- [x] 完成 H3C/华三设备首批接入调研。
|
||||
- [] 完成 H3C/华三设备首批接入调研。
|
||||
- 原因:会议确认现场设备以 H3C/华三为主,第 1 阶段应优先适配该品牌常见指标、接口状态和 Trap/Syslog 样例。
|
||||
- 验收:明确首批设备型号、SNMP 版本、OID 清单、Trap 字典、Syslog 样例、账号权限和网络连通性。
|
||||
- 产物:`docs/H3C华三首批接入调研.md`。
|
||||
- 风险:仓库现有资料未提供现场具体型号、SNMP 版本、真实 Trap/Syslog 样例和账号权限;文档已提供首批接入基线和现场确认表,正式验收前必须由院方或现场工程师补齐。
|
||||
|
||||
- [x] 完成国产/国内生态时序数据库选型验证。
|
||||
- [] 完成国产/国内生态时序数据库选型验证。
|
||||
- 原因:高频指标和采集样本不应全部压入 PostgreSQL,需要选型 TDengine、Apache IoTDB、openGemini 或其他合适产品。
|
||||
- 验收:形成选型记录,覆盖 Linux/麒麟部署、Go 连接方式、批量写入、范围查询、聚合、降采样、保留策略、备份恢复和授权风险。
|
||||
- 产物:`docs/国产时序数据库选型验证.md`。
|
||||
|
||||
@@ -80,7 +80,7 @@
|
||||
### 5.1 处理流程
|
||||
|
||||
```text
|
||||
-----------+ +-------------+ +----------------+
|
||||
+-----------+ +-------------+ +----------------+
|
||||
| 接收原文 | ---> | 写 raw_events | ---> | 尝试字典/规则解析 |
|
||||
+-----------+ +-------------+ +----------------+
|
||||
|
|
||||
@@ -170,4 +170,3 @@
|
||||
| 页面截图 | 资源详情、未解析事件池、通知记录、派单失败提示。 |
|
||||
| 日志 | 能按 `traceId` 查询采集、解析、通知、派单链路。 |
|
||||
| 数据库记录 | `collector_runs`、`raw_events`、`notification_records`、`ticket_transitions` 有对应记录。 |
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
## 1. 文档目标
|
||||
|
||||
本文定义 OPS 第 1 阶段后端、前端和端到端测试范围。当前仓库尚未初始化 `server/`、`web/`,本文先作为编码前测试规格,后续实现必须按本文补齐测试。
|
||||
本文定义 OPS 第 1 阶段后端、前端和端到端测试范围。当前仓库尚未保留实际 `server/`、`web/` 工程;本文作为编码和联调前测试规格,后续实现必须按本文补齐测试。
|
||||
|
||||
## 2. 测试分层
|
||||
|
||||
@@ -73,7 +73,7 @@
|
||||
|
||||
## 6. 本地验证命令
|
||||
|
||||
后端初始化后至少运行:
|
||||
后端至少运行:
|
||||
|
||||
```powershell
|
||||
Set-Location .\server
|
||||
@@ -111,4 +111,3 @@ pnpm build
|
||||
- 前端核心页面必须覆盖 `docs/首期UI状态覆盖.md` 中列出的状态。
|
||||
- 端到端测试必须能证明主闭环,不得只校验静态页面存在。
|
||||
- 测试不能使用 mock 数据库替代真实数据库行为。
|
||||
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
<!-- /autoplan restore point: C:\Users\27105\.gstack\projects\ops\main-autoplan-restore-20260621-151741.md -->
|
||||
<!-- /autoplan restore point: C:\Users\27105\.gstack\projects\ops\main-autoplan-restore-20260621-181451.md -->
|
||||
<!-- /autoplan restore point: C:\Users\27105\.gstack\projects\ops\main-autoplan-restore-20260621-180424.md -->
|
||||
<!-- /autoplan restore point: C:\Users\27105\.gstack\projects\ops\main-autoplan-restore-20260621-151741.md -->
|
||||
# 一体化运维平台完整蓝图与分期落地方案
|
||||
|
||||
生成来源:`/office-hours`
|
||||
@@ -838,4 +840,3 @@
|
||||
**审批结论:**
|
||||
- 用户已选择 A:按当前方案批准蓝图方向。后续进入 P1 待办处理与第 1 阶段实施准备;Git 远程凭据风险已按用户要求忽略,不作为当前交付阻塞项。
|
||||
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -4,7 +4,7 @@
|
||||
|
||||
本文区分本地开发、联调验收和 Linux/麒麟部署三类场景,避免把模板 README 直接作为交付部署手册。
|
||||
|
||||
当前仓库尚未初始化 `server/` 和 `web/`。后续实际工程创建后,应在对应目录补充更细的运行说明。
|
||||
当前仓库尚未保留实际 `server/` 和 `web/` 工程。后续实际工程创建后,应在对应目录补充更细的运行说明。
|
||||
|
||||
## 2. 场景边界
|
||||
|
||||
@@ -18,16 +18,16 @@
|
||||
|
||||
| 目录 | 职责 | 状态 |
|
||||
| --- | --- | --- |
|
||||
| `server/` | 实际后端工程,基于 `templates/server_sample/` 初始化 | 尚未创建 |
|
||||
| `server/` | 实际后端工程,基于 `templates/server_sample/` 初始化后继续改造 | 尚未创建 |
|
||||
| `web/` | 实际前端工程,基于 `templates/front_sample/standard` 初始化 | 尚未创建 |
|
||||
| `deploy/` | 部署、迁移、回滚、烟测说明和配置示例 | 已规划 |
|
||||
| `deploy/` | 部署、迁移、回滚、烟测说明和配置示例 | 已创建 |
|
||||
| `docs/` | 需求、架构、验收和测试文档 | 已存在 |
|
||||
|
||||
模板目录默认只读,不作为最终交付目录。
|
||||
|
||||
## 4. 初始化实际工程
|
||||
|
||||
后端初始化:
|
||||
后端已初始化。若在干净仓库中重新初始化,可参考:
|
||||
|
||||
```powershell
|
||||
Copy-Item -LiteralPath .\templates\server_sample -Destination .\server -Recurse
|
||||
@@ -43,7 +43,7 @@ Copy-Item -LiteralPath .\templates\front_sample\standard -Destination .\web -Rec
|
||||
|
||||
| 检查项 | 要求 |
|
||||
| --- | --- |
|
||||
| 配置示例 | 只提交 `etc/*.example.yaml` 或 `.env.example`,不提交真实密码。 |
|
||||
| 配置示例 | 只提交 `etc/*.example.yaml`、`*.example.yaml` 或 `.env.example`,不提交真实密码。 |
|
||||
| 目录结构 | 后端延续 `cmd/`、`internal/config/`、`internal/logic/`、`internal/models/`、`internal/routers/`。 |
|
||||
| 前端结构 | API 放入 `src/api/`,页面放入 `src/views/`,状态放入 Pinia。 |
|
||||
| 模板引用 | 业务代码不直接写回 `templates/`。 |
|
||||
@@ -68,6 +68,8 @@ Set-Location .\server
|
||||
go run .\cmd\cli\main.go migrate
|
||||
```
|
||||
|
||||
后端重新初始化后,应只提交 `server/etc/*.example.yaml` 或等价 `.example` 配置文件。本地真实配置应复制为 `server/etc/ops_dev.yaml` 等文件后再填写,并在 `server/.gitignore` 中排除。
|
||||
|
||||
后端本地配置要求:
|
||||
|
||||
| 配置 | 要求 |
|
||||
|
||||
@@ -1,113 +0,0 @@
|
||||
name: Actions
|
||||
run-name: ${{ gitea.actor }} 🚀
|
||||
on:
|
||||
push:
|
||||
tags:
|
||||
- 'v*'
|
||||
|
||||
|
||||
jobs:
|
||||
Explore-Gitea-Actions:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Clean temp directory
|
||||
run: rm -rf *
|
||||
# 设置 Go 环境
|
||||
- name: 设置 Go
|
||||
uses: https://git.apinb.com/github/setup-go@v5
|
||||
with:
|
||||
go-version: '1.24.6'
|
||||
tag_name: ${{ gitea.ref }}
|
||||
release_name: ${{ gitea.ref }}
|
||||
|
||||
- run: echo "🎉 The job was automatically triggered by a ${{ gitea.event_name }} event."
|
||||
- run: echo "🔎 The name of your branch is ${{ gitea.ref }} and your repository is ${{ gitea.repository_owner }}."
|
||||
- name: Extract repository name
|
||||
id: extract_repo
|
||||
run: |
|
||||
repo_name=$(echo ${{ gitea.repository }} | cut -d'/' -f2)
|
||||
echo "Repository name: $repo_name"
|
||||
echo "::set-output name=repo_name::$repo_name"
|
||||
|
||||
# 提取tag标签名称
|
||||
- name: Extract tag name
|
||||
id: extract_tag
|
||||
run: echo "::set-output name=tag_name::$(echo ${{ gitea.ref }} | sed 's/^refs\/tags\///')"
|
||||
- run: echo "🏷 The tag name is ${{ steps.extract_tag.outputs.tag_name }}."
|
||||
|
||||
# 检查出代码
|
||||
- name: Check out repository code
|
||||
uses: https://git.apinb.com/github/checkout@v4
|
||||
|
||||
# 缓存 Go 依赖项
|
||||
- name: Cache Go modules
|
||||
uses: https://git.apinb.com/github/cache@v4
|
||||
with:
|
||||
path: |
|
||||
~/.cache/go-build
|
||||
~/go/pkg/mod
|
||||
key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }}
|
||||
restore-keys: |
|
||||
${{ runner.os }}-go-
|
||||
|
||||
|
||||
- name: set last version
|
||||
run: |
|
||||
echo "export srv_version='${{ steps.extract_tag.outputs.tag_name }}';export srv_name='${{ steps.extract_repo.outputs.repo_name }}'" > ${{ gitea.repository_owner }}-${{ steps.extract_repo.outputs.repo_name }}_last_version.sh
|
||||
- run: go env -w GOPROXY=https://goproxy.cn
|
||||
- run: go env -w GOPRIVATE=git.apinb.com/*
|
||||
- run: go env -w GONOPROXY=git.apinb.com/*
|
||||
- run: go env -w GOINSECURE=git.apinb.com/*
|
||||
- run: go env -w GONOSUMDB=git.apinb.com/*
|
||||
- run: go env -w GOEXPERIMENT=jsonv2
|
||||
- run: go build -o ${{ gitea.repository_owner }}-${{ steps.extract_repo.outputs.repo_name }} ./cmd/main/main.go
|
||||
- run: echo "🍏 This job's status is ${{ job.status }}."
|
||||
- name: upload version.sh to minio oss - 1
|
||||
uses: https://git.apinb.com/github/minio-upload@main
|
||||
with:
|
||||
endpoint: http://172.24.0.20:9000
|
||||
access-key-id: 9jtPPB7wwJpe5R2164bS
|
||||
access-key-secret: ho9LYavUIGdkf0b50aaOduIA4zdx8FQFWpUYx30p
|
||||
bucket: reles
|
||||
source: ./${{ gitea.repository_owner }}-${{ steps.extract_repo.outputs.repo_name }}_last_version.sh
|
||||
insecure: true
|
||||
recursive: true
|
||||
|
||||
- name: upload bin to minio oss - 2
|
||||
uses: https://git.apinb.com/github/minio-upload@main
|
||||
with:
|
||||
endpoint: http://172.24.0.20:9000
|
||||
access-key-id: 9jtPPB7wwJpe5R2164bS
|
||||
access-key-secret: ho9LYavUIGdkf0b50aaOduIA4zdx8FQFWpUYx30p
|
||||
bucket: reles
|
||||
source: ./${{ gitea.repository_owner }}-${{ steps.extract_repo.outputs.repo_name }}
|
||||
target: /${{ gitea.repository_owner }}-${{ steps.extract_repo.outputs.repo_name }}@${{ steps.extract_tag.outputs.tag_name }}/
|
||||
insecure: true
|
||||
recursive: false
|
||||
|
||||
- name: upload etc/ to minio oss - 3
|
||||
uses: https://git.apinb.com/github/minio-upload@main
|
||||
with:
|
||||
endpoint: http://172.24.0.20:9000
|
||||
access-key-id: 9jtPPB7wwJpe5R2164bS
|
||||
access-key-secret: ho9LYavUIGdkf0b50aaOduIA4zdx8FQFWpUYx30p
|
||||
bucket: reles
|
||||
source: ./etc
|
||||
target: /${{ gitea.repository_owner }}-${{ steps.extract_repo.outputs.repo_name }}@${{ steps.extract_tag.outputs.tag_name }}/
|
||||
insecure: true
|
||||
recursive: true
|
||||
|
||||
- name: upload swagger to minio oss - 4
|
||||
uses: https://git.apinb.com/github/minio-upload@main
|
||||
with:
|
||||
endpoint: http://172.24.0.20:9000
|
||||
access-key-id: 9jtPPB7wwJpe5R2164bS
|
||||
access-key-secret: ho9LYavUIGdkf0b50aaOduIA4zdx8FQFWpUYx30p
|
||||
bucket: reles
|
||||
source: ./swagger
|
||||
target: /${{ gitea.repository_owner }}-${{ steps.extract_repo.outputs.repo_name }}@${{ steps.extract_tag.outputs.tag_name }}/
|
||||
insecure: true
|
||||
recursive: true
|
||||
|
||||
- name: upload success
|
||||
run: echo "build&upload success."
|
||||
35
server/.gitignore
vendored
35
server/.gitignore
vendored
@@ -1,35 +0,0 @@
|
||||
# ---> Go
|
||||
# If you prefer the allow list template instead of the deny list, see community template:
|
||||
# https://github.com/github/gitignore/blob/main/community/Golang/Go.AllowList.gitignore
|
||||
#
|
||||
# Binaries for programs and plugins
|
||||
*.exe
|
||||
*.exe~
|
||||
*.dll
|
||||
*.so
|
||||
*.dylib
|
||||
|
||||
# Test binary, built with `go test -c`
|
||||
*.test
|
||||
|
||||
# Output of the go coverage tool, specifically when used with LiteIDE
|
||||
*.out
|
||||
|
||||
# Dependency directories (remove the comment below to include it)
|
||||
# vendor/
|
||||
builds/
|
||||
build/
|
||||
logs/
|
||||
pkg/
|
||||
cache/
|
||||
tmp/
|
||||
.builds/
|
||||
.build/
|
||||
.logs/
|
||||
.pkg/
|
||||
.cache/
|
||||
.tmp/
|
||||
|
||||
# Go workspace file
|
||||
go.work
|
||||
|
||||
@@ -1,27 +0,0 @@
|
||||
.PHONY: build run cli migrate lint tidy clean
|
||||
|
||||
BINARY_NAME=sample
|
||||
CLI_NAME=sample-cli
|
||||
|
||||
build:
|
||||
go build -o build/$(BINARY_NAME) ./cmd/main/main.go
|
||||
go build -o build/$(CLI_NAME) ./cmd/cli/main.go
|
||||
|
||||
run:
|
||||
go run ./cmd/main/main.go
|
||||
|
||||
cli:
|
||||
go run ./cmd/cli/main.go $(ARGS)
|
||||
|
||||
migrate:
|
||||
go run ./cmd/cli/main.go migrate
|
||||
|
||||
lint:
|
||||
go vet ./...
|
||||
go fmt ./...
|
||||
|
||||
tidy:
|
||||
go mod tidy
|
||||
|
||||
clean:
|
||||
rm -rf build/
|
||||
183
server/README.md
183
server/README.md
@@ -1,183 +0,0 @@
|
||||
# Sample
|
||||
|
||||
基于 [BSM-SDK Core](https://git.apinb.com/bsm-sdk/core) 的 OPS 微服务样板项目,演示 Gin HTTP 服务、配置管理、数据库(GORM)、Redis 缓存、JWT 鉴权与标准分层架构,可作为新服务的起始模板。
|
||||
|
||||
## 功能概览
|
||||
|
||||
| 模块 | 说明 |
|
||||
|------|------|
|
||||
| 健康检查 | `HEAD /` 与 `GET /Sample/v1/ping/hello` |
|
||||
| 示例 CRUD | `Sample/v1/sample/demo` 完整增删改查(JWT 鉴权) |
|
||||
| 数据模型 | `sample_demo` 表,启动时自动迁移 |
|
||||
| CLI | `migrate` 数据库迁移、`version` 版本查看 |
|
||||
|
||||
## 项目结构
|
||||
|
||||
```
|
||||
sample/
|
||||
├── cmd/
|
||||
│ ├── main/ # HTTP 服务入口
|
||||
│ └── cli/ # 命令行工具
|
||||
├── internal/
|
||||
│ ├── config/ # 配置加载与校验
|
||||
│ ├── impl/ # 基础设施实例(DB、Redis、缓存、日志)
|
||||
│ ├── logic/ # 业务逻辑层
|
||||
│ │ ├── ping/ # 健康检查
|
||||
│ │ └── demo/ # 示例 CRUD
|
||||
│ ├── models/ # 数据模型与数据库操作
|
||||
│ └── routers/ # 路由注册
|
||||
├── etc/ # 配置文件(按环境区分)
|
||||
├── scripts/ # 构建与工具脚本
|
||||
├── test/ # HTTP 接口测试文件
|
||||
└── Makefile
|
||||
```
|
||||
|
||||
## 环境要求
|
||||
|
||||
- Go 1.26+
|
||||
- PostgreSQL(或修改配置使用 MySQL)
|
||||
- Redis
|
||||
- 可访问 `git.apinb.com` 私有仓库
|
||||
|
||||
## 快速开始
|
||||
|
||||
### 1. 配置 Go 私有仓库
|
||||
|
||||
```bash
|
||||
go env -w GOPRIVATE=git.apinb.com/*
|
||||
go env -w GONOPROXY=git.apinb.com/*
|
||||
go env -w GOINSECURE=git.apinb.com/*
|
||||
go env -w GONOSUMDB=git.apinb.com/*
|
||||
```
|
||||
|
||||
### 2. 准备配置文件
|
||||
|
||||
配置文件命名规则:`{服务键}_{运行模式}.yaml`,本项目服务键为 `Sample`,开发模式对应 `etc/sample_dev.yaml`。
|
||||
|
||||
```bash
|
||||
cp etc/sample_dev.yaml.example etc/sample_dev.yaml
|
||||
# 编辑 etc/sample_dev.yaml,填入数据库与 Redis 连接信息
|
||||
```
|
||||
|
||||
### 3. 设置环境变量
|
||||
|
||||
```bash
|
||||
# Linux / macOS
|
||||
export BSM_RuntimeMode=dev
|
||||
export BSM_Prefix=$(pwd)/etc
|
||||
export BSM_JwtSecretKey=your-secret-key
|
||||
|
||||
# Windows PowerShell
|
||||
$env:BSM_RuntimeMode="dev"
|
||||
$env:BSM_Prefix="$(pwd)/etc"
|
||||
$env:BSM_JwtSecretKey="your-secret-key"
|
||||
```
|
||||
|
||||
| 变量 | 说明 | 默认值 |
|
||||
|------|------|--------|
|
||||
| `BSM_RuntimeMode` | 运行模式:`dev` / `test` / `prod` | `dev` |
|
||||
| `BSM_Prefix` | 配置文件目录 | 开发模式为当前路径 |
|
||||
| `BSM_JwtSecretKey` | JWT 签名密钥 | SDK 内置默认值 |
|
||||
| `BSM_Workspace` | 工作空间标识 | `default` |
|
||||
|
||||
### 4. 安装依赖并启动
|
||||
|
||||
```bash
|
||||
go mod tidy
|
||||
make build # 或 go run ./cmd/main/main.go
|
||||
make run
|
||||
```
|
||||
|
||||
服务默认监听 `12426` 端口,启动成功后访问:
|
||||
|
||||
```bash
|
||||
curl http://127.0.0.1:12426/Sample/v1/ping/hello
|
||||
```
|
||||
|
||||
## API 接口
|
||||
|
||||
### 统一响应格式
|
||||
|
||||
```json
|
||||
{
|
||||
"code": 0,
|
||||
"message": "",
|
||||
"details": {},
|
||||
"timeseq": 1710000000000
|
||||
}
|
||||
```
|
||||
|
||||
### 匿名接口
|
||||
|
||||
| 方法 | 路径 | 说明 |
|
||||
|------|------|------|
|
||||
| `HEAD` | `/` | 健康检查 |
|
||||
| `GET` | `/Sample/v1/ping/hello` | Ping 测试 |
|
||||
|
||||
### 鉴权接口(JWT)
|
||||
|
||||
路由组:`/Sample/v1/sample`,请求头需携带 `Authorization: Bearer <token>`。
|
||||
|
||||
| 方法 | 路径 | 说明 |
|
||||
|------|------|------|
|
||||
| `POST` | `/Sample/v1/demo` | 创建示例数据 |
|
||||
| `GET` | `/Sample/v1/demo` | 分页列表(`page`、`size`) |
|
||||
| `GET` | `/Sample/v1/demo/:identity` | 按 identity 查询 |
|
||||
| `PUT` | `/Sample/v1/demo/:identity` | 更新 |
|
||||
| `DELETE` | `/Sample/v1/demo/:identity` | 删除 |
|
||||
|
||||
**创建请求示例:**
|
||||
|
||||
```json
|
||||
{
|
||||
"name": "Alice",
|
||||
"age": 25
|
||||
}
|
||||
```
|
||||
|
||||
## CLI 工具
|
||||
|
||||
```bash
|
||||
# 查看版本
|
||||
go run ./cmd/cli/main.go version
|
||||
|
||||
# 执行数据库自动迁移(模型定义见 internal/models)
|
||||
go run ./cmd/cli/main.go migrate
|
||||
```
|
||||
|
||||
也可使用 Makefile:
|
||||
|
||||
```bash
|
||||
make migrate
|
||||
make cli ARGS="version"
|
||||
```
|
||||
|
||||
## 开发与测试
|
||||
|
||||
```bash
|
||||
make lint # go vet + go fmt
|
||||
make tidy # go mod tidy
|
||||
```
|
||||
|
||||
接口测试文件位于 `test/` 目录,可使用 VS Code REST Client 或 IntelliJ HTTP Client 直接运行。
|
||||
|
||||
## 生产部署
|
||||
|
||||
### 构建
|
||||
|
||||
```bash
|
||||
./scripts/build.sh
|
||||
# 产物:build/sample、build/sample-cli
|
||||
```
|
||||
|
||||
### systemd
|
||||
|
||||
```bash
|
||||
cp etc/sample.service /etc/systemd/system/
|
||||
cp etc/sample.env.example /data/app/etc/sample.env
|
||||
# 编辑环境变量后
|
||||
systemctl enable sample
|
||||
systemctl start sample
|
||||
```
|
||||
|
||||
|
||||
@@ -1,42 +0,0 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
|
||||
"git.apinb.com/ops/sample/internal/config"
|
||||
"git.apinb.com/ops/sample/internal/impl"
|
||||
_ "git.apinb.com/ops/sample/internal/models"
|
||||
)
|
||||
|
||||
const (
|
||||
serviceKey = "Sample"
|
||||
version = "1.0.0"
|
||||
)
|
||||
|
||||
func main() {
|
||||
if len(os.Args) < 2 {
|
||||
printUsage()
|
||||
return
|
||||
}
|
||||
|
||||
switch os.Args[1] {
|
||||
case "version":
|
||||
fmt.Println("sample-cli", version)
|
||||
case "migrate":
|
||||
config.New(serviceKey)
|
||||
impl.NewImpl()
|
||||
fmt.Println("database migrate completed")
|
||||
default:
|
||||
fmt.Fprintf(os.Stderr, "unknown command: %s\n", os.Args[1])
|
||||
printUsage()
|
||||
os.Exit(1)
|
||||
}
|
||||
}
|
||||
|
||||
func printUsage() {
|
||||
fmt.Println("usage: sample-cli <command>")
|
||||
fmt.Println("commands:")
|
||||
fmt.Println(" version show cli version")
|
||||
fmt.Println(" migrate run database auto migrate")
|
||||
}
|
||||
@@ -1,74 +0,0 @@
|
||||
/**
|
||||
* @Author: david.yan(david.yan@qq.com)
|
||||
* @Date: 2021-11-26 15:25:03
|
||||
*/
|
||||
package main
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"net/http"
|
||||
"os"
|
||||
"os/signal"
|
||||
"syscall"
|
||||
"time"
|
||||
|
||||
"git.apinb.com/bsm-sdk/core/infra"
|
||||
"git.apinb.com/bsm-sdk/core/middleware"
|
||||
"git.apinb.com/bsm-sdk/core/printer"
|
||||
"git.apinb.com/ops/sample/internal/config"
|
||||
"git.apinb.com/ops/sample/internal/impl"
|
||||
"git.apinb.com/ops/sample/internal/routers"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
var (
|
||||
ServiceKey = "Sample"
|
||||
)
|
||||
|
||||
func main() {
|
||||
// 配置初始化
|
||||
config.New(ServiceKey)
|
||||
|
||||
// 创建实现层
|
||||
impl.NewImpl()
|
||||
|
||||
// 初始化Gin引擎
|
||||
app := gin.Default()
|
||||
|
||||
// 使用中间件
|
||||
middleware.Mode(app)
|
||||
app.Use(middleware.Cors())
|
||||
app.Use(gin.Recovery())
|
||||
|
||||
// 注册健康检查路由
|
||||
app.HEAD("/", infra.Health)
|
||||
|
||||
// 注册应用路由
|
||||
routers.Register(ServiceKey, app)
|
||||
|
||||
addr := fmt.Sprintf(":%s", config.Spec.Port)
|
||||
srv := &http.Server{Addr: addr, Handler: app}
|
||||
|
||||
go func() {
|
||||
if err := srv.ListenAndServe(); err != nil && err != http.ErrServerClosed {
|
||||
panic(err)
|
||||
}
|
||||
}()
|
||||
|
||||
printer.Success("[BSM - %s] Service Started At: %s", ServiceKey, addr)
|
||||
|
||||
quit := make(chan os.Signal, 1)
|
||||
signal.Notify(quit, syscall.SIGINT, syscall.SIGTERM)
|
||||
<-quit
|
||||
|
||||
printer.Info("[BSM - %s] Shutting down...", ServiceKey)
|
||||
|
||||
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
|
||||
defer cancel()
|
||||
if err := srv.Shutdown(ctx); err != nil {
|
||||
panic(err)
|
||||
}
|
||||
|
||||
printer.Success("[BSM - %s] Service stopped", ServiceKey)
|
||||
}
|
||||
@@ -1,5 +0,0 @@
|
||||
# systemd EnvironmentFile 示例,复制为 /data/app/etc/sample.env 后按需修改
|
||||
BSM_Workspace=default
|
||||
BSM_RuntimeMode=prod
|
||||
BSM_Prefix=/data/app
|
||||
BSM_JwtSecretKey=change-me-to-a-random-string
|
||||
@@ -1,16 +0,0 @@
|
||||
[Unit]
|
||||
Description=Sample Service
|
||||
|
||||
[Service]
|
||||
Type=simple
|
||||
Restart=always
|
||||
RestartSec=5s
|
||||
EnvironmentFile=/data/app/etc/sample.env
|
||||
ExecStart=/data/app/sample
|
||||
WorkingDirectory=/data/app/
|
||||
StandardOutput=file:/data/app/logs/sample.log
|
||||
StandardError=file:/data/app/logs/sample.error.log
|
||||
|
||||
|
||||
[Install]
|
||||
WantedBy=multi-user.target
|
||||
@@ -1,27 +0,0 @@
|
||||
Service: sample
|
||||
Port: 12426
|
||||
|
||||
Databases:
|
||||
Driver: postgres
|
||||
Source:
|
||||
- host=8.137.107.29 user=postgres password=Weidong2023~! dbname=sample_dev port=19432 sslmode=disable TimeZone=Asia/Shanghai
|
||||
|
||||
# cache DB的选择请在后面直接带参数,不带会自动HASH计算选择DB库。
|
||||
Cache: redis://null:Weidong2023~!@8.137.107.29:19379/0
|
||||
|
||||
# 是否启用微服务模式
|
||||
OnMicroService: false
|
||||
|
||||
# 微服务调用密钥
|
||||
SecretKey: 6ad9529688041483f458f8de11ed16ff
|
||||
|
||||
# Rpc:
|
||||
# fts:
|
||||
# Endpoint: https://api-v2.traingo.cn/fts/v2
|
||||
# SecretKey: 4ef05311358cd1c8f787281f08b38b1c
|
||||
|
||||
|
||||
# 链路追踪,性能监控,日志收集
|
||||
# APM:
|
||||
# Platform: elasticAPM
|
||||
# Endpoint: http://127.0.0.1:14268/api/traces
|
||||
@@ -1,27 +0,0 @@
|
||||
Service: sample
|
||||
Port: 12426
|
||||
|
||||
Databases:
|
||||
Driver: postgres
|
||||
Source:
|
||||
- host=8.137.107.29 user=postgres password=Weidong2023~! dbname=sample_prod port=19432 sslmode=disable TimeZone=Asia/Shanghai
|
||||
|
||||
# cache DB的选择请在后面直接带参数,不带会自动HASH计算选择DB库。
|
||||
Cache: redis://null:Weidong2023~!@8.137.107.29:19379/0
|
||||
|
||||
# 是否启用微服务模式
|
||||
OnMicroService: false
|
||||
|
||||
# 微服务调用密钥
|
||||
SecretKey: 6ad9529688041483f458f8de11ed16ff
|
||||
|
||||
# Rpc:
|
||||
# fts:
|
||||
# Endpoint: https://api-v2.traingo.cn/fts/v2
|
||||
# SecretKey: 4ef05311358cd1c8f787281f08b38b1c
|
||||
|
||||
|
||||
# 链路追踪,性能监控,日志收集
|
||||
# APM:
|
||||
# Platform: elasticAPM
|
||||
# Endpoint: http://127.0.0.1:14268/api/traces
|
||||
@@ -1,27 +0,0 @@
|
||||
Service: sample
|
||||
Port: 12426
|
||||
|
||||
Databases:
|
||||
Driver: postgres
|
||||
Source:
|
||||
- host=8.137.107.29 user=postgres password=Weidong2023~! dbname=sample_test port=19432 sslmode=disable TimeZone=Asia/Shanghai
|
||||
|
||||
# cache DB的选择请在后面直接带参数,不带会自动HASH计算选择DB库。
|
||||
Cache: redis://null:Weidong2023~!@8.137.107.29:19379/0
|
||||
|
||||
# 是否启用微服务模式
|
||||
OnMicroService: false
|
||||
|
||||
# 微服务调用密钥
|
||||
SecretKey: 6ad9529688041483f458f8de11ed16ff
|
||||
|
||||
# Rpc:
|
||||
# fts:
|
||||
# Endpoint: https://api-v2.traingo.cn/fts/v2
|
||||
# SecretKey: 4ef05311358cd1c8f787281f08b38b1c
|
||||
|
||||
|
||||
# 链路追踪,性能监控,日志收集
|
||||
# APM:
|
||||
# Platform: elasticAPM
|
||||
# Endpoint: http://127.0.0.1:14268/api/traces
|
||||
@@ -1,80 +0,0 @@
|
||||
module git.apinb.com/ops/sample
|
||||
|
||||
go 1.26.1
|
||||
|
||||
require (
|
||||
github.com/grpc-ecosystem/grpc-gateway/v2 v2.29.0 // indirect
|
||||
gorm.io/driver/mysql v1.6.0 // indirect
|
||||
)
|
||||
|
||||
require github.com/gin-gonic/gin v1.12.0
|
||||
|
||||
require github.com/patrickmn/go-cache v2.1.0+incompatible
|
||||
|
||||
require (
|
||||
filippo.io/edwards25519 v1.2.0 // indirect
|
||||
github.com/bytedance/gopkg v0.1.4 // indirect
|
||||
github.com/bytedance/sonic v1.15.2 // indirect
|
||||
github.com/bytedance/sonic/loader v0.5.1 // indirect
|
||||
github.com/cloudwego/base64x v0.1.7 // indirect
|
||||
github.com/coreos/go-semver v0.3.1 // indirect
|
||||
github.com/coreos/go-systemd/v22 v22.7.0 // indirect
|
||||
github.com/gabriel-vasile/mimetype v1.4.13 // indirect
|
||||
github.com/gin-contrib/cors v1.7.7 // indirect
|
||||
github.com/gin-contrib/sse v1.1.1 // indirect
|
||||
github.com/go-playground/locales v0.14.1 // indirect
|
||||
github.com/go-playground/universal-translator v0.18.1 // indirect
|
||||
github.com/go-playground/validator/v10 v10.30.3 // indirect
|
||||
github.com/goccy/go-json v0.10.6 // indirect
|
||||
github.com/goccy/go-yaml v1.19.2 // indirect
|
||||
github.com/gogo/protobuf v1.3.2 // indirect
|
||||
github.com/golang-jwt/jwt/v5 v5.3.1 // indirect
|
||||
github.com/golang/protobuf v1.5.4 // indirect
|
||||
github.com/json-iterator/go v1.1.12 // indirect
|
||||
github.com/klauspost/cpuid/v2 v2.3.0 // indirect
|
||||
github.com/leodido/go-urn v1.4.0 // indirect
|
||||
github.com/mattn/go-isatty v0.0.22 // indirect
|
||||
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
|
||||
github.com/modern-go/reflect2 v1.0.2 // indirect
|
||||
github.com/pelletier/go-toml/v2 v2.4.0 // indirect
|
||||
github.com/quic-go/qpack v0.6.0 // indirect
|
||||
github.com/quic-go/quic-go v0.60.0 // indirect
|
||||
github.com/skip2/go-qrcode v0.0.0-20200617195104-da1b6568686e // indirect
|
||||
github.com/twitchyliquid64/golang-asm v0.15.1 // indirect
|
||||
github.com/ugorji/go/codec v1.3.1 // indirect
|
||||
go.etcd.io/etcd/api/v3 v3.6.12 // indirect
|
||||
go.mongodb.org/mongo-driver/v2 v2.7.0 // indirect
|
||||
go.uber.org/atomic v1.11.0 // indirect
|
||||
go.uber.org/multierr v1.11.0 // indirect
|
||||
go.uber.org/zap v1.28.0 // indirect
|
||||
golang.org/x/arch v0.28.0 // indirect
|
||||
google.golang.org/genproto/googleapis/api v0.0.0-20260618152121-87f3d3e198d3 // indirect
|
||||
)
|
||||
|
||||
require (
|
||||
git.apinb.com/bsm-sdk/core v0.2.0
|
||||
github.com/cespare/xxhash/v2 v2.3.0 // indirect
|
||||
github.com/go-sql-driver/mysql v1.10.0 // indirect
|
||||
github.com/google/uuid v1.6.0 // indirect
|
||||
github.com/jackc/pgpassfile v1.0.0 // indirect
|
||||
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 // indirect
|
||||
github.com/jackc/pgx/v5 v5.10.0 // indirect
|
||||
github.com/jackc/puddle/v2 v2.2.2 // indirect
|
||||
github.com/jinzhu/inflection v1.0.0 // indirect
|
||||
github.com/jinzhu/now v1.1.5 // indirect
|
||||
github.com/oklog/ulid/v2 v2.1.1 // indirect
|
||||
github.com/redis/go-redis/v9 v9.20.1 // indirect
|
||||
go.etcd.io/etcd/client/pkg/v3 v3.6.12 // indirect
|
||||
go.etcd.io/etcd/client/v3 v3.6.12 // indirect
|
||||
golang.org/x/crypto v0.53.0 // indirect
|
||||
golang.org/x/net v0.56.0 // indirect
|
||||
golang.org/x/sync v0.21.0 // indirect
|
||||
golang.org/x/sys v0.46.0 // indirect
|
||||
golang.org/x/text v0.38.0 // indirect
|
||||
google.golang.org/genproto/googleapis/rpc v0.0.0-20260618152121-87f3d3e198d3 // indirect
|
||||
google.golang.org/grpc v1.81.1 // indirect
|
||||
google.golang.org/protobuf v1.36.11 // indirect
|
||||
gopkg.in/yaml.v3 v3.0.1 // indirect
|
||||
gorm.io/driver/postgres v1.6.0 // indirect
|
||||
gorm.io/gorm v1.31.1
|
||||
)
|
||||
227
server/go.sum
227
server/go.sum
@@ -1,227 +0,0 @@
|
||||
filippo.io/edwards25519 v1.2.0 h1:crnVqOiS4jqYleHd9vaKZ+HKtHfllngJIiOpNpoJsjo=
|
||||
filippo.io/edwards25519 v1.2.0/go.mod h1:xzAOLCNug/yB62zG1bQ8uziwrIqIuxhctzJT18Q77mc=
|
||||
git.apinb.com/bsm-sdk/core v0.2.0 h1:/e9yqpsbKBrRgMiGpS3KX2O4qDLxo5V5GpPSLNGxEKw=
|
||||
git.apinb.com/bsm-sdk/core v0.2.0/go.mod h1:E9T6Eboo/0Zb36BjkKbIgvFzq4fQ2Q8P/7y5zmYTI6Y=
|
||||
github.com/bsm/ginkgo/v2 v2.12.0 h1:Ny8MWAHyOepLGlLKYmXG4IEkioBysk6GpaRTLC8zwWs=
|
||||
github.com/bsm/ginkgo/v2 v2.12.0/go.mod h1:SwYbGRRDovPVboqFv0tPTcG1sN61LM1Z4ARdbAV9g4c=
|
||||
github.com/bsm/gomega v1.27.10 h1:yeMWxP2pV2fG3FgAODIY8EiRE3dy0aeFYt4l7wh6yKA=
|
||||
github.com/bsm/gomega v1.27.10/go.mod h1:JyEr/xRbxbtgWNi8tIEVPUYZ5Dzef52k01W3YH0H+O0=
|
||||
github.com/bytedance/gopkg v0.1.4 h1:oZnQwnX82KAIWb7033bEwtxvTqXcYMxDBaQxo5JJHWM=
|
||||
github.com/bytedance/gopkg v0.1.4/go.mod h1:v1zWfPm21Fb+OsyXN2VAHdL6TBb2L88anLQgdyje6R4=
|
||||
github.com/bytedance/sonic v1.15.2 h1:90H+rcF/FwLXwfB1cudOLq/je83n683Utf4Cbp0xHCo=
|
||||
github.com/bytedance/sonic v1.15.2/go.mod h1:mT2NbXunuaEbnZ+mRIX/vYqKISmgEuHFDI4UzmKx2SA=
|
||||
github.com/bytedance/sonic/loader v0.5.1 h1:Ygpfa9zwRCCKSlrp5bBP/b/Xzc3VxsAW+5NIYXrOOpI=
|
||||
github.com/bytedance/sonic/loader v0.5.1/go.mod h1:AR4NYCk5DdzZizZ5djGqQ92eEhCCcdf5x77udYiSJRo=
|
||||
github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UFvs=
|
||||
github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
||||
github.com/cloudwego/base64x v0.1.7 h1:NppS+Fgzg5ovhn4NkUXaDT3x9jldgH5ToMCqzBSi2zI=
|
||||
github.com/cloudwego/base64x v0.1.7/go.mod h1:Cu1PV9zfrSf7ET2tIbWbbEy7jO7HHJ13q4X2SQ8aWYg=
|
||||
github.com/coreos/go-semver v0.3.1 h1:yi21YpKnrx1gt5R+la8n5WgS0kCrsPp33dmEyHReZr4=
|
||||
github.com/coreos/go-semver v0.3.1/go.mod h1:irMmmIw/7yzSRPWryHsK7EYSg09caPQL03VsM8rvUec=
|
||||
github.com/coreos/go-systemd/v22 v22.7.0 h1:LAEzFkke61DFROc7zNLX/WA2i5J8gYqe0rSj9KI28KA=
|
||||
github.com/coreos/go-systemd/v22 v22.7.0/go.mod h1:xNUYtjHu2EDXbsxz1i41wouACIwT7Ybq9o0BQhMwD0w=
|
||||
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
|
||||
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/gabriel-vasile/mimetype v1.4.13 h1:46nXokslUBsAJE/wMsp5gtO500a4F3Nkz9Ufpk2AcUM=
|
||||
github.com/gabriel-vasile/mimetype v1.4.13/go.mod h1:d+9Oxyo1wTzWdyVUPMmXFvp4F9tea18J8ufA774AB3s=
|
||||
github.com/gin-contrib/cors v1.7.7 h1:Oh9joP463x7Mw72vhvJ61YQm8ODh9b04YR7vsOErD0Q=
|
||||
github.com/gin-contrib/cors v1.7.7/go.mod h1:K5tW0RkzJtWSiOdikXloy8VEZlgdVNpHNw8FpjUPNrE=
|
||||
github.com/gin-contrib/sse v1.1.1 h1:uGYpNwTacv5R68bSGMapo62iLTRa9l5zxGCps4hK6ko=
|
||||
github.com/gin-contrib/sse v1.1.1/go.mod h1:QXzuVkA0YO7o/gun03UI1Q+FTI8ZV/n5t03kIQAI89s=
|
||||
github.com/gin-gonic/gin v1.12.0 h1:b3YAbrZtnf8N//yjKeU2+MQsh2mY5htkZidOM7O0wG8=
|
||||
github.com/gin-gonic/gin v1.12.0/go.mod h1:VxccKfsSllpKshkBWgVgRniFFAzFb9csfngsqANjnLc=
|
||||
github.com/go-logr/logr v1.4.3 h1:CjnDlHq8ikf6E492q6eKboGOC0T8CDaOvkHCIg8idEI=
|
||||
github.com/go-logr/logr v1.4.3/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY=
|
||||
github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag=
|
||||
github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE=
|
||||
github.com/go-playground/assert/v2 v2.2.0 h1:JvknZsQTYeFEAhQwI4qEt9cyV5ONwRHC+lYKSsYSR8s=
|
||||
github.com/go-playground/assert/v2 v2.2.0/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4=
|
||||
github.com/go-playground/locales v0.14.1 h1:EWaQ/wswjilfKLTECiXz7Rh+3BjFhfDFKv/oXslEjJA=
|
||||
github.com/go-playground/locales v0.14.1/go.mod h1:hxrqLVvrK65+Rwrd5Fc6F2O76J/NuW9t0sjnWqG1slY=
|
||||
github.com/go-playground/universal-translator v0.18.1 h1:Bcnm0ZwsGyWbCzImXv+pAJnYK9S473LQFuzCbDbfSFY=
|
||||
github.com/go-playground/universal-translator v0.18.1/go.mod h1:xekY+UJKNuX9WP91TpwSH2VMlDf28Uj24BCp08ZFTUY=
|
||||
github.com/go-playground/validator/v10 v10.30.3 h1:4MU6YkEwx7GbcPJOZxrtbu+QfF3pJLJuaYTeAH0DYy8=
|
||||
github.com/go-playground/validator/v10 v10.30.3/go.mod h1:4Axh7oCNGcoGkqLoE4YWt6n20mcEIsPRlB7vPk3lpyc=
|
||||
github.com/go-sql-driver/mysql v1.10.0 h1:Q+1LV8DkHJvSYAdR83XzuhDaTykuDx0l6fkXxoWCWfw=
|
||||
github.com/go-sql-driver/mysql v1.10.0/go.mod h1:M+cqaI7+xxXGG9swrdeUIoPG3Y3KCkF0pZej+SK+nWk=
|
||||
github.com/goccy/go-json v0.10.6 h1:p8HrPJzOakx/mn/bQtjgNjdTcN+/S6FcG2CTtQOrHVU=
|
||||
github.com/goccy/go-json v0.10.6/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M=
|
||||
github.com/goccy/go-yaml v1.19.2 h1:PmFC1S6h8ljIz6gMRBopkjP1TVT7xuwrButHID66PoM=
|
||||
github.com/goccy/go-yaml v1.19.2/go.mod h1:XBurs7gK8ATbW4ZPGKgcbrY1Br56PdM69F7LkFRi1kA=
|
||||
github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q=
|
||||
github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q=
|
||||
github.com/golang-jwt/jwt/v5 v5.3.1 h1:kYf81DTWFe7t+1VvL7eS+jKFVWaUnK9cB1qbwn63YCY=
|
||||
github.com/golang-jwt/jwt/v5 v5.3.1/go.mod h1:fxCRLWMO43lRc8nhHWY6LGqRcf+1gQWArsqaEUEa5bE=
|
||||
github.com/golang/protobuf v1.5.4 h1:i7eJL8qZTpSEXOPTxNKhASYpMn+8e5Q6AdndVa1dWek=
|
||||
github.com/golang/protobuf v1.5.4/go.mod h1:lnTiLA8Wa4RWRcIUkrtSVa5nRhsEGBg48fD6rSs7xps=
|
||||
github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8=
|
||||
github.com/google/go-cmp v0.7.0/go.mod h1:pXiqmnSA92OHEEa9HXL2W4E7lf9JzCmGVUdgjX3N/iU=
|
||||
github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
||||
github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0=
|
||||
github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
|
||||
github.com/grpc-ecosystem/grpc-gateway/v2 v2.29.0 h1:5VipnvEpbqr2gA2VbM+nYVbkIF28c5ZQfqCBQ5g2xfk=
|
||||
github.com/grpc-ecosystem/grpc-gateway/v2 v2.29.0/go.mod h1:Hyl3n6Twe1hvtd9XUXDec4pTvgMSEixRuQKPTMH2bNs=
|
||||
github.com/jackc/pgpassfile v1.0.0 h1:/6Hmqy13Ss2zCq62VdNG8tM1wchn8zjSGOBJ6icpsIM=
|
||||
github.com/jackc/pgpassfile v1.0.0/go.mod h1:CEx0iS5ambNFdcRtxPj5JhEz+xB6uRky5eyVu/W2HEg=
|
||||
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 h1:iCEnooe7UlwOQYpKFhBabPMi4aNAfoODPEFNiAnClxo=
|
||||
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761/go.mod h1:5TJZWKEWniPve33vlWYSoGYefn3gLQRzjfDlhSJ9ZKM=
|
||||
github.com/jackc/pgx/v5 v5.10.0 h1:VhSvgU2jSli8o3AqIEOTJr7rZwAEUVo4E4XhR94Zfr0=
|
||||
github.com/jackc/pgx/v5 v5.10.0/go.mod h1:mal1tBGAFfLHvZzaYh77YS/eC6IX9OWbRV1QIIM0Jn4=
|
||||
github.com/jackc/puddle/v2 v2.2.2 h1:PR8nw+E/1w0GLuRFSmiioY6UooMp6KJv0/61nB7icHo=
|
||||
github.com/jackc/puddle/v2 v2.2.2/go.mod h1:vriiEXHvEE654aYKXXjOvZM39qJ0q+azkZFrfEOc3H4=
|
||||
github.com/jinzhu/inflection v1.0.0 h1:K317FqzuhWc8YvSVlFMCCUb36O/S9MCKRDI7QkRKD/E=
|
||||
github.com/jinzhu/inflection v1.0.0/go.mod h1:h+uFLlag+Qp1Va5pdKtLDYj+kHp5pxUVkryuEj+Srlc=
|
||||
github.com/jinzhu/now v1.1.5 h1:/o9tlHleP7gOFmsnYNz3RGnqzefHA47wQpKrrdTIwXQ=
|
||||
github.com/jinzhu/now v1.1.5/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8=
|
||||
github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM=
|
||||
github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo=
|
||||
github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8=
|
||||
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
|
||||
github.com/klauspost/cpuid/v2 v2.3.0 h1:S4CRMLnYUhGeDFDqkGriYKdfoFlDnMtqTiI/sFzhA9Y=
|
||||
github.com/klauspost/cpuid/v2 v2.3.0/go.mod h1:hqwkgyIinND0mEev00jJYCxPNVRVXFQeu1XKlok6oO0=
|
||||
github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE=
|
||||
github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk=
|
||||
github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
|
||||
github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
|
||||
github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ=
|
||||
github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI=
|
||||
github.com/mattn/go-isatty v0.0.22 h1:j8l17JJ9i6VGPUFUYoTUKPSgKe/83EYU2zBC7YNKMw4=
|
||||
github.com/mattn/go-isatty v0.0.22/go.mod h1:ZXfXG4SQHsB/w3ZeOYbR0PrPwLy+n6xiMrJlRFqopa4=
|
||||
github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
|
||||
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg=
|
||||
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
|
||||
github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M=
|
||||
github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk=
|
||||
github.com/oklog/ulid/v2 v2.1.1 h1:suPZ4ARWLOJLegGFiZZ1dFAkqzhMjL3J1TzI+5wHz8s=
|
||||
github.com/oklog/ulid/v2 v2.1.1/go.mod h1:rcEKHmBBKfef9DhnvX7y1HZBYxjXb0cP5ExxNsTT1QQ=
|
||||
github.com/patrickmn/go-cache v2.1.0+incompatible h1:HRMgzkcYKYpi3C8ajMPV8OFXaaRUnok+kx1WdO15EQc=
|
||||
github.com/patrickmn/go-cache v2.1.0+incompatible/go.mod h1:3Qf8kWWT7OJRJbdiICTKqZju1ZixQ/KpMGzzAfe6+WQ=
|
||||
github.com/pborman/getopt v0.0.0-20170112200414-7148bc3a4c30/go.mod h1:85jBQOZwpVEaDAr341tbn15RS4fCAsIst0qp7i8ex1o=
|
||||
github.com/pelletier/go-toml/v2 v2.4.0 h1:Mwu0mAkUKbittDs3/ADDWXqMmq3EOK2VHiuCkV00Row=
|
||||
github.com/pelletier/go-toml/v2 v2.4.0/go.mod h1:2gIqNv+qfxSVS7cM2xJQKtLSTLUE9V8t9Stt+h56mCY=
|
||||
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
|
||||
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||
github.com/quic-go/go-ossfuzz-seeds v0.1.0 h1:APacT+iIaNF6fd8AGEiN3bT/Jtkd2jz4v4TzM7MFjy0=
|
||||
github.com/quic-go/go-ossfuzz-seeds v0.1.0/go.mod h1:3IOHRbJIc+L6YKMwfDtJAM9Vj9k0YY4muhuyUYk5tbk=
|
||||
github.com/quic-go/qpack v0.6.0 h1:g7W+BMYynC1LbYLSqRt8PBg5Tgwxn214ZZR34VIOjz8=
|
||||
github.com/quic-go/qpack v0.6.0/go.mod h1:lUpLKChi8njB4ty2bFLX2x4gzDqXwUpaO1DP9qMDZII=
|
||||
github.com/quic-go/quic-go v0.60.0 h1:xcQioE8OM66UQLeUMHltK1CCcOu3JbVB4JAQdDQSB+0=
|
||||
github.com/quic-go/quic-go v0.60.0/go.mod h1:wpKpjmPpftl30sL6pFh7REVpjbcCVy4zt2vDyK1TuJk=
|
||||
github.com/redis/go-redis/v9 v9.20.1 h1:sfCU6A8P3dXbKyWes02uxA2baehGux9dZHfEKtsTB1w=
|
||||
github.com/redis/go-redis/v9 v9.20.1/go.mod h1:v/M13XI1PVCDcm01VtPFOADfZtHf8YW3baQf57KlIkA=
|
||||
github.com/rogpeppe/go-internal v1.14.1 h1:UQB4HGPB6osV0SQTLymcB4TgvyWu6ZyliaW0tI/otEQ=
|
||||
github.com/rogpeppe/go-internal v1.14.1/go.mod h1:MaRKkUm5W0goXpeCfT7UZI6fk/L7L7so1lCWt35ZSgc=
|
||||
github.com/skip2/go-qrcode v0.0.0-20200617195104-da1b6568686e h1:MRM5ITcdelLK2j1vwZ3Je0FKVCfqOLp5zO6trqMLYs0=
|
||||
github.com/skip2/go-qrcode v0.0.0-20200617195104-da1b6568686e/go.mod h1:XV66xRDqSt+GTGFMVlhk3ULuV0y9ZmzeVGR4mloJI3M=
|
||||
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
|
||||
github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw=
|
||||
github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo=
|
||||
github.com/stretchr/objx v0.5.2/go.mod h1:FRsXN1f5AsAjCGJKqEizvkpNtU+EGNCLh3NxZ/8L+MA=
|
||||
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
|
||||
github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
|
||||
github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
|
||||
github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU=
|
||||
github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo=
|
||||
github.com/stretchr/testify v1.10.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY=
|
||||
github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu7U=
|
||||
github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U=
|
||||
github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI=
|
||||
github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08=
|
||||
github.com/ugorji/go/codec v1.3.1 h1:waO7eEiFDwidsBN6agj1vJQ4AG7lh2yqXyOXqhgQuyY=
|
||||
github.com/ugorji/go/codec v1.3.1/go.mod h1:pRBVtBSKl77K30Bv8R2P+cLSGaTtex6fsA2Wjqmfxj4=
|
||||
github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
||||
github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
||||
github.com/zeebo/xxh3 v1.1.0 h1:s7DLGDK45Dyfg7++yxI0khrfwq9661w9EN78eP/UZVs=
|
||||
github.com/zeebo/xxh3 v1.1.0/go.mod h1:IisAie1LELR4xhVinxWS5+zf1lA4p0MW4T+w+W07F5s=
|
||||
go.etcd.io/etcd/api/v3 v3.6.12 h1:OLOZUKEuAA36TR48F0cIaa8FdzrWygjyfrJxXg4iDgs=
|
||||
go.etcd.io/etcd/api/v3 v3.6.12/go.mod h1:p14EIQXHbuOQbVvL/WEes5uqKnxP9AgKJgpjbMVvzvE=
|
||||
go.etcd.io/etcd/client/pkg/v3 v3.6.12 h1:36zzB+pQOdHbhN+kH2iJz/K8bJn0ZLtLfPPO7jozTDo=
|
||||
go.etcd.io/etcd/client/pkg/v3 v3.6.12/go.mod h1:hh2+ZXtfLzs3o6mn92ntgNPBrTJJOvXqICM5g3L3DMY=
|
||||
go.etcd.io/etcd/client/v3 v3.6.12 h1:kMSP6JcPZMqSJiX+TXdUIBU/4eXEZWBAaui4VihMbIc=
|
||||
go.etcd.io/etcd/client/v3 v3.6.12/go.mod h1:CMs6fJWYiZQk4ytFjd4lE1diOvvRMmtbbn/alZXd3dQ=
|
||||
go.mongodb.org/mongo-driver/v2 v2.7.0 h1:RO+zqavD2/GCL3cxOMyZhx6R9Irzr8/6gsoqx5tcY/c=
|
||||
go.mongodb.org/mongo-driver/v2 v2.7.0/go.mod h1:yOI9kBsufol30iFsl1slpdq1I0eHPzybRWdyYUs8K/0=
|
||||
go.opentelemetry.io/auto/sdk v1.2.1 h1:jXsnJ4Lmnqd11kwkBV2LgLoFMZKizbCi5fNZ/ipaZ64=
|
||||
go.opentelemetry.io/auto/sdk v1.2.1/go.mod h1:KRTj+aOaElaLi+wW1kO/DZRXwkF4C5xPbEe3ZiIhN7Y=
|
||||
go.opentelemetry.io/otel v1.43.0 h1:mYIM03dnh5zfN7HautFE4ieIig9amkNANT+xcVxAj9I=
|
||||
go.opentelemetry.io/otel v1.43.0/go.mod h1:JuG+u74mvjvcm8vj8pI5XiHy1zDeoCS2LB1spIq7Ay0=
|
||||
go.opentelemetry.io/otel/metric v1.43.0 h1:d7638QeInOnuwOONPp4JAOGfbCEpYb+K6DVWvdxGzgM=
|
||||
go.opentelemetry.io/otel/metric v1.43.0/go.mod h1:RDnPtIxvqlgO8GRW18W6Z/4P462ldprJtfxHxyKd2PY=
|
||||
go.opentelemetry.io/otel/sdk v1.43.0 h1:pi5mE86i5rTeLXqoF/hhiBtUNcrAGHLKQdhg4h4V9Dg=
|
||||
go.opentelemetry.io/otel/sdk v1.43.0/go.mod h1:P+IkVU3iWukmiit/Yf9AWvpyRDlUeBaRg6Y+C58QHzg=
|
||||
go.opentelemetry.io/otel/sdk/metric v1.43.0 h1:S88dyqXjJkuBNLeMcVPRFXpRw2fuwdvfCGLEo89fDkw=
|
||||
go.opentelemetry.io/otel/sdk/metric v1.43.0/go.mod h1:C/RJtwSEJ5hzTiUz5pXF1kILHStzb9zFlIEe85bhj6A=
|
||||
go.opentelemetry.io/otel/trace v1.43.0 h1:BkNrHpup+4k4w+ZZ86CZoHHEkohws8AY+WTX09nk+3A=
|
||||
go.opentelemetry.io/otel/trace v1.43.0/go.mod h1:/QJhyVBUUswCphDVxq+8mld+AvhXZLhe+8WVFxiFff0=
|
||||
go.uber.org/atomic v1.11.0 h1:ZvwS0R+56ePWxUNi+Atn9dWONBPp/AUETXlHW0DxSjE=
|
||||
go.uber.org/atomic v1.11.0/go.mod h1:LUxbIzbOniOlMKjJjyPfpl4v+PKK2cNJn91OQbhoJI0=
|
||||
go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto=
|
||||
go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE=
|
||||
go.uber.org/mock v0.6.0 h1:hyF9dfmbgIX5EfOdasqLsWD6xqpNZlXblLB/Dbnwv3Y=
|
||||
go.uber.org/mock v0.6.0/go.mod h1:KiVJ4BqZJaMj4svdfmHM0AUx4NJYO8ZNpPnZn1Z+BBU=
|
||||
go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0=
|
||||
go.uber.org/multierr v1.11.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y=
|
||||
go.uber.org/zap v1.28.0 h1:IZzaP1Fv73/T/pBMLk4VutPl36uNC+OSUh3JLG3FIjo=
|
||||
go.uber.org/zap v1.28.0/go.mod h1:rDLpOi171uODNm/mxFcuYWxDsqWSAVkFdX4XojSKg/Q=
|
||||
go.yaml.in/yaml/v3 v3.0.4 h1:tfq32ie2Jv2UxXFdLJdh3jXuOzWiL1fo0bu/FbuKpbc=
|
||||
go.yaml.in/yaml/v3 v3.0.4/go.mod h1:DhzuOOF2ATzADvBadXxruRBLzYTpT36CKvDb3+aBEFg=
|
||||
golang.org/x/arch v0.28.0 h1:wVwVdqsTuUbJvhYVCspQYwZXHNYeLSoZnmHD+ggddpQ=
|
||||
golang.org/x/arch v0.28.0/go.mod h1:0X+GdSIP+kL5wPmpK7sdkEVTt2XoYP0cSjQSbZBwOi8=
|
||||
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
||||
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||
golang.org/x/crypto v0.53.0 h1:QZ4Muo8THX6CizN2vPPd5fBGHyogrdK9fG4wLPFUsto=
|
||||
golang.org/x/crypto v0.53.0/go.mod h1:DNLU434OwVakk9PzuwV8w62mAJpRJL3vsgcfp4Qnsio=
|
||||
golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
|
||||
golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
||||
golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
||||
golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
||||
golang.org/x/net v0.56.0 h1:Rw8j/hFzGvJUZwNBXnAtf5sVDVt+65SK2C7IxCxZt5o=
|
||||
golang.org/x/net v0.56.0/go.mod h1:D3Ku6r+V6JROoZK144D2XfMHFcMq/0zSfLelVTCFKec=
|
||||
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.21.0 h1:HLII4xRRTtCRkxYp4HNFF0Js/Og6q2i++KXbg0gHCwM=
|
||||
golang.org/x/sync v0.21.0/go.mod h1:9xrNwdLfx4jkKbNva9FpL6vEN7evnE43NNNJQ2LF3+0=
|
||||
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.46.0 h1:noSf2Fq6F8DBgS+LysIkx7rIExoNHJsxOAtPp4rthXw=
|
||||
golang.org/x/sys v0.46.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw=
|
||||
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||
golang.org/x/text v0.38.0 h1:sXmwo9DwP3OK9EZ7PqAdaooSGozfl/3a6/xJcbzPRhE=
|
||||
golang.org/x/text v0.38.0/go.mod h1:YXZt3QhHUKYT53r2lLKFIVi6Ao1jdzrTR/KQ09qyxF4=
|
||||
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
|
||||
golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
|
||||
golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE=
|
||||
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
gonum.org/v1/gonum v0.17.0 h1:VbpOemQlsSMrYmn7T2OUvQ4dqxQXU+ouZFQsZOx50z4=
|
||||
gonum.org/v1/gonum v0.17.0/go.mod h1:El3tOrEuMpv2UdMrbNlKEh9vd86bmQ6vqIcDwxEOc1E=
|
||||
google.golang.org/genproto/googleapis/api v0.0.0-20260618152121-87f3d3e198d3 h1:ctPmKL12ZsoKAlmPUsoW70zEDiYF+/H6aLieXxgAU0k=
|
||||
google.golang.org/genproto/googleapis/api v0.0.0-20260618152121-87f3d3e198d3/go.mod h1:Z4WJ5pJOYWFWcHEQUelD5QaZDknIQkpIL/+fyJOT9+A=
|
||||
google.golang.org/genproto/googleapis/rpc v0.0.0-20260618152121-87f3d3e198d3 h1:phvBWCAQMGN1945mp5fjCXP6jEF0+a0+4TjokS4sxNY=
|
||||
google.golang.org/genproto/googleapis/rpc v0.0.0-20260618152121-87f3d3e198d3/go.mod h1:4Hqkh8ycfw05ld/3BWL7rJOSfebL2Q+DVDeRgYgxUU8=
|
||||
google.golang.org/grpc v1.81.1 h1:VnnIIZ88UzOOKLukQi+ImGz8O1Wdp8nAGGnvOfEIWQQ=
|
||||
google.golang.org/grpc v1.81.1/go.mod h1:xGH9GfzOyMTGIOXBJmXt+BX/V0kcdQbdcuwQ/zNw42I=
|
||||
google.golang.org/protobuf v1.36.11 h1:fV6ZwhNocDyBLK0dj+fg8ektcVegBBuEolpbTQyBNVE=
|
||||
google.golang.org/protobuf v1.36.11/go.mod h1:HTf+CrKn2C3g5S8VImy6tdcUvCska2kB7j23XfzDpco=
|
||||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q=
|
||||
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
|
||||
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
|
||||
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
|
||||
gorm.io/driver/mysql v1.6.0 h1:eNbLmNTpPpTOVZi8MMxCi2aaIm0ZpInbORNXDwyLGvg=
|
||||
gorm.io/driver/mysql v1.6.0/go.mod h1:D/oCC2GWK3M/dqoLxnOlaNKmXz8WNTfcS9y5ovaSqKo=
|
||||
gorm.io/driver/postgres v1.6.0 h1:2dxzU8xJ+ivvqTRph34QX+WrRaJlmfyPqXmoGVjMBa4=
|
||||
gorm.io/driver/postgres v1.6.0/go.mod h1:vUw0mrGgrTK+uPHEhAdV4sfFELrByKVGnaVRkXDhtWo=
|
||||
gorm.io/gorm v1.31.1 h1:7CA8FTFz/gRfgqgpeKIBcervUn3xSyPUmr6B2WXJ7kg=
|
||||
gorm.io/gorm v1.31.1/go.mod h1:XyQVbO2k6YkOis7C2437jSit3SsDK72s7n7rsSHd+Gs=
|
||||
@@ -1,33 +0,0 @@
|
||||
package config
|
||||
|
||||
import (
|
||||
"net"
|
||||
|
||||
"git.apinb.com/bsm-sdk/core/conf"
|
||||
)
|
||||
|
||||
var (
|
||||
Spec SrvConfig
|
||||
)
|
||||
|
||||
type SrvConfig struct {
|
||||
conf.Base `yaml:",inline"`
|
||||
Databases *conf.DBConf `yaml:"Databases"`
|
||||
Rpc map[string]conf.RpcConf `yaml:"Rpc"`
|
||||
Apm *conf.ApmConf `yaml:"APM"`
|
||||
}
|
||||
|
||||
func New(srvKey string) {
|
||||
// 初始化配置 创建一个新的配置实例,用于服务配置
|
||||
conf.New(srvKey, &Spec)
|
||||
|
||||
// 配置校验 服务IP,端口; 端口如果不合规,则随机分配端口
|
||||
Spec.Port = conf.CheckPort(Spec.Port)
|
||||
Spec.BindIP = conf.CheckIP(Spec.BindIP)
|
||||
Spec.Addr = net.JoinHostPort(Spec.BindIP, Spec.Port)
|
||||
|
||||
// 配置校验 服务名称地址及监听地址不能为空
|
||||
conf.NotNil(Spec.Service, Spec.Cache)
|
||||
|
||||
conf.PrintInfo(Spec.Addr)
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
package impl
|
||||
|
||||
import (
|
||||
"git.apinb.com/bsm-sdk/core/cache/redis"
|
||||
"git.apinb.com/bsm-sdk/core/logger"
|
||||
"git.apinb.com/bsm-sdk/core/with"
|
||||
"git.apinb.com/ops/sample/internal/config"
|
||||
"github.com/patrickmn/go-cache"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
var (
|
||||
RedisService *redis.RedisClient // Redis 客户端服务
|
||||
DBService *gorm.DB // 数据库服务
|
||||
MemoryService *cache.Cache // 内存缓存服务
|
||||
Logger *logger.Logger
|
||||
)
|
||||
|
||||
// NewImpl 初始化各类服务实例
|
||||
func NewImpl() {
|
||||
// 初始化内存缓存
|
||||
MemoryService = with.Memory(nil)
|
||||
// 初始化 Redis 缓存
|
||||
RedisService = with.RedisCache(config.Spec.Cache)
|
||||
// 初始化数据库服务
|
||||
DBService = with.Databases(config.Spec.Databases, nil)
|
||||
// 初始化 日志服务
|
||||
logger.New(nil)
|
||||
}
|
||||
@@ -1,125 +0,0 @@
|
||||
package demo
|
||||
|
||||
import (
|
||||
"git.apinb.com/bsm-sdk/core/errcode"
|
||||
"git.apinb.com/bsm-sdk/core/infra"
|
||||
"git.apinb.com/bsm-sdk/core/utils"
|
||||
"git.apinb.com/ops/sample/internal/models"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
type CreateRequest struct {
|
||||
Name string `json:"name" binding:"required,max=255"`
|
||||
Age int `json:"age"`
|
||||
}
|
||||
|
||||
type UpdateRequest struct {
|
||||
Name string `json:"name" binding:"required,max=255"`
|
||||
Age int `json:"age"`
|
||||
}
|
||||
|
||||
type ListReply struct {
|
||||
Total int64 `json:"total"`
|
||||
List []models.SampleDemo `json:"list"`
|
||||
}
|
||||
|
||||
func Create(ctx *gin.Context) {
|
||||
var req CreateRequest
|
||||
if err := ctx.ShouldBindJSON(&req); err != nil {
|
||||
infra.Response.Error(ctx, errcode.ErrInvalidArgument)
|
||||
return
|
||||
}
|
||||
|
||||
data := models.SampleDemo{
|
||||
Name: req.Name,
|
||||
Age: req.Age,
|
||||
}
|
||||
data.Identity = utils.UUID()
|
||||
data.Status = 1
|
||||
if err := models.CreateSampleDemo(&data); err != nil {
|
||||
infra.Response.Error(ctx, err)
|
||||
return
|
||||
}
|
||||
infra.Response.Success(ctx, data)
|
||||
}
|
||||
|
||||
func List(ctx *gin.Context) {
|
||||
page := utils.String2Int(ctx.DefaultQuery("page", "1"))
|
||||
size := utils.String2Int(ctx.DefaultQuery("size", "20"))
|
||||
if page < 1 {
|
||||
page = 1
|
||||
}
|
||||
if size < 1 || size > 100 {
|
||||
size = 20
|
||||
}
|
||||
|
||||
list, total, err := models.ListSampleDemos(page, size)
|
||||
if err != nil {
|
||||
infra.Response.Error(ctx, err)
|
||||
return
|
||||
}
|
||||
infra.Response.Success(ctx, ListReply{Total: total, List: list})
|
||||
}
|
||||
|
||||
func Get(ctx *gin.Context) {
|
||||
identity := ctx.Param("identity")
|
||||
if identity == "" {
|
||||
infra.Response.Error(ctx, errcode.ErrInvalidArgument)
|
||||
return
|
||||
}
|
||||
|
||||
data, err := models.GetSampleDemoByField("identity", identity)
|
||||
if err != nil {
|
||||
infra.Response.Error(ctx, err)
|
||||
return
|
||||
}
|
||||
infra.Response.Success(ctx, data)
|
||||
}
|
||||
|
||||
func Update(ctx *gin.Context) {
|
||||
identity := ctx.Param("identity")
|
||||
if identity == "" {
|
||||
infra.Response.Error(ctx, errcode.ErrInvalidArgument)
|
||||
return
|
||||
}
|
||||
|
||||
var req UpdateRequest
|
||||
if err := ctx.ShouldBindJSON(&req); err != nil {
|
||||
infra.Response.Error(ctx, errcode.ErrInvalidArgument)
|
||||
return
|
||||
}
|
||||
|
||||
data, err := models.GetSampleDemoByField("identity", identity)
|
||||
if err != nil {
|
||||
infra.Response.Error(ctx, err)
|
||||
return
|
||||
}
|
||||
|
||||
data.Name = req.Name
|
||||
data.Age = req.Age
|
||||
if err := models.UpdateSampleDemo(data); err != nil {
|
||||
infra.Response.Error(ctx, err)
|
||||
return
|
||||
}
|
||||
infra.Response.Success(ctx, data)
|
||||
}
|
||||
|
||||
func Delete(ctx *gin.Context) {
|
||||
identity := ctx.Param("identity")
|
||||
if identity == "" {
|
||||
infra.Response.Error(ctx, errcode.ErrInvalidArgument)
|
||||
return
|
||||
}
|
||||
|
||||
data, err := models.GetSampleDemoByField("identity", identity)
|
||||
if err != nil {
|
||||
infra.Response.Error(ctx, err)
|
||||
return
|
||||
}
|
||||
|
||||
if err := models.DeleteSampleDemo(data); err != nil {
|
||||
infra.Response.Error(ctx, err)
|
||||
return
|
||||
}
|
||||
infra.Response.Success(ctx, identity)
|
||||
}
|
||||
@@ -1,10 +0,0 @@
|
||||
package ping
|
||||
|
||||
import (
|
||||
"git.apinb.com/bsm-sdk/core/infra"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
func Hello(ctx *gin.Context) {
|
||||
infra.Response.Success(ctx, "OK")
|
||||
}
|
||||
@@ -1,6 +0,0 @@
|
||||
/**
|
||||
* @Author: David Yan(david.yan@qq.com)
|
||||
* @Description: 自定义查询方法
|
||||
*/
|
||||
|
||||
package models
|
||||
@@ -1,86 +0,0 @@
|
||||
package models
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
||||
"git.apinb.com/bsm-sdk/core/database"
|
||||
"git.apinb.com/bsm-sdk/core/errcode"
|
||||
"git.apinb.com/bsm-sdk/core/types"
|
||||
"git.apinb.com/ops/sample/internal/impl"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
/*
|
||||
* SampleDemo
|
||||
* Comment: 示例数据表
|
||||
* Version: 10
|
||||
* Created: 2022-04-12 10:44:51 , Updated:0001-01-01 00:00:00
|
||||
*/
|
||||
type SampleDemo struct {
|
||||
types.Std_IICUDS
|
||||
Name string `gorm:"column:name;type:varchar(255);default:'';" json:"name"` // 名称
|
||||
Age int `gorm:"column:age;type:int;default:0;" json:"age"` // 年龄
|
||||
}
|
||||
|
||||
func init() {
|
||||
database.AppendMigrate(&SampleDemo{})
|
||||
}
|
||||
|
||||
// TableName .
|
||||
func (table *SampleDemo) TableName() string {
|
||||
return "sample_demo" //对应数据库表名
|
||||
}
|
||||
|
||||
// GetSampleDemoByField 根据特定字段值获取 SampleDemo 对象
|
||||
func GetSampleDemoByField(field string, value any) (*SampleDemo, error) {
|
||||
var (
|
||||
data SampleDemo
|
||||
condition = map[string]any{field: value}
|
||||
)
|
||||
err := impl.DBService.Where(condition).First(&data).Error
|
||||
if err != nil {
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return nil, errcode.ErrRecordNotFound
|
||||
}
|
||||
return nil, errcode.ErrDB
|
||||
}
|
||||
|
||||
return &data, nil
|
||||
}
|
||||
|
||||
func CreateSampleDemo(data *SampleDemo) error {
|
||||
if err := impl.DBService.Create(data).Error; err != nil {
|
||||
return errcode.ErrDB
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func ListSampleDemos(page, size int) ([]SampleDemo, int64, error) {
|
||||
var (
|
||||
list []SampleDemo
|
||||
total int64
|
||||
)
|
||||
db := impl.DBService.Model(&SampleDemo{})
|
||||
if err := db.Count(&total).Error; err != nil {
|
||||
return nil, 0, errcode.ErrDB
|
||||
}
|
||||
offset := (page - 1) * size
|
||||
if err := db.Order("id desc").Offset(offset).Limit(size).Find(&list).Error; err != nil {
|
||||
return nil, 0, errcode.ErrDB
|
||||
}
|
||||
return list, total, nil
|
||||
}
|
||||
|
||||
func UpdateSampleDemo(data *SampleDemo) error {
|
||||
if err := impl.DBService.Save(data).Error; err != nil {
|
||||
return errcode.ErrDB
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func DeleteSampleDemo(data *SampleDemo) error {
|
||||
if err := impl.DBService.Delete(data).Error; err != nil {
|
||||
return errcode.ErrDB
|
||||
}
|
||||
return nil
|
||||
}
|
||||
@@ -1,36 +0,0 @@
|
||||
package routers
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"git.apinb.com/bsm-sdk/core/middleware"
|
||||
"git.apinb.com/ops/sample/internal/logic/demo"
|
||||
"git.apinb.com/ops/sample/internal/logic/ping"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
// Register 注册路由,请求地址格式: ip:port/{srvKey}/v1/{group}/{action}
|
||||
func Register(srvKey string, engine *gin.Engine) {
|
||||
v1Key := fmt.Sprintf("/%s/%s", srvKey, "v1")
|
||||
registerAnonymous(v1Key, engine)
|
||||
registerRouters(v1Key, engine)
|
||||
}
|
||||
|
||||
func registerAnonymous(v1Key string, engine *gin.Engine) {
|
||||
anonymous := engine.Group(v1Key)
|
||||
{
|
||||
anonymous.GET("/ping/hello", ping.Hello)
|
||||
}
|
||||
}
|
||||
|
||||
func registerRouters(v1Key string, engine *gin.Engine) {
|
||||
demoGroup := engine.Group(fmt.Sprintf("/%s/%s", v1Key, "demo"))
|
||||
demoGroup.Use(middleware.JwtAuth(true))
|
||||
{
|
||||
demoGroup.POST("", demo.Create)
|
||||
demoGroup.GET("", demo.List)
|
||||
demoGroup.GET("/:identity", demo.Get)
|
||||
demoGroup.PUT("/:identity", demo.Update)
|
||||
demoGroup.DELETE("/:identity", demo.Delete)
|
||||
}
|
||||
}
|
||||
@@ -1,9 +0,0 @@
|
||||
#!/bin/bash
|
||||
set -euo pipefail
|
||||
|
||||
mkdir -p build
|
||||
|
||||
GOARCH=amd64 GOOS=linux go build -o ./build/sample ./cmd/main/main.go
|
||||
GOARCH=amd64 GOOS=linux go build -o ./build/sample-cli ./cmd/cli/main.go
|
||||
|
||||
echo "build completed: ./build/sample, ./build/sample-cli"
|
||||
@@ -1,5 +0,0 @@
|
||||
#!/bin/bash
|
||||
set -euo pipefail
|
||||
|
||||
go vet ./...
|
||||
go fmt ./...
|
||||
@@ -1,7 +0,0 @@
|
||||
git pull
|
||||
go get all
|
||||
go get -u ./...
|
||||
go mod tidy
|
||||
git add .
|
||||
git commit -m 'run ./scripts/update.sh'
|
||||
git push
|
||||
@@ -1,31 +0,0 @@
|
||||
### 创建示例数据(需要 JWT)
|
||||
POST http://127.0.0.1:12426/Sample/v1/sample/demo
|
||||
Content-Type: application/json
|
||||
Authorization: Bearer {{token}}
|
||||
|
||||
{
|
||||
"name": "Alice",
|
||||
"age": 25
|
||||
}
|
||||
|
||||
### 列表查询
|
||||
GET http://127.0.0.1:12426/Sample/v1/sample/demo?page=1&size=20
|
||||
Authorization: Bearer {{token}}
|
||||
|
||||
### 详情查询
|
||||
GET http://127.0.0.1:12426/Sample/v1/sample/demo/{{identity}}
|
||||
Authorization: Bearer {{token}}
|
||||
|
||||
### 更新
|
||||
PUT http://127.0.0.1:12426/Sample/v1/sample/demo/{{identity}}
|
||||
Content-Type: application/json
|
||||
Authorization: Bearer {{token}}
|
||||
|
||||
{
|
||||
"name": "Alice Updated",
|
||||
"age": 26
|
||||
}
|
||||
|
||||
### 删除
|
||||
DELETE http://127.0.0.1:12426/Sample/v1/sample/demo/{{identity}}
|
||||
Authorization: Bearer {{token}}
|
||||
@@ -1,2 +0,0 @@
|
||||
GET http://127.0.0.1:12426/Sample/v1/ping/hello
|
||||
Content-Type: application/json
|
||||
@@ -1,2 +0,0 @@
|
||||
# HTTP 接口测试文件,使用 VS Code REST Client 或 IntelliJ HTTP Client 运行。
|
||||
# 将 {{token}}、{{identity}} 替换为实际值。
|
||||
Reference in New Issue
Block a user