feat: 初次启动

This commit is contained in:
Blizzard
2026-04-27 21:23:13 +08:00
parent e515f6a287
commit bb8ad4d515
148 changed files with 8602 additions and 5678 deletions
+10 -26
View File
@@ -1,22 +1,20 @@
Name: plant-api
Log:
Encoding: plain
Host: 0.0.0.0
Port: 9004
Auth:
AccessSecret: 9149f2eb-d517-4a50-a03a-231dbcf0d872
AccessExpire: 7200
AccessSecret: sundynix-jwt-secret-2024
AccessExpire: 604800
# MySQL
DB:
DataSource: root:root@tcp(192.168.100.127:3307)/sundynix_micro_go?charset=utf8mb4&parseTime=True&loc=Local
PlantRpc:
Etcd:
Hosts:
- 192.168.100.127:2379
Key: plant.rpc
# Redis
Cache:
- Host: 127.0.0.1:6379
Pass: sundynix
Type: node
# RPC 依赖
UserRpc:
Etcd:
Hosts:
@@ -28,17 +26,3 @@ FileRpc:
Hosts:
- 192.168.100.127:2379
Key: file.rpc
# 百度植物识别
BaiduImgClassify:
ApiKey: hpBfjwy8ifv3qswYGYjUCNKN
SecretKey: i5aXZdM4XZVuDroBslL0f3uIuwbAyXFS
# 微信支付
WechatPay:
MchId: "1735188493"
MchCertificateSerialNumber: "3725BFCA9CA3AF819AEC5D0CB7D3540BBC67F2CF"
MchApiV3Key: "a1B2c3D4e5F6g7H8i9J0k1L2m3N4o5P6"
PrivateKeyPath: "/Users/blizzard/privateFolder/cert/apiclient_key.pem"
PublicKeyPath: "/Users/blizzard/privateFolder/cert/pub_key.pem"
NotifyUrl: "https://prod.sundynix.cn/api/wechatpay/notify"
+3 -22
View File
@@ -14,26 +14,7 @@ type Config struct {
AccessSecret string
AccessExpire int64
}
DB struct {
DataSource string
}
Cache []struct {
Host string
Pass string
Type string
}
UserRpc zrpc.RpcClientConf
FileRpc zrpc.RpcClientConf
BaiduImgClassify struct {
ApiKey string
SecretKey string
}
WechatPay struct {
MchId string
MchCertificateSerialNumber string
MchApiV3Key string
PrivateKeyPath string
PublicKeyPath string
NotifyUrl string
}
PlantRpc zrpc.RpcClientConf
UserRpc zrpc.RpcClientConf
FileRpc zrpc.RpcClientConf
}
@@ -1,4 +1,3 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
@@ -7,7 +6,7 @@ import (
"github.com/zeromicro/go-zero/core/logx"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plant"
)
type AddCarePlanLogic struct {
@@ -22,12 +21,9 @@ func NewAddCarePlanLogic(ctx context.Context, svcCtx *svc.ServiceContext) *AddCa
func (l *AddCarePlanLogic) AddCarePlan(req *types.CarePlanReq) error {
userId := fmt.Sprintf("%v", l.ctx.Value("userId"))
plan := plantModel.SundynixCarePlan{
UserID: userId, PlantID: req.PlantId, Name: req.Name,
TargetAction: req.TargetAction, Period: req.Period, Icon: req.Icon,
}
if err := l.svcCtx.DB.Create(&plan).Error; err != nil {
return fmt.Errorf("创建养护计划失败")
}
return nil
_, err := l.svcCtx.PlantRpc.AddCarePlan(l.ctx, &plant.AddCarePlanReq{
UserId: userId, PlantId: req.PlantId, Name: req.Name, Icon: req.Icon,
TargetAction: req.TargetAction, Period: int32(req.Period),
})
return err
}
@@ -1,4 +1,3 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
@@ -7,7 +6,7 @@ import (
"github.com/zeromicro/go-zero/core/logx"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plant"
)
type AddCareRecordLogic struct {
@@ -22,12 +21,8 @@ func NewAddCareRecordLogic(ctx context.Context, svcCtx *svc.ServiceContext) *Add
func (l *AddCareRecordLogic) AddCareRecord(req *types.CareRecordReq) error {
userId := fmt.Sprintf("%v", l.ctx.Value("userId"))
record := plantModel.SundynixCareRecord{
UserID: userId, PlantID: req.PlantId, PlanID: req.PlanId,
Name: req.Action, Remark: req.Note,
}
if err := l.svcCtx.DB.Create(&record).Error; err != nil {
return fmt.Errorf("创建养护记录失败")
}
return nil
_, err := l.svcCtx.PlantRpc.AddCareRecord(l.ctx, &plant.AddCareRecordReq{
UserId: userId, PlantId: req.PlantId, PlanId: req.PlanId, Action: req.Action, Note: req.Note,
})
return err
}
@@ -1,4 +1,3 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
@@ -7,7 +6,7 @@ import (
"github.com/zeromicro/go-zero/core/logx"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plant"
)
type AddGrowthRecordLogic struct {
@@ -22,11 +21,8 @@ func NewAddGrowthRecordLogic(ctx context.Context, svcCtx *svc.ServiceContext) *A
func (l *AddGrowthRecordLogic) AddGrowthRecord(req *types.GrowthRecordReq) error {
userId := fmt.Sprintf("%v", l.ctx.Value("userId"))
record := plantModel.SundynixGrowthRecord{
PlantID: req.PlantId, UserID: userId, Content: req.Content,
}
if err := l.svcCtx.DB.Create(&record).Error; err != nil {
return fmt.Errorf("创建成长记录失败")
}
return nil
_, err := l.svcCtx.PlantRpc.AddGrowthRecord(l.ctx, &plant.AddGrowthRecordReq{
UserId: userId, PlantId: req.PlantId, Content: req.Content, ImgIds: req.ImgIds,
})
return err
}
@@ -1,4 +1,3 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
@@ -7,8 +6,7 @@ import (
"github.com/zeromicro/go-zero/core/logx"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"time"
"sundynix-micro-go/app/plant/rpc/plant"
)
type CreatePlantLogic struct {
@@ -23,20 +21,10 @@ func NewCreatePlantLogic(ctx context.Context, svcCtx *svc.ServiceContext) *Creat
func (l *CreatePlantLogic) CreatePlant(req *types.CreatePlantReq) error {
userId := fmt.Sprintf("%v", l.ctx.Value("userId"))
plantTime, _ := time.Parse("2006-01-02", req.PlantTime)
plant := plantModel.SundynixMyPlant{
UserID: userId, Name: req.Name, PlantTime: plantTime, Placement: req.Placement,
_, err := l.svcCtx.PlantRpc.CreatePlant(l.ctx, &plant.CreatePlantReq{
UserId: userId, Name: req.Name, PlantTime: req.PlantTime, Placement: req.Placement,
PotMaterial: req.PotMaterial, PotSize: req.PotSize, Sunlight: req.Sunlight,
PlantingMaterial: req.PlantingMaterial, Status: 1,
}
if err := l.svcCtx.DB.Create(&plant).Error; err != nil {
l.Errorf("创建植物失败: %v", err)
return fmt.Errorf("创建植物失败")
}
if len(req.ImgIds) > 0 {
for _, imgID := range req.ImgIds {
l.svcCtx.DB.Create(&plantModel.SundynixMyPlantOss{MyPlantID: plant.ID, OssID: imgID})
}
}
return nil
PlantingMaterial: req.PlantingMaterial, ImgIds: req.ImgIds,
})
return err
}
@@ -1,13 +1,11 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
"context"
"fmt"
"github.com/zeromicro/go-zero/core/logx"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plant"
)
type DeletePlantLogic struct {
@@ -21,13 +19,6 @@ func NewDeletePlantLogic(ctx context.Context, svcCtx *svc.ServiceContext) *Delet
}
func (l *DeletePlantLogic) DeletePlant(req *types.IdsReq) error {
if err := l.svcCtx.DB.Where("id IN ?", req.Ids).Delete(&plantModel.SundynixMyPlant{}).Error; err != nil {
return fmt.Errorf("删除植物失败")
}
// 清理关联数据
l.svcCtx.DB.Where("plant_id IN ?", req.Ids).Delete(&plantModel.SundynixCarePlan{})
l.svcCtx.DB.Where("plant_id IN ?", req.Ids).Delete(&plantModel.SundynixCareRecord{})
l.svcCtx.DB.Where("plant_id IN ?", req.Ids).Delete(&plantModel.SundynixCareTask{})
l.svcCtx.DB.Where("plant_id IN ?", req.Ids).Delete(&plantModel.SundynixGrowthRecord{})
return nil
_, err := l.svcCtx.PlantRpc.DeletePlant(l.ctx, &plant.IdsReq{Ids: req.Ids})
return err
}
@@ -1,4 +1,3 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
@@ -7,7 +6,7 @@ import (
"github.com/zeromicro/go-zero/core/logx"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plant"
)
type GetMyPlantListLogic struct {
@@ -22,22 +21,11 @@ func NewGetMyPlantListLogic(ctx context.Context, svcCtx *svc.ServiceContext) *Ge
func (l *GetMyPlantListLogic) GetMyPlantList(req *types.PlantListReq) (resp interface{}, err error) {
userId := fmt.Sprintf("%v", l.ctx.Value("userId"))
var plants []plantModel.SundynixMyPlant
var total int64
db := l.svcCtx.DB.Model(&plantModel.SundynixMyPlant{}).Where("user_id = ?", userId)
if req.Name != "" {
db = db.Where("name LIKE ?", "%"+req.Name+"%")
result, err := l.svcCtx.PlantRpc.GetPlantList(l.ctx, &plant.PlantListReq{
UserId: userId, Current: int32(req.Current), PageSize: int32(req.PageSize), Name: req.Name,
})
if err != nil {
return nil, err
}
db.Count(&total)
current, pageSize := req.Current, req.PageSize
if current <= 0 {
current = 1
}
if pageSize <= 0 {
pageSize = 10
}
if err := db.Offset((current - 1) * pageSize).Limit(pageSize).Order("created_at DESC").Find(&plants).Error; err != nil {
return nil, fmt.Errorf("查询植物列表失败")
}
return map[string]interface{}{"list": plants, "total": total, "current": current, "size": pageSize}, nil
return map[string]interface{}{"list": result.List, "total": result.Total}, nil
}
@@ -1,14 +1,11 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
"context"
"fmt"
"github.com/zeromicro/go-zero/core/logx"
"gorm.io/gorm"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plant"
)
type GetPlantDetailLogic struct {
@@ -22,24 +19,9 @@ func NewGetPlantDetailLogic(ctx context.Context, svcCtx *svc.ServiceContext) *Ge
}
func (l *GetPlantDetailLogic) GetPlantDetail(req *types.IdPathReq) (resp interface{}, err error) {
var plant plantModel.SundynixMyPlant
if err := l.svcCtx.DB.Where("id = ?", req.Id).First(&plant).Error; err != nil {
if err == gorm.ErrRecordNotFound {
return nil, fmt.Errorf("植物不存在")
}
return nil, fmt.Errorf("查询植物失败")
result, err := l.svcCtx.PlantRpc.GetPlantDetail(l.ctx, &plant.IdReq{Id: req.Id})
if err != nil {
return nil, err
}
// 查询关联图片ID
var ossIds []string
l.svcCtx.DB.Model(&plantModel.SundynixMyPlantOss{}).Where("sundynix_my_plant_id = ?", plant.ID).Pluck("sundynix_oss_id", &ossIds)
// 查询养护计划
var plans []plantModel.SundynixCarePlan
l.svcCtx.DB.Where("plant_id = ?", plant.ID).Find(&plans)
// 查询成长记录
var records []plantModel.SundynixGrowthRecord
l.svcCtx.DB.Where("plant_id = ?", plant.ID).Order("created_at DESC").Limit(10).Find(&records)
return map[string]interface{}{
"plant": plant, "imgIds": ossIds, "carePlans": plans, "growthRecords": records,
}, nil
return result, nil
}
@@ -1,13 +1,11 @@
// Code scaffolded by goctl. Safe to edit.
package myPlant
import (
"context"
"fmt"
"github.com/zeromicro/go-zero/core/logx"
"sundynix-micro-go/app/plant/api/internal/svc"
"sundynix-micro-go/app/plant/api/internal/types"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plant"
)
type UpdatePlantLogic struct {
@@ -21,32 +19,10 @@ func NewUpdatePlantLogic(ctx context.Context, svcCtx *svc.ServiceContext) *Updat
}
func (l *UpdatePlantLogic) UpdatePlant(req *types.UpdatePlantReq) error {
updates := map[string]interface{}{}
if req.Name != "" {
updates["name"] = req.Name
}
if req.Status > 0 {
updates["status"] = req.Status
}
if req.Placement != "" {
updates["placement"] = req.Placement
}
if req.PotMaterial != "" {
updates["pot_material"] = req.PotMaterial
}
if req.PotSize != "" {
updates["pot_size"] = req.PotSize
}
if req.Sunlight != "" {
updates["sunlight"] = req.Sunlight
}
if req.PlantingMaterial != "" {
updates["planting_material"] = req.PlantingMaterial
}
if len(updates) > 0 {
if err := l.svcCtx.DB.Model(&plantModel.SundynixMyPlant{}).Where("id = ?", req.Id).Updates(updates).Error; err != nil {
return fmt.Errorf("更新植物失败")
}
}
return nil
_, err := l.svcCtx.PlantRpc.UpdatePlant(l.ctx, &plant.UpdatePlantReq{
Id: req.Id, Name: req.Name, Status: int32(req.Status), Placement: req.Placement,
PotMaterial: req.PotMaterial, PotSize: req.PotSize, Sunlight: req.Sunlight,
PlantingMaterial: req.PlantingMaterial, ImgIds: req.ImgIds,
})
return err
}
+9 -43
View File
@@ -6,58 +6,24 @@ package svc
import (
"sundynix-micro-go/app/file/rpc/fileservice"
"sundynix-micro-go/app/plant/api/internal/config"
plantModel "sundynix-micro-go/app/plant/model"
"sundynix-micro-go/app/plant/rpc/plantservice"
"sundynix-micro-go/app/user/rpc/userservice"
"github.com/zeromicro/go-zero/core/logx"
"github.com/zeromicro/go-zero/zrpc"
"gorm.io/driver/mysql"
"gorm.io/gorm"
)
type ServiceContext struct {
Config config.Config
DB *gorm.DB
UserRpc userservice.UserService
FileRpc fileservice.FileService
Config config.Config
PlantRpc plantservice.PlantService
UserRpc userservice.UserService
FileRpc fileservice.FileService
}
func NewServiceContext(c config.Config) *ServiceContext {
db, err := gorm.Open(mysql.Open(c.DB.DataSource), &gorm.Config{})
if err != nil {
logx.Errorf("连接数据库失败: %v", err)
panic(err)
}
// 自动迁移
if err := db.AutoMigrate(
&plantModel.SundynixPlantUserProfile{},
&plantModel.SundynixMyPlant{},
&plantModel.SundynixCarePlan{},
&plantModel.SundynixCareRecord{},
&plantModel.SundynixCareTask{},
&plantModel.SundynixGrowthRecord{},
&plantModel.SundynixWiki{},
&plantModel.SundynixWikiClass{},
&plantModel.SundynixPost{},
&plantModel.SundynixPostComment{},
&plantModel.SundynixPostLike{},
&plantModel.SundynixPostTopic{},
&plantModel.SundynixUserStar{},
&plantModel.SundynixExchangeItem{},
&plantModel.SundynixExchangeOrder{},
&plantModel.SundynixLevelConfig{},
&plantModel.SundynixBadgeConfig{},
&plantModel.SundynixUserBadge{},
&plantModel.SundynixAiChatHistory{},
); err != nil {
logx.Errorf("数据库迁移失败: %v", err)
}
return &ServiceContext{
Config: c,
DB: db,
UserRpc: userservice.NewUserService(zrpc.MustNewClient(c.UserRpc)),
FileRpc: fileservice.NewFileService(zrpc.MustNewClient(c.FileRpc)),
Config: c,
PlantRpc: plantservice.NewPlantService(zrpc.MustNewClient(c.PlantRpc)),
UserRpc: userservice.NewUserService(zrpc.MustNewClient(c.UserRpc)),
FileRpc: fileservice.NewFileService(zrpc.MustNewClient(c.FileRpc)),
}
}