本文档为 Go-ES 项目的开发指南,介绍了如何设置开发环境、代码规范、测试方法以及如何贡献和扩展本项目。
若使用 VSCode,推荐安装以下插件:
# 克隆仓库
git clone https://github.com/saixiaoxi/go-es.git
cd go-es
# 安装依赖
go mod tidy
# 创建配置文件
cp config.example.yaml config.yaml
# 编辑配置文件,设置开发环境参数
vim config.yaml
# 运行应用
go run cmd/api/main.go
# 或构建并运行
go build -o bin/go-es cmd/api/main.go
./bin/go-es
domain/entity/
目录下创建新实体// 例如,创建 category.go
package entity
import (
"time"
"github.com/google/uuid"
)
// Category 类别实体
type Category struct {
ID string `json:"id" gorm:"type:varchar(36);primary_key"`
Name string `json:"name" gorm:"type:varchar(100);not null;unique"`
Description string `json:"description" gorm:"type:text"`
ParentID string `json:"parent_id" gorm:"type:varchar(36);index"`
CreatedAt time.Time `json:"created_at" gorm:"autoCreateTime"`
UpdatedAt time.Time `json:"updated_at" gorm:"autoUpdateTime"`
}
// NewCategory 创建新类别
func NewCategory(name, description, parentID string) *Category {
return &Category{
ID: uuid.New().String(),
Name: name,
Description: description,
ParentID: parentID,
CreatedAt: time.Now(),
UpdatedAt: time.Now(),
}
}
domain/repository/
目录下定义仓储接口// 例如,创建 category_repository.go
package repository
import (
"context"
"github.com/saixiaoxi/go-es/domain/entity"
)
// CategoryRepository 类别仓储接口
type CategoryRepository interface {
Create(ctx context.Context, category *entity.Category) error
FindByID(ctx context.Context, id string) (*entity.Category, error)
FindAll(ctx context.Context) ([]*entity.Category, error)
Update(ctx context.Context, category *entity.Category) error
Delete(ctx context.Context, id string) error
}
infrastructure/repository/
目录下实现仓储接口// 例如,创建 category_repository_impl.go
package repository
import (
"context"
"github.com/saixiaoxi/go-es/domain/entity"
"github.com/saixiaoxi/go-es/domain/repository"
"github.com/saixiaoxi/go-es/infrastructure/persistence"
)
// CategoryRepositoryImpl 类别仓储实现
type CategoryRepositoryImpl struct {
db *persistence.Database
}
// NewCategoryRepository 创建类别仓储
func NewCategoryRepository(db *persistence.Database) repository.CategoryRepository {
return &CategoryRepositoryImpl{
db: db,
}
}
// Create 创建类别
func (r *CategoryRepositoryImpl) Create(ctx context.Context, category *entity.Category) error {
return r.db.GetDB().Create(category).Error
}
// 实现其他方法...
创建领域服务:在 domain/service/
目录下创建领域服务
创建应用服务:在 application/service/
目录下创建应用服务
创建 DTO:在 interfaces/dto/
目录下定义 DTO
创建 API 处理器:在 interfaces/api/handler/
目录下创建处理器
注册路由:在 interfaces/api/router/router.go
中注册新路由
例如,添加一个用户认证模块:
domain/service/
目录下实现interfaces/api/middleware/
目录下创建认证中间件//
注释,而不是 /* */
errors.Wrap
来添加上下文为关键组件编写单元测试:
// product_service_test.go
package service_test
import (
"context"
"testing"
"github.com/saixiaoxi/go-es/domain/entity"
"github.com/saixiaoxi/go-es/domain/service"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/mock"
)
// MockProductRepository 模拟产品仓储
type MockProductRepository struct {
mock.Mock
}
// 实现ProductRepository接口的方法...
func TestCreateProduct(t *testing.T) {
// 准备测试数据
mockRepo := new(MockProductRepository)
productService := service.NewProductService(mockRepo)
product := entity.NewProduct("Test Product", "Description", 100.0, "Category", []string{"tag1"})
// 设置Mock期望
mockRepo.On("Create", mock.Anything, product).Return(nil)
mockRepo.On("IndexProduct", mock.Anything, product).Return(nil)
// 执行测试
err := productService.CreateProduct(context.Background(), product)
// 断言
assert.NoError(t, err)
mockRepo.AssertExpectations(t)
}
编写集成测试验证系统各部分之间的交互:
// 在 tests/integration 目录下
func TestProductAPI(t *testing.T) {
// 准备测试环境...
// 发送HTTP请求
resp, err := http.Post(
"http://localhost:8080/api/v1/products",
"application/json",
strings.NewReader(`{"name":"Test Product","price":100,"category":"Test"}`),
)
// 断言
assert.NoError(t, err)
assert.Equal(t, http.StatusCreated, resp.StatusCode)
// 解析响应...
}
# 运行所有测试
go test ./...
# 运行指定包的测试
go test ./domain/service/...
# 运行带覆盖率的测试
go test -cover ./...
# 生成覆盖率报告
go test -coverprofile=coverage.out ./...
go tool cover -html=coverage.out
项目使用 Swagger 自动生成 API 文档:
# 安装 swag 工具
go install github.com/swaggo/swag/cmd/swag@latest
# 生成文档
swag init -g ./cmd/api/main.go
生成 Go 代码文档:
# 启动本地文档服务器
godoc -http=:6060
# 访问 http://localhost:6060/pkg/github.com/saixiaoxi/go-es/ 查看文档
infrastructure
层创建集成客户端log
包打印调试信息delve
调试器进行源码级调试curl
或 API 客户端(如 Postman)测试 API 端点[模块] 简短描述
详细描述,解释更改原因
提交 PR 后,代码审查将检查: