Files
order/dao/order_dao.go

300 lines
7.7 KiB
Go
Raw Permalink Normal View History

2025-12-10 09:02:41 +08:00
package dao
import (
"context"
"errors"
"fmt"
2025-12-15 09:02:30 +08:00
"strings"
2025-12-10 09:02:41 +08:00
"time"
2025-12-10 13:51:09 +08:00
"go.mongodb.org/mongo-driver/v2/bson"
2025-12-15 09:02:30 +08:00
"go.mongodb.org/mongo-driver/v2/mongo/options"
2025-12-10 13:51:09 +08:00
"order/consts"
2025-12-10 09:02:41 +08:00
"order/model/entity"
2026-02-24 17:17:10 +08:00
"gitea.com/red-future/common/db/mongo"
2025-12-15 09:02:30 +08:00
)
2025-12-10 14:39:03 +08:00
type order struct {
}
2025-12-10 09:02:41 +08:00
2025-12-10 13:51:09 +08:00
// Order 订单数据访问对象
2025-12-30 11:03:11 +08:00
var Order = &order{}
2025-12-10 09:02:41 +08:00
// getCollection 根据订单状态获取对应的集合
2025-12-10 13:51:09 +08:00
func (d *order) getCollection(status consts.OrderStatus) (string, error) {
switch status {
case consts.OrderStatusPending:
return consts.OrderPendingCollection, nil
case consts.OrderStatusPaid:
return consts.OrderPaidCollection, nil
case consts.OrderStatusShipped:
return consts.OrderShippedCollection, nil
case consts.OrderStatusCompleted:
return consts.OrderCompletedCollection, nil
default:
return "", fmt.Errorf("collection for status %s not found", status)
2025-12-10 09:02:41 +08:00
}
}
// CreatePendingOrder 创建待支付订单
2025-12-10 13:51:09 +08:00
func (d *order) CreatePendingOrder(ctx context.Context, order *entity.OrderPending) error {
collection, err := d.getCollection(consts.OrderStatusPending)
2025-12-10 09:02:41 +08:00
if err != nil {
return err
}
2025-12-12 16:20:47 +08:00
order.Id = bson.NewObjectID()
2025-12-10 09:02:41 +08:00
order.CreatedAt = time.Now()
order.UpdatedAt = time.Now()
2025-12-30 11:03:11 +08:00
_, err = mongo.DB().Insert(ctx, []interface{}{order}, collection)
2025-12-10 09:02:41 +08:00
return err
}
// GetOrderByNo 根据订单号查询订单(自动识别状态)
2025-12-12 18:16:28 +08:00
func (d *order) GetOrderByNo(ctx context.Context, orderNo string) (interface{}, consts.OrderStatus, error) {
2025-12-10 09:02:41 +08:00
// 按状态优先级搜索(从最新状态开始)
2025-12-10 13:51:09 +08:00
statuses := []consts.OrderStatus{
consts.OrderStatusCompleted,
consts.OrderStatusShipped,
consts.OrderStatusPaid,
consts.OrderStatusPending,
2025-12-10 09:02:41 +08:00
}
for _, status := range statuses {
collection, err := d.getCollection(status)
if err != nil {
continue
}
switch status {
2025-12-10 13:51:09 +08:00
case consts.OrderStatusPending:
2025-12-10 09:02:41 +08:00
var order entity.OrderPending
2025-12-12 18:16:28 +08:00
if err := d.findOrderByNo(collection, ctx, orderNo, &order); err == nil {
2025-12-10 09:02:41 +08:00
return &order, status, nil
}
2025-12-10 13:51:09 +08:00
case consts.OrderStatusPaid:
2025-12-10 09:02:41 +08:00
var order entity.OrderPaid
2025-12-12 18:16:28 +08:00
if err := d.findOrderByNo(collection, ctx, orderNo, &order); err == nil {
2025-12-10 09:02:41 +08:00
return &order, status, nil
}
2025-12-10 13:51:09 +08:00
case consts.OrderStatusShipped:
2025-12-10 09:02:41 +08:00
var order entity.OrderShipped
2025-12-12 18:16:28 +08:00
if err := d.findOrderByNo(collection, ctx, orderNo, &order); err == nil {
2025-12-10 09:02:41 +08:00
return &order, status, nil
}
2025-12-10 13:51:09 +08:00
case consts.OrderStatusCompleted:
2025-12-10 09:02:41 +08:00
var order entity.OrderCompleted
2025-12-12 18:16:28 +08:00
if err := d.findOrderByNo(collection, ctx, orderNo, &order); err == nil {
2025-12-10 09:02:41 +08:00
return &order, status, nil
}
}
}
return nil, "", errors.New("order not found")
}
// findOrderByNo 通用订单查询方法
2025-12-12 18:16:28 +08:00
func (d *order) findOrderByNo(collection string, ctx context.Context, orderNo string, result interface{}) error {
2025-12-10 09:02:41 +08:00
filter := bson.M{
2025-12-12 18:16:28 +08:00
"order_no": orderNo,
2025-12-10 09:02:41 +08:00
}
2025-12-30 11:03:11 +08:00
err := mongo.DB().FindOne(ctx, filter, result, collection)
2025-12-10 13:51:09 +08:00
if err != nil {
2025-12-10 09:02:41 +08:00
return errors.New("order not found")
}
2025-12-10 13:51:09 +08:00
return nil
2025-12-10 09:02:41 +08:00
}
// MoveOrderToStatus 将订单从一个状态移动到另一个状态
2025-12-12 18:16:28 +08:00
func (d *order) MoveOrderToStatus(ctx context.Context, fromStatus, toStatus consts.OrderStatus, orderNo string, updateData bson.M) error {
2025-12-10 09:02:41 +08:00
// 获取源集合
srcCollection, err := d.getCollection(fromStatus)
if err != nil {
return err
}
// 获取目标集合
destCollection, err := d.getCollection(toStatus)
if err != nil {
return err
}
// 查找源订单
var orderData bson.M
filter := bson.M{
2025-12-12 18:16:28 +08:00
"order_no": orderNo,
2025-12-10 09:02:41 +08:00
}
2025-12-30 11:03:11 +08:00
err = mongo.DB().FindOne(ctx, filter, &orderData, srcCollection)
2025-12-10 09:02:41 +08:00
if err != nil {
return err
}
// 更新数据
orderData["updated_at"] = time.Now()
for key, value := range updateData {
orderData[key] = value
}
// 插入到目标集合
2025-12-30 11:03:11 +08:00
_, err = mongo.DB().Insert(ctx, []interface{}{orderData}, destCollection)
2025-12-10 09:02:41 +08:00
if err != nil {
return err
}
// 从源集合删除
2025-12-30 11:03:11 +08:00
_, err = mongo.DB().Delete(ctx, filter, srcCollection)
2025-12-10 09:02:41 +08:00
return err
}
// UpdatePendingOrder 更新待支付订单
2025-12-12 18:16:28 +08:00
func (d *order) UpdatePendingOrder(ctx context.Context, orderNo string, update bson.M) error {
2025-12-10 13:51:09 +08:00
collection, err := d.getCollection(consts.OrderStatusPending)
2025-12-10 09:02:41 +08:00
if err != nil {
return err
}
update["updated_at"] = time.Now()
2025-12-10 13:51:09 +08:00
filter := bson.M{
2025-12-12 18:16:28 +08:00
"order_no": orderNo,
2025-12-10 13:51:09 +08:00
}
2025-12-30 11:03:11 +08:00
_, err = mongo.DB().Update(ctx, filter, bson.M{"$set": update}, collection)
2025-12-10 09:02:41 +08:00
return err
}
// ListOrdersByStatus 根据状态查询订单列表
2025-12-15 09:02:30 +08:00
func (d *order) ListOrdersByStatus(ctx context.Context, status consts.OrderStatus, userID string, page int, pageSize int, sortFields ...string) (interface{}, int64, error) {
2025-12-10 09:02:41 +08:00
collection, err := d.getCollection(status)
if err != nil {
return nil, 0, err
}
// 构建查询条件
2025-12-12 18:16:28 +08:00
filter := bson.M{}
2025-12-10 09:02:41 +08:00
if userID != "" {
filter["user_id"] = userID
}
// 计算总数
2025-12-30 11:03:11 +08:00
total, err := mongo.DB().Count(ctx, filter, collection)
2025-12-10 09:02:41 +08:00
if err != nil {
return nil, 0, err
}
2025-12-15 09:02:30 +08:00
// 设置分页参数
var findOptions []options.Lister[options.FindOptions]
if page > 0 && pageSize > 0 {
findOptions = append(findOptions, options.Find().SetSkip(int64((page-1)*pageSize)).SetLimit(int64(pageSize)))
}
// 设置排序参数
if len(sortFields) > 0 {
sort := bson.D{}
for _, field := range sortFields {
var order int
if strings.HasPrefix(field, "-") {
order = -1
field = strings.TrimPrefix(field, "-")
} else {
order = 1
}
sort = append(sort, bson.E{Key: field, Value: order})
}
findOptions = append(findOptions, options.Find().SetSort(sort))
}
2025-12-10 09:02:41 +08:00
// 根据状态返回对应的订单类型
switch status {
2025-12-10 13:51:09 +08:00
case consts.OrderStatusPending:
2025-12-10 09:02:41 +08:00
var orders []entity.OrderPending
2025-12-30 11:03:11 +08:00
if err := mongo.DB().Find(ctx, filter, &orders, collection, findOptions...); err != nil {
2025-12-10 09:02:41 +08:00
return nil, 0, err
}
return orders, total, nil
2025-12-10 13:51:09 +08:00
case consts.OrderStatusPaid:
2025-12-10 09:02:41 +08:00
var orders []entity.OrderPaid
2025-12-30 11:03:11 +08:00
if err := mongo.DB().Find(ctx, filter, &orders, collection, findOptions...); err != nil {
2025-12-10 09:02:41 +08:00
return nil, 0, err
}
return orders, total, nil
2025-12-10 13:51:09 +08:00
case consts.OrderStatusShipped:
2025-12-10 09:02:41 +08:00
var orders []entity.OrderShipped
2025-12-30 11:03:11 +08:00
if err := mongo.DB().Find(ctx, filter, &orders, collection, findOptions...); err != nil {
2025-12-10 09:02:41 +08:00
return nil, 0, err
}
return orders, total, nil
2025-12-10 13:51:09 +08:00
case consts.OrderStatusCompleted:
2025-12-10 09:02:41 +08:00
var orders []entity.OrderCompleted
2025-12-30 11:03:11 +08:00
if err := mongo.DB().Find(ctx, filter, &orders, collection, findOptions...); err != nil {
2025-12-10 09:02:41 +08:00
return nil, 0, err
}
return orders, total, nil
default:
return nil, 0, errors.New("unsupported order status")
}
}
// GetExpiredPendingOrders 获取过期的待支付订单
2025-12-15 09:02:30 +08:00
// GetPendingOrder gets pending order by order number
func (d *order) GetPendingOrder(ctx context.Context, orderNo string) (*entity.OrderPending, error) {
collection, err := d.getCollection(consts.OrderStatusPending)
if err != nil {
return nil, err
}
filter := bson.M{"order_no": orderNo}
var order entity.OrderPending
2025-12-30 11:03:11 +08:00
if err := mongo.DB().FindOne(ctx, filter, &order, collection); err != nil {
2025-12-15 09:02:30 +08:00
if err.Error() == "mongo: no documents in result" {
return nil, nil
}
return nil, err
}
return &order, nil
}
2025-12-12 18:16:28 +08:00
func (d *order) GetExpiredPendingOrders(ctx context.Context) ([]entity.OrderPending, error) {
2025-12-10 13:51:09 +08:00
collection, err := d.getCollection(consts.OrderStatusPending)
2025-12-10 09:02:41 +08:00
if err != nil {
return nil, err
}
filter := bson.M{
"expired_at": bson.M{"$lte": time.Now()},
}
var orders []entity.OrderPending
2025-12-30 11:03:11 +08:00
if err := mongo.DB().Find(ctx, filter, &orders, collection); err != nil {
2025-12-10 09:02:41 +08:00
return nil, err
}
return orders, nil
}
// UpdatePayInfo 更新支付信息(待支付订单)
2025-12-12 18:16:28 +08:00
func (d *order) UpdatePayInfo(ctx context.Context, orderNo string, payInfo entity.PayInfo) error {
2025-12-10 13:51:09 +08:00
collection, err := d.getCollection(consts.OrderStatusPending)
2025-12-10 09:02:41 +08:00
if err != nil {
return err
}
2025-12-10 13:51:09 +08:00
filter := bson.M{
2025-12-12 18:16:28 +08:00
"order_no": orderNo,
2025-12-10 13:51:09 +08:00
}
update := bson.M{
2025-12-10 09:02:41 +08:00
"pay_info": payInfo,
"updated_at": time.Now(),
2025-12-10 13:51:09 +08:00
}
2025-12-30 11:03:11 +08:00
_, err = mongo.DB().Update(ctx, filter, bson.M{"$set": update}, collection)
2025-12-10 09:02:41 +08:00
return err
}