正在显示
65 个修改的文件
包含
4031 行增加
和
123 行删除
| @@ -78,6 +78,10 @@ spec: | @@ -78,6 +78,10 @@ spec: | ||
| 78 | value: "6DwjBO735" | 78 | value: "6DwjBO735" |
| 79 | - name: BUSINESS_ADMIN_HOST | 79 | - name: BUSINESS_ADMIN_HOST |
| 80 | value: "http://suplus-business-admin-dev.fjmaimaimai.com" | 80 | value: "http://suplus-business-admin-dev.fjmaimaimai.com" |
| 81 | + - name: KAFKA_HOST | ||
| 82 | + value: "192.168.0.250:9092;192.168.0.251:9092;192.168.0.252:9092" | ||
| 83 | + - name: KAFKA_CONSUMER_ID | ||
| 84 | + value: "partnermg_dev" | ||
| 81 | volumes: | 85 | volumes: |
| 82 | - name: accesslogs | 86 | - name: accesslogs |
| 83 | emptyDir: {} | 87 | emptyDir: {} |
| @@ -60,7 +60,7 @@ spec: | @@ -60,7 +60,7 @@ spec: | ||
| 60 | - name: POSTGRESQL_PORT | 60 | - name: POSTGRESQL_PORT |
| 61 | value: "31544" | 61 | value: "31544" |
| 62 | - name: LOG_LEVEL | 62 | - name: LOG_LEVEL |
| 63 | - value: "debug" | 63 | + value: "info" |
| 64 | - name: ERROR_BASE_CODE | 64 | - name: ERROR_BASE_CODE |
| 65 | value: "1" | 65 | value: "1" |
| 66 | - name: ERROR_BASE_CODE_MULTIPLE | 66 | - name: ERROR_BASE_CODE_MULTIPLE |
| @@ -75,6 +75,10 @@ spec: | @@ -75,6 +75,10 @@ spec: | ||
| 75 | value: "rsF0pL!6DwjBO735" | 75 | value: "rsF0pL!6DwjBO735" |
| 76 | - name: BUSINESS_ADMIN_HOST | 76 | - name: BUSINESS_ADMIN_HOST |
| 77 | value: "http://suplus-business-admin-prd.fjmaimaimai.com" | 77 | value: "http://suplus-business-admin-prd.fjmaimaimai.com" |
| 78 | + - name: KAFKA_HOST | ||
| 79 | + value: "192.168.0.250:9092;192.168.0.251:9092;192.168.0.252:9092" | ||
| 80 | + - name: KAFKA_CONSUMER_ID | ||
| 81 | + value: "partnermg_prd" | ||
| 78 | volumes: | 82 | volumes: |
| 79 | - name: accesslogs | 83 | - name: accesslogs |
| 80 | emptyDir: {} | 84 | emptyDir: {} |
| @@ -75,6 +75,10 @@ spec: | @@ -75,6 +75,10 @@ spec: | ||
| 75 | value: "rsF0pL!6DwjBO735" | 75 | value: "rsF0pL!6DwjBO735" |
| 76 | - name: BUSINESS_ADMIN_HOST | 76 | - name: BUSINESS_ADMIN_HOST |
| 77 | value: "http://suplus-business-admin-test.fjmaimaimai.com" | 77 | value: "http://suplus-business-admin-test.fjmaimaimai.com" |
| 78 | + - name: KAFKA_HOST | ||
| 79 | + value: "192.168.0.250:9092;192.168.0.251:9092;192.168.0.252:9092" | ||
| 80 | + - name: KAFKA_CONSUMER_ID | ||
| 81 | + value: "partnermg_test" | ||
| 78 | volumes: | 82 | volumes: |
| 79 | - name: accesslogs | 83 | - name: accesslogs |
| 80 | emptyDir: {} | 84 | emptyDir: {} |
| @@ -4,8 +4,10 @@ go 1.14 | @@ -4,8 +4,10 @@ go 1.14 | ||
| 4 | 4 | ||
| 5 | require ( | 5 | require ( |
| 6 | github.com/GeeTeam/gt3-golang-sdk v0.0.0-20200116043922-446ca8a507d2 | 6 | github.com/GeeTeam/gt3-golang-sdk v0.0.0-20200116043922-446ca8a507d2 |
| 7 | + github.com/Shopify/sarama v1.23.1 | ||
| 7 | github.com/ajg/form v1.5.1 // indirect | 8 | github.com/ajg/form v1.5.1 // indirect |
| 8 | github.com/astaxie/beego v1.12.2 | 9 | github.com/astaxie/beego v1.12.2 |
| 10 | + github.com/bsm/sarama-cluster v2.1.15+incompatible | ||
| 9 | github.com/dgrijalva/jwt-go v3.2.0+incompatible | 11 | github.com/dgrijalva/jwt-go v3.2.0+incompatible |
| 10 | github.com/fasthttp-contrib/websocket v0.0.0-20160511215533-1f3b11f56072 // indirect | 12 | github.com/fasthttp-contrib/websocket v0.0.0-20160511215533-1f3b11f56072 // indirect |
| 11 | github.com/fatih/structs v1.1.0 // indirect | 13 | github.com/fatih/structs v1.1.0 // indirect |
| 1 | package main | 1 | package main |
| 2 | 2 | ||
| 3 | import ( | 3 | import ( |
| 4 | + "context" | ||
| 5 | + "os" | ||
| 6 | + "os/signal" | ||
| 7 | + "syscall" | ||
| 8 | + | ||
| 4 | "github.com/astaxie/beego" | 9 | "github.com/astaxie/beego" |
| 5 | "github.com/astaxie/beego/logs" | 10 | "github.com/astaxie/beego/logs" |
| 6 | _ "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg" | 11 | _ "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg" |
| 7 | _ "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/log" | 12 | _ "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/log" |
| 8 | _ "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/port/beego" | 13 | _ "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/port/beego" |
| 14 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/port/consumer" | ||
| 9 | ) | 15 | ) |
| 10 | 16 | ||
| 11 | func main() { | 17 | func main() { |
| 18 | + sigs := make(chan os.Signal, 1) | ||
| 19 | + signal.Notify(sigs, os.Interrupt, os.Kill, syscall.SIGINT, syscall.SIGTERM) | ||
| 20 | + ctx, cancel := context.WithCancel(context.Background()) | ||
| 21 | + go func() { | ||
| 12 | logs.Info("应用启动") | 22 | logs.Info("应用启动") |
| 13 | beego.Run() | 23 | beego.Run() |
| 24 | + }() | ||
| 25 | + consumerRun := consumer.NewRuner() | ||
| 26 | + | ||
| 27 | + if err := consumerRun.InitConsumer(); err != nil { | ||
| 28 | + logs.Error("启动kafka消息消费者失败:%s", err) | ||
| 29 | + } | ||
| 30 | + | ||
| 31 | + go func() { | ||
| 32 | + consumerRun.Start(ctx) | ||
| 33 | + }() | ||
| 34 | + go func() { | ||
| 35 | + <-consumerRun.IsReady() | ||
| 36 | + logs.Info("Sarama consumer up and running!...") | ||
| 37 | + }() | ||
| 38 | + for { | ||
| 39 | + select { | ||
| 40 | + case <-sigs: | ||
| 41 | + cancel() | ||
| 42 | + return | ||
| 43 | + default: | ||
| 44 | + } | ||
| 45 | + } | ||
| 14 | } | 46 | } |
| 1 | +package subscriber | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "fmt" | ||
| 5 | + "time" | ||
| 6 | + | ||
| 7 | + coreDomain "github.com/linmadan/egglib-go/core/domain" | ||
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 9 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain/event" | ||
| 10 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | ||
| 11 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/repository" | ||
| 12 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/lib" | ||
| 13 | +) | ||
| 14 | + | ||
| 15 | +//订单数据修改触发的订阅事件 | ||
| 16 | +type OrderLogSubscriber struct { | ||
| 17 | + TransactionContext *transaction.TransactionContext | ||
| 18 | +} | ||
| 19 | + | ||
| 20 | +var _ coreDomain.DomainEventSubscriber = (*OrderLogSubscriber)(nil) | ||
| 21 | + | ||
| 22 | +func (subscriber *OrderLogSubscriber) HandleEvent(domainEvent coreDomain.DomainEvent) error { | ||
| 23 | + var ( | ||
| 24 | + orderLogRepository domain.OrderLogRepository | ||
| 25 | + userRepository domain.UsersRepository | ||
| 26 | + adminUser domain.Users | ||
| 27 | + err error | ||
| 28 | + ) | ||
| 29 | + | ||
| 30 | + if orderLogRepository, err = repository.NewOrderLogRepository(subscriber.TransactionContext); err != nil { | ||
| 31 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 32 | + } | ||
| 33 | + if userRepository, err = repository.NewUsersRepository(subscriber.TransactionContext); err != nil { | ||
| 34 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 35 | + } | ||
| 36 | + | ||
| 37 | + switch domainEvent.EventType() { | ||
| 38 | + //订单分红因为货品的数量变动而发送改变 | ||
| 39 | + case event.UPDATE_BONUS_BY_GOOD_NUMBER_EVENT: | ||
| 40 | + currentEvent := domainEvent.(event.UpdateBonusByGoodNumber) | ||
| 41 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: currentEvent.AdminId}) | ||
| 42 | + if err != nil { | ||
| 43 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 44 | + } | ||
| 45 | + orderLog := domain.OrderLog{ | ||
| 46 | + OperatorType: domain.ORDER_LOG_OPERATOR_ADMIN, | ||
| 47 | + OperatorId: currentEvent.AdminId, | ||
| 48 | + Operator: adminUser.Name, | ||
| 49 | + AlterTime: time.Now(), | ||
| 50 | + DataFrom: domain.ORDER_LOG_FROM, | ||
| 51 | + LogAction: "修改", | ||
| 52 | + OrderId: currentEvent.OrderId, | ||
| 53 | + GoodId: currentEvent.GoodId, | ||
| 54 | + Descript: []domain.OrderLogDescript{ | ||
| 55 | + domain.OrderLogDescript{ | ||
| 56 | + Title: "调整商品数量", | ||
| 57 | + Item: currentEvent.GoodName, | ||
| 58 | + Action: []string{ | ||
| 59 | + fmt.Sprintf(`购买数量由"%s"调整为"%s"`, currentEvent.FormerNumber, currentEvent.NewNumber), | ||
| 60 | + fmt.Sprintf(`商品总价由"¥%s"调整为"¥%s"`, currentEvent.FormerAmount, currentEvent.NewAmount), | ||
| 61 | + }, | ||
| 62 | + }, | ||
| 63 | + }, | ||
| 64 | + } | ||
| 65 | + err = orderLogRepository.Add(&orderLog) | ||
| 66 | + break | ||
| 67 | + //订单分红因为合伙人分红比例变动而发送改变 | ||
| 68 | + case event.UPDATE_BONUS_BY_PARTENT_BONUS_PERCENT_EVENT: | ||
| 69 | + currentEvent := domainEvent.(event.UpdateBounsByPartnerBonusPercent) | ||
| 70 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: currentEvent.AdminId}) | ||
| 71 | + if err != nil { | ||
| 72 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 73 | + } | ||
| 74 | + orderLog := domain.OrderLog{ | ||
| 75 | + OperatorType: domain.ORDER_LOG_OPERATOR_ADMIN, | ||
| 76 | + OperatorId: currentEvent.AdminId, | ||
| 77 | + Operator: adminUser.Name, | ||
| 78 | + AlterTime: time.Now(), | ||
| 79 | + DataFrom: domain.ORDER_LOG_FROM, | ||
| 80 | + LogAction: "修改", | ||
| 81 | + OrderId: currentEvent.OrderId, | ||
| 82 | + GoodId: currentEvent.GoodId, | ||
| 83 | + Descript: []domain.OrderLogDescript{ | ||
| 84 | + domain.OrderLogDescript{ | ||
| 85 | + Title: "合伙人分红比例", | ||
| 86 | + Item: currentEvent.GoodName, | ||
| 87 | + Action: []string{ | ||
| 88 | + fmt.Sprintf(`分红比例由"%s"调整为"%s"`, currentEvent.FormerPartnerBonusPercent, currentEvent.NewPartnerBonusPercent), | ||
| 89 | + fmt.Sprintf(`应收分红由"¥%s"调整为"¥%s"`, currentEvent.FormerPartnerBonus, currentEvent.NewPartnerBonus), | ||
| 90 | + }, | ||
| 91 | + }, | ||
| 92 | + }, | ||
| 93 | + } | ||
| 94 | + err = orderLogRepository.Add(&orderLog) | ||
| 95 | + break | ||
| 96 | + //更新订单的备注 | ||
| 97 | + case event.UPDATE_ORDER_REMARK: | ||
| 98 | + currentEvent := domainEvent.(event.UpdateOrderRemark) | ||
| 99 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: currentEvent.AdminId}) | ||
| 100 | + if err != nil { | ||
| 101 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 102 | + } | ||
| 103 | + orderLog := domain.OrderLog{ | ||
| 104 | + OperatorType: domain.ORDER_LOG_OPERATOR_ADMIN, | ||
| 105 | + OperatorId: currentEvent.AdminId, | ||
| 106 | + Operator: adminUser.Name, | ||
| 107 | + AlterTime: time.Now(), | ||
| 108 | + DataFrom: domain.ORDER_LOG_FROM, | ||
| 109 | + LogAction: "修改", | ||
| 110 | + OrderId: currentEvent.OrderId, | ||
| 111 | + GoodId: 0, | ||
| 112 | + Descript: []domain.OrderLogDescript{ | ||
| 113 | + domain.OrderLogDescript{ | ||
| 114 | + Title: "编辑备注", | ||
| 115 | + Item: currentEvent.NewRemark, | ||
| 116 | + Action: []string{}, | ||
| 117 | + }, | ||
| 118 | + }, | ||
| 119 | + } | ||
| 120 | + err = orderLogRepository.Add(&orderLog) | ||
| 121 | + break | ||
| 122 | + // 支付订单中货品的分红 | ||
| 123 | + case event.PAY_ORDER_GOOD_BONUS_EVENT: | ||
| 124 | + currentEvent := domainEvent.(event.PayOrderGoodBonus) | ||
| 125 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: currentEvent.AdminId}) | ||
| 126 | + if err != nil { | ||
| 127 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 128 | + } | ||
| 129 | + orderLog := domain.OrderLog{ | ||
| 130 | + OperatorType: domain.ORDER_LOG_OPERATOR_ADMIN, | ||
| 131 | + OperatorId: currentEvent.AdminId, | ||
| 132 | + Operator: adminUser.Name, | ||
| 133 | + AlterTime: time.Now(), | ||
| 134 | + DataFrom: domain.ORDER_LOG_FROM, | ||
| 135 | + LogAction: "支付", | ||
| 136 | + OrderId: currentEvent.OrderId, | ||
| 137 | + GoodId: currentEvent.GoodId, | ||
| 138 | + Descript: []domain.OrderLogDescript{ | ||
| 139 | + domain.OrderLogDescript{ | ||
| 140 | + Title: "支付分红", | ||
| 141 | + Item: currentEvent.GoodName, | ||
| 142 | + Action: []string{ | ||
| 143 | + fmt.Sprintf(`支付分红"¥%.2f"`, currentEvent.PartnerBonus), | ||
| 144 | + }, | ||
| 145 | + }, | ||
| 146 | + }, | ||
| 147 | + } | ||
| 148 | + err = orderLogRepository.Add(&orderLog) | ||
| 149 | + break | ||
| 150 | + } | ||
| 151 | + return err | ||
| 152 | +} | ||
| 153 | + | ||
| 154 | +func (subscriber *OrderLogSubscriber) SubscribedToEventTypes() []string { | ||
| 155 | + return []string{ | ||
| 156 | + event.UPDATE_BONUS_BY_GOOD_NUMBER_EVENT, | ||
| 157 | + event.UPDATE_BONUS_BY_PARTENT_BONUS_PERCENT_EVENT, | ||
| 158 | + event.UPDATE_ORDER_REMARK, | ||
| 159 | + event.PAY_ORDER_GOOD_BONUS_EVENT, | ||
| 160 | + } | ||
| 161 | +} |
| @@ -21,6 +21,14 @@ func CreateOrderBaseDao(options map[string]interface{}) (*dao.OrderBaseDao, erro | @@ -21,6 +21,14 @@ func CreateOrderBaseDao(options map[string]interface{}) (*dao.OrderBaseDao, erro | ||
| 21 | return dao.NewOrderBaseDao(transactionContext) | 21 | return dao.NewOrderBaseDao(transactionContext) |
| 22 | } | 22 | } |
| 23 | 23 | ||
| 24 | +func CreateOrderBestshopDao(options map[string]interface{}) (*dao.OrderBestshopDao, error) { | ||
| 25 | + var transactionContext *transaction.TransactionContext | ||
| 26 | + if value, ok := options["transactionContext"]; ok { | ||
| 27 | + transactionContext = value.(*transaction.TransactionContext) | ||
| 28 | + } | ||
| 29 | + return dao.NewOrderBestshopDao(transactionContext) | ||
| 30 | +} | ||
| 31 | + | ||
| 24 | func CreateUsersDao(options map[string]interface{}) (*dao.UsersDao, error) { | 32 | func CreateUsersDao(options map[string]interface{}) (*dao.UsersDao, error) { |
| 25 | var transactionContext *transaction.TransactionContext | 33 | var transactionContext *transaction.TransactionContext |
| 26 | if value, ok := options["transactionContext"]; ok { | 34 | if value, ok := options["transactionContext"]; ok { |
| @@ -13,3 +13,11 @@ func CreateBusinessBonusService(options map[string]interface{}) (service.Busines | @@ -13,3 +13,11 @@ func CreateBusinessBonusService(options map[string]interface{}) (service.Busines | ||
| 13 | } | 13 | } |
| 14 | return domainService.NewBusinessBonusService(transactionContext), nil | 14 | return domainService.NewBusinessBonusService(transactionContext), nil |
| 15 | } | 15 | } |
| 16 | + | ||
| 17 | +func CreateOrderBonusService(options map[string]interface{}) (service.OrderBonusService, error) { | ||
| 18 | + var transactionContext *transaction.TransactionContext | ||
| 19 | + if value, ok := options["transactionContext"]; ok { | ||
| 20 | + transactionContext = value.(*transaction.TransactionContext) | ||
| 21 | + } | ||
| 22 | + return domainService.NewOrderBonusService(transactionContext), nil | ||
| 23 | +} |
| @@ -42,7 +42,7 @@ func CreateOrderGoodRepository(options map[string]interface{}) (domain.OrderGood | @@ -42,7 +42,7 @@ func CreateOrderGoodRepository(options map[string]interface{}) (domain.OrderGood | ||
| 42 | return repository.NewOrderGoodRepository(transactionContext) | 42 | return repository.NewOrderGoodRepository(transactionContext) |
| 43 | } | 43 | } |
| 44 | 44 | ||
| 45 | -//CreateOrderGoodRepository 订单信息 | 45 | +//CreateOrderGoodRepository 订单货品信息 |
| 46 | func CreateUsersRepository(options map[string]interface{}) (domain.UsersRepository, error) { | 46 | func CreateUsersRepository(options map[string]interface{}) (domain.UsersRepository, error) { |
| 47 | var transactionContext *transaction.TransactionContext | 47 | var transactionContext *transaction.TransactionContext |
| 48 | if value, ok := options["transactionContext"]; ok { | 48 | if value, ok := options["transactionContext"]; ok { |
| @@ -77,3 +77,30 @@ func CreateBusinessBonusRepository(options map[string]interface{}) (domain.Busin | @@ -77,3 +77,30 @@ func CreateBusinessBonusRepository(options map[string]interface{}) (domain.Busin | ||
| 77 | } | 77 | } |
| 78 | return repository.NewBusinessBonusRepository(transactionContext) | 78 | return repository.NewBusinessBonusRepository(transactionContext) |
| 79 | } | 79 | } |
| 80 | + | ||
| 81 | +//CreateOrderGoodBestshopRepository 小米(海鲜干货改)的订单商品信息 | ||
| 82 | +func CreateOrderGoodBestshopRepository(options map[string]interface{}) (domain.OrderGoodBestshopRepository, error) { | ||
| 83 | + var transactionContext *transaction.TransactionContext | ||
| 84 | + if value, ok := options["transactionContext"]; ok { | ||
| 85 | + transactionContext = value.(*transaction.TransactionContext) | ||
| 86 | + } | ||
| 87 | + return repository.NewOrderGoodBestshopRepository(transactionContext) | ||
| 88 | +} | ||
| 89 | + | ||
| 90 | +//CreateOrderGoodBestshopRepository 小米(海鲜干货改)订单信息 | ||
| 91 | +func CreateOrderBestshopRepository(options map[string]interface{}) (domain.OrderBestshopRepository, error) { | ||
| 92 | + var transactionContext *transaction.TransactionContext | ||
| 93 | + if value, ok := options["transactionContext"]; ok { | ||
| 94 | + transactionContext = value.(*transaction.TransactionContext) | ||
| 95 | + } | ||
| 96 | + return repository.NewOrderBestshopRepository(transactionContext) | ||
| 97 | +} | ||
| 98 | + | ||
| 99 | +//CreateOrderGoodBestshopRepository小米(海鲜干货改)订单信息 | ||
| 100 | +func CreateOrderLogRepository(options map[string]interface{}) (domain.OrderLogRepository, error) { | ||
| 101 | + var transactionContext *transaction.TransactionContext | ||
| 102 | + if value, ok := options["transactionContext"]; ok { | ||
| 103 | + transactionContext = value.(*transaction.TransactionContext) | ||
| 104 | + } | ||
| 105 | + return repository.NewOrderLogRepository(transactionContext) | ||
| 106 | +} |
| @@ -2,6 +2,7 @@ package command | @@ -2,6 +2,7 @@ package command | ||
| 2 | 2 | ||
| 3 | import "time" | 3 | import "time" |
| 4 | 4 | ||
| 5 | +//订单发货 | ||
| 5 | type OrderDeliveryCommand struct { | 6 | type OrderDeliveryCommand struct { |
| 6 | OrderId int64 `json:"orderId"` | 7 | OrderId int64 `json:"orderId"` |
| 7 | DeliveryTime time.Time `json:"deliveryTime"` | 8 | DeliveryTime time.Time `json:"deliveryTime"` |
| 1 | package command | 1 | package command |
| 2 | 2 | ||
| 3 | -//更新订单的商品数字并更新分红的数据 | 3 | +//UpdateGoodBouns 更新订单的商品数量,和支付状态 并更新分红的数据 |
| 4 | type UpdateGoodBouns struct { | 4 | type UpdateGoodBouns struct { |
| 5 | Id int64 `json:"id"` //订单id | 5 | Id int64 `json:"id"` //订单id |
| 6 | GoodBouns []GoodBouns `json:"goodBouns"` | 6 | GoodBouns []GoodBouns `json:"goodBouns"` |
| @@ -10,9 +10,11 @@ type ListOrderBaseQuery struct { | @@ -10,9 +10,11 @@ type ListOrderBaseQuery struct { | ||
| 10 | Offset int `json:"offset" ` | 10 | Offset int `json:"offset" ` |
| 11 | // 查询限制 | 11 | // 查询限制 |
| 12 | Limit int `json:"limit"` | 12 | Limit int `json:"limit"` |
| 13 | - //订单类型 | ||
| 14 | - OrderType int `json:"orderType"` | ||
| 15 | //发货单号 | 13 | //发货单号 |
| 16 | DeliveryCode string `json:"deliveryCode"` | 14 | DeliveryCode string `json:"deliveryCode"` |
| 17 | CompanyId int64 `json:"companyId"` | 15 | CompanyId int64 `json:"companyId"` |
| 16 | + | ||
| 17 | + //订单类型 | ||
| 18 | + OrderType int `json:"orderType"` | ||
| 19 | + PartnerOrCode string `json:"partner_or_code"` | ||
| 18 | } | 20 | } |
| @@ -2,19 +2,24 @@ package service | @@ -2,19 +2,24 @@ package service | ||
| 2 | 2 | ||
| 3 | import ( | 3 | import ( |
| 4 | "fmt" | 4 | "fmt" |
| 5 | + "strings" | ||
| 5 | "time" | 6 | "time" |
| 6 | 7 | ||
| 7 | "github.com/astaxie/beego/logs" | 8 | "github.com/astaxie/beego/logs" |
| 8 | 9 | ||
| 10 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/event/subscriber" | ||
| 9 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/factory" | 11 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/factory" |
| 10 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/orderinfo/command" | 12 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/orderinfo/command" |
| 11 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/orderinfo/query" | 13 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/orderinfo/query" |
| 12 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | 14 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" |
| 15 | + domainService "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain/service" | ||
| 13 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/dao" | 16 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/dao" |
| 17 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/models" | ||
| 18 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | ||
| 14 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/lib" | 19 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/lib" |
| 15 | ) | 20 | ) |
| 16 | 21 | ||
| 17 | -//OrderService 管理员相关服务 | 22 | +//OrderService 自建订单,意向单,实发订单 |
| 18 | type OrderInfoService struct { | 23 | type OrderInfoService struct { |
| 19 | } | 24 | } |
| 20 | 25 | ||
| @@ -151,6 +156,7 @@ func (service OrderInfoService) GetOrderDetail(getOrderQuery query.GetOrderQuery | @@ -151,6 +156,7 @@ func (service OrderInfoService) GetOrderDetail(getOrderQuery query.GetOrderQuery | ||
| 151 | return order, nil | 156 | return order, nil |
| 152 | } | 157 | } |
| 153 | 158 | ||
| 159 | +//CreateNewOrder 创建订单 | ||
| 154 | func (service OrderInfoService) CreateNewOrder(cmd command.CreateOrderCommand) (*domain.OrderBase, error) { | 160 | func (service OrderInfoService) CreateNewOrder(cmd command.CreateOrderCommand) (*domain.OrderBase, error) { |
| 155 | var ( | 161 | var ( |
| 156 | transactionContext, _ = factory.CreateTransactionContext(nil) | 162 | transactionContext, _ = factory.CreateTransactionContext(nil) |
| @@ -436,10 +442,12 @@ func (service OrderInfoService) UpdateOrderData(cmd command.UpdateOrderCommand) | @@ -436,10 +442,12 @@ func (service OrderInfoService) UpdateOrderData(cmd command.UpdateOrderCommand) | ||
| 436 | oldOrderData.Goods = newOrderGoods | 442 | oldOrderData.Goods = newOrderGoods |
| 437 | //删不需要的订单总不需要的商品 | 443 | //删不需要的订单总不需要的商品 |
| 438 | delGoods = service.deleteOldOrderGoods(newOrderGoods, oldOrderGoods) | 444 | delGoods = service.deleteOldOrderGoods(newOrderGoods, oldOrderGoods) |
| 445 | + if len(delGoods) > 0 { | ||
| 439 | err = orderGoodRepository.Remove(oldOrderData.Id, cmd.CompanyId, delGoods...) | 446 | err = orderGoodRepository.Remove(oldOrderData.Id, cmd.CompanyId, delGoods...) |
| 440 | if err != nil { | 447 | if err != nil { |
| 441 | return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, fmt.Sprintf("删除订单中的商品数据失败:%s", err)) | 448 | return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, fmt.Sprintf("删除订单中的商品数据失败:%s", err)) |
| 442 | } | 449 | } |
| 450 | + } | ||
| 443 | err = transactionContext.CommitTransaction() | 451 | err = transactionContext.CommitTransaction() |
| 444 | if err != nil { | 452 | if err != nil { |
| 445 | return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | 453 | return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) |
| @@ -612,7 +620,7 @@ func (service OrderInfoService) DisableOrEnable(cmd command.DisableOrderCommand) | @@ -612,7 +620,7 @@ func (service OrderInfoService) DisableOrEnable(cmd command.DisableOrderCommand) | ||
| 612 | return nil | 620 | return nil |
| 613 | } | 621 | } |
| 614 | 622 | ||
| 615 | -//UpdateGoodBouns 更新货品的分红相关的数值 | 623 | +//UpdateGoodBouns 分红时,更新货品的分红相关的数值 |
| 616 | func (service OrderInfoService) UpdateGoodBouns(cmd command.UpdateGoodBouns) error { | 624 | func (service OrderInfoService) UpdateGoodBouns(cmd command.UpdateGoodBouns) error { |
| 617 | var ( | 625 | var ( |
| 618 | transactionContext, _ = factory.CreateTransactionContext(nil) | 626 | transactionContext, _ = factory.CreateTransactionContext(nil) |
| @@ -687,7 +695,7 @@ func (service OrderInfoService) UpdateGoodBouns(cmd command.UpdateGoodBouns) err | @@ -687,7 +695,7 @@ func (service OrderInfoService) UpdateGoodBouns(cmd command.UpdateGoodBouns) err | ||
| 687 | } | 695 | } |
| 688 | } | 696 | } |
| 689 | oldOrderData.Goods = oldOrderGoods | 697 | oldOrderData.Goods = oldOrderGoods |
| 690 | - //变更订单类型 | 698 | + |
| 691 | err = oldOrderData.Compute() | 699 | err = oldOrderData.Compute() |
| 692 | if err != nil { | 700 | if err != nil { |
| 693 | return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, fmt.Sprintf("核算订单中合计的数值失败:%s", err)) | 701 | return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, fmt.Sprintf("核算订单中合计的数值失败:%s", err)) |
| @@ -707,3 +715,466 @@ func (service OrderInfoService) UpdateGoodBouns(cmd command.UpdateGoodBouns) err | @@ -707,3 +715,466 @@ func (service OrderInfoService) UpdateGoodBouns(cmd command.UpdateGoodBouns) err | ||
| 707 | return nil | 715 | return nil |
| 708 | 716 | ||
| 709 | } | 717 | } |
| 718 | + | ||
| 719 | +//PageListOrderBouns 获取订单的分红列表 | ||
| 720 | +func (service OrderInfoService) PageListOrderBonus(listOrderQuery query.ListOrderBonusQuery) ([]map[string]interface{}, int, error) { | ||
| 721 | + transactionContext, err := factory.CreateTransactionContext(nil) | ||
| 722 | + if err != nil { | ||
| 723 | + return nil, 0, lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 724 | + } | ||
| 725 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 726 | + return nil, 0, err | ||
| 727 | + } | ||
| 728 | + defer func() { | ||
| 729 | + transactionContext.RollbackTransaction() | ||
| 730 | + }() | ||
| 731 | + var ( | ||
| 732 | + ordersM []models.OrderBase | ||
| 733 | + orders []domain.OrderBase | ||
| 734 | + cnt int | ||
| 735 | + orderBaseDao *dao.OrderBaseDao | ||
| 736 | + ) | ||
| 737 | + | ||
| 738 | + if orderBaseDao, err = factory.CreateOrderBaseDao(map[string]interface{}{ | ||
| 739 | + "transactionContext": transactionContext, | ||
| 740 | + }); err != nil { | ||
| 741 | + return nil, cnt, lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 742 | + } | ||
| 743 | + ordersM, cnt, err = orderBaseDao.OrderBonusListByCondition( | ||
| 744 | + listOrderQuery.CompanyId, | ||
| 745 | + listOrderQuery.OrderType, | ||
| 746 | + listOrderQuery.PartnerOrCode, | ||
| 747 | + listOrderQuery.Limit, | ||
| 748 | + listOrderQuery.Offset, | ||
| 749 | + ) | ||
| 750 | + for _, orderModel := range ordersM { | ||
| 751 | + order := domain.OrderBase{ | ||
| 752 | + Id: orderModel.Id, OrderType: orderModel.OrderType, OrderCode: orderModel.OrderCode, | ||
| 753 | + DeliveryCode: orderModel.DeliveryCode, Buyer: orderModel.Buyer, RegionInfo: orderModel.RegionInfo, | ||
| 754 | + PartnerId: orderModel.PartnerId, SalesmanBonusPercent: orderModel.SalesmanBonusPercent, | ||
| 755 | + CreateTime: orderModel.CreateTime, DeliveryTime: orderModel.DeliveryTime, UpdateTime: orderModel.UpdateTime, | ||
| 756 | + IsDisable: orderModel.IsDisable, | ||
| 757 | + OrderCompute: domain.OrderCompute{ | ||
| 758 | + PlanPartnerBonus: orderModel.PlanPartnerBonus, UsePartnerBonus: orderModel.UsePartnerBonus, | ||
| 759 | + PartnerBonusHas: orderModel.PartnerBonusHas, PartnerBonusNot: orderModel.PartnerBonusNot, | ||
| 760 | + PartnerBonusExpense: orderModel.PartnerBonusExpense, SalesmanBonus: orderModel.SalesmanBonus, | ||
| 761 | + PlanOrderCount: orderModel.PlanOrderCount, PlanOrderAmount: orderModel.PlanOrderAmount, | ||
| 762 | + UseOrderCount: orderModel.UseOrderCount, UseOrderAmount: orderModel.UseOrderAmount, | ||
| 763 | + }, | ||
| 764 | + PartnerInfo: domain.Partner{ | ||
| 765 | + Id: orderModel.PartnerId, | ||
| 766 | + }, | ||
| 767 | + BonusStatus: orderModel.BonusStatus, | ||
| 768 | + CompanyId: orderModel.CompanyId, | ||
| 769 | + } | ||
| 770 | + orders = append(orders, order) | ||
| 771 | + } | ||
| 772 | + var ( | ||
| 773 | + PartnerInfoRepository domain.PartnerInfoRepository | ||
| 774 | + orderGoodRepository domain.OrderGoodRepository | ||
| 775 | + ) | ||
| 776 | + if PartnerInfoRepository, err = factory.CreatePartnerInfoRepository(map[string]interface{}{ | ||
| 777 | + "transactionContext": transactionContext, | ||
| 778 | + }); err != nil { | ||
| 779 | + return nil, 0, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 780 | + } | ||
| 781 | + if orderGoodRepository, err = factory.CreateOrderGoodRepository(map[string]interface{}{ | ||
| 782 | + "transactionContext": transactionContext, | ||
| 783 | + }); err != nil { | ||
| 784 | + return nil, 0, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 785 | + } | ||
| 786 | + var resp = []map[string]interface{}{} | ||
| 787 | + for i := range orders { | ||
| 788 | + partnerData := &domain.PartnerInfo{} | ||
| 789 | + partnerData, err = PartnerInfoRepository.FindOne(domain.PartnerFindOneQuery{ | ||
| 790 | + UserId: orders[i].PartnerId, | ||
| 791 | + }) | ||
| 792 | + if err != nil { | ||
| 793 | + logs.Error("获取合伙(id=%d)失败%s", orders[i].PartnerId, err) | ||
| 794 | + } else { | ||
| 795 | + orders[i].PartnerInfo = partnerData.Partner | ||
| 796 | + } | ||
| 797 | + var ( | ||
| 798 | + goods []domain.OrderGood | ||
| 799 | + hasBonusPercent bool | ||
| 800 | + ) | ||
| 801 | + goods, _, err = orderGoodRepository.Find(domain.OrderGoodFindQuery{OrderId: orders[i].Id}) | ||
| 802 | + for ii := range goods { | ||
| 803 | + if goods[ii].PartnerBonusPercent > 0 { | ||
| 804 | + hasBonusPercent = true | ||
| 805 | + } | ||
| 806 | + } | ||
| 807 | + listItem := map[string]interface{}{ | ||
| 808 | + "updateTime": orders[i].UpdateTime.Local().Format("2006-01-02 15:04:05"), | ||
| 809 | + "id": orders[i].Id, | ||
| 810 | + "shipmentsId": orders[i].DeliveryCode, | ||
| 811 | + "partner": orders[i].PartnerInfo.PartnerName, | ||
| 812 | + "dividendsReceivable": fmt.Sprint(orders[i].GetCurrentPartnerBonus()), | ||
| 813 | + "dividendSpending": fmt.Sprint(orders[i].OrderCompute.PartnerBonusExpense), | ||
| 814 | + "receiveDividends": fmt.Sprint(orders[i].OrderCompute.PartnerBonusHas), | ||
| 815 | + "uncollectedDividends": fmt.Sprint(orders[i].OrderCompute.PartnerBonusNot), | ||
| 816 | + "stateOfPayment": orders[i].BonusStatus, | ||
| 817 | + "orderType": orders[i].OrderType, | ||
| 818 | + "orderTypeName": domain.GetOrderBaseTypeName(orders[i].OrderType), | ||
| 819 | + "orderNumber": orders[i].OrderCode, | ||
| 820 | + } | ||
| 821 | + if !hasBonusPercent { | ||
| 822 | + listItem["receiveDividends"] = "-" | ||
| 823 | + listItem["dividendsReceivable"] = "-" | ||
| 824 | + listItem["dividendSpending"] = "-" | ||
| 825 | + listItem["uncollectedDividends"] = "-" | ||
| 826 | + } | ||
| 827 | + resp = append(resp, listItem) | ||
| 828 | + } | ||
| 829 | + err = transactionContext.CommitTransaction() | ||
| 830 | + if err != nil { | ||
| 831 | + return resp, cnt, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 832 | + } | ||
| 833 | + return resp, cnt, nil | ||
| 834 | +} | ||
| 835 | + | ||
| 836 | +//GetOrderBestshopInfo 获取来源于xiangmi订单的详情以及分红数据 | ||
| 837 | +func (service OrderInfoService) GetOrderBestshopInfoWithBonus(orderBaseId int64, companyId int64) (interface{}, error) { | ||
| 838 | + var ( | ||
| 839 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 840 | + err error | ||
| 841 | + ) | ||
| 842 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 843 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 844 | + } | ||
| 845 | + defer func() { | ||
| 846 | + transactionContext.RollbackTransaction() | ||
| 847 | + }() | ||
| 848 | + var ( | ||
| 849 | + orderBaseRepository domain.OrderBaseRepository | ||
| 850 | + orderGoodRepository domain.OrderGoodRepository | ||
| 851 | + orderBestshopRepository domain.OrderBestshopRepository | ||
| 852 | + orderGoodBestshopRepository domain.OrderGoodBestshopRepository | ||
| 853 | + orderLogRepository domain.OrderLogRepository | ||
| 854 | + partnerRepository domain.PartnerInfoRepository | ||
| 855 | + ) | ||
| 856 | + if orderBaseRepository, err = factory.CreateOrderBaseRepository(map[string]interface{}{ | ||
| 857 | + "transactionContext": transactionContext, | ||
| 858 | + }); err != nil { | ||
| 859 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 860 | + } | ||
| 861 | + if orderGoodRepository, err = factory.CreateOrderGoodRepository(map[string]interface{}{ | ||
| 862 | + "transactionContext": transactionContext, | ||
| 863 | + }); err != nil { | ||
| 864 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 865 | + } | ||
| 866 | + if orderBestshopRepository, err = factory.CreateOrderBestshopRepository(map[string]interface{}{ | ||
| 867 | + "transactionContext": transactionContext, | ||
| 868 | + }); err != nil { | ||
| 869 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 870 | + } | ||
| 871 | + if orderGoodBestshopRepository, err = factory.CreateOrderGoodBestshopRepository(map[string]interface{}{ | ||
| 872 | + "transactionContext": transactionContext, | ||
| 873 | + }); err != nil { | ||
| 874 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 875 | + } | ||
| 876 | + if orderLogRepository, err = factory.CreateOrderLogRepository(map[string]interface{}{ | ||
| 877 | + "transactionContext": transactionContext, | ||
| 878 | + }); err != nil { | ||
| 879 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 880 | + } | ||
| 881 | + if partnerRepository, err = factory.CreatePartnerInfoRepository(map[string]interface{}{ | ||
| 882 | + "transactionContext": transactionContext, | ||
| 883 | + }); err != nil { | ||
| 884 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 885 | + } | ||
| 886 | + var ( | ||
| 887 | + orderData *domain.OrderBase | ||
| 888 | + orderGoods []domain.OrderGood | ||
| 889 | + orderBestshopData *domain.OrderBestShop | ||
| 890 | + orderGoodBestshop []domain.OrderGoodBestShop | ||
| 891 | + orderLogs []domain.OrderLog | ||
| 892 | + partnerInfo *domain.PartnerInfo | ||
| 893 | + ) | ||
| 894 | + | ||
| 895 | + orderData, err = orderBaseRepository.FindOne(domain.OrderBaseFindOneQuery{ | ||
| 896 | + OrderId: orderBaseId, | ||
| 897 | + CompanyId: companyId, | ||
| 898 | + }) | ||
| 899 | + if err != nil { | ||
| 900 | + e := fmt.Sprintf("获取订单(order_base)数据失败,id=%d,company_id=%d,err=%s", orderBaseId, companyId, err) | ||
| 901 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 902 | + } | ||
| 903 | + if orderData.OrderType != domain.OrderTypeBestShop { | ||
| 904 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "获取的订单数据失败,OrderType err") | ||
| 905 | + } | ||
| 906 | + orderGoods, _, err = orderGoodRepository.Find(domain.OrderGoodFindQuery{OrderId: orderData.Id}) | ||
| 907 | + if err != nil { | ||
| 908 | + e := fmt.Sprintf("获取订单的商品(order_good)数据失败,order_id=%d,err=%s", orderData.Id, err) | ||
| 909 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 910 | + } | ||
| 911 | + orderData.Goods = orderGoods | ||
| 912 | + partnerInfo, err = partnerRepository.FindOne(domain.PartnerFindOneQuery{UserId: orderData.PartnerId}) | ||
| 913 | + if err != nil { | ||
| 914 | + e := fmt.Sprintf("获取订单中的合伙人(partner)数据失败,id=%d,order_id=%d,err=%s", orderData.PartnerId, orderData.Id, err) | ||
| 915 | + logs.Error(e) | ||
| 916 | + } | ||
| 917 | + orderData.PartnerInfo = partnerInfo.Partner | ||
| 918 | + orderBestshopData, err = orderBestshopRepository.FindOne(domain.OrderBestshopFindOneQuery{OrderId: orderData.DataFrom.DataId}) | ||
| 919 | + if err != nil { | ||
| 920 | + e := fmt.Sprintf("获取xiangmi订单(order_bestshop)数据失败,id=%d,err=%s", orderData.DataFrom.DataId, err) | ||
| 921 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 922 | + } | ||
| 923 | + orderGoodBestshop, err = orderGoodBestshopRepository.Find(domain.OrderGoodBestshopFindQuery{OrderId: orderBestshopData.Id}) | ||
| 924 | + if err != nil { | ||
| 925 | + e := fmt.Sprintf("获取xiangmi订单货品(order_good_bestshop)数据失败,order_id=%d,err=%s", orderBestshopData.Id, err) | ||
| 926 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 927 | + } | ||
| 928 | + orderBestshopData.Goods = orderGoodBestshop | ||
| 929 | + orderLogs, err = orderLogRepository.Find(domain.OrderLogFindQuery{OrderId: orderData.Id}) | ||
| 930 | + if err != nil { | ||
| 931 | + e := fmt.Sprintf("获取订单的修改记录(order_log)失败,err=%s", err) | ||
| 932 | + logs.Error(e) | ||
| 933 | + } | ||
| 934 | + err = transactionContext.CommitTransaction() | ||
| 935 | + if err != nil { | ||
| 936 | + return nil, lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 937 | + } | ||
| 938 | + result := service.buildOrderBestshopInfoData(orderData, orderBestshopData, orderLogs) | ||
| 939 | + return result, nil | ||
| 940 | +} | ||
| 941 | + | ||
| 942 | +//BuildOrderBestshopInfoData 构建前端需要的数据结构 | ||
| 943 | +func (service OrderInfoService) buildOrderBestshopInfoData(orderBase *domain.OrderBase, | ||
| 944 | + orderBestshop *domain.OrderBestShop, orderLogs []domain.OrderLog) interface{} { | ||
| 945 | + orderGoodBestshopMap := map[int64]*domain.OrderGoodBestShop{} | ||
| 946 | + for i := range orderBestshop.Goods { | ||
| 947 | + goodid := orderBestshop.Goods[i].Id | ||
| 948 | + orderGoodBestshopMap[goodid] = &orderBestshop.Goods[i] | ||
| 949 | + } | ||
| 950 | + //订单中的商品 | ||
| 951 | + productDetail := []map[string]interface{}{} | ||
| 952 | + var hasPartnerBonusPercent bool | ||
| 953 | + for i := range orderBase.Goods { | ||
| 954 | + detail := map[string]interface{}{ | ||
| 955 | + "commodityName": orderBase.Goods[i].GoodName, | ||
| 956 | + "productCodes": "", | ||
| 957 | + "commodityCode": "", | ||
| 958 | + "univalence": orderBase.Goods[i].Price, | ||
| 959 | + "orderNum": orderBase.Goods[i].GetCurrentGoodNumber(), | ||
| 960 | + "commodityPrice": orderBase.Goods[i].GetCurrentAmount(), | ||
| 961 | + "partnerDividends": "", | ||
| 962 | + "productId": orderBase.Goods[i].Id, | ||
| 963 | + "paymentStatus": orderBase.Goods[i].BonusStatus, | ||
| 964 | + "partnerRatio": orderBase.Goods[i].PartnerBonusPercent, | ||
| 965 | + } | ||
| 966 | + if orderBase.Goods[i].PartnerBonusPercent >= 0 { | ||
| 967 | + hasPartnerBonusPercent = true | ||
| 968 | + detail["partnerDividends"] = fmt.Sprint(orderBase.Goods[i].GetCurrentPartnerBonus()) | ||
| 969 | + } | ||
| 970 | + goodBestshopId := orderBase.Goods[i].DataFrom.DataId | ||
| 971 | + if v, ok := orderGoodBestshopMap[goodBestshopId]; ok { | ||
| 972 | + detail["productCodes"] = v.Sn | ||
| 973 | + detail["commodityCode"] = v.Bn | ||
| 974 | + } | ||
| 975 | + productDetail = append(productDetail, detail) | ||
| 976 | + } | ||
| 977 | + product := map[string]interface{}{ | ||
| 978 | + "orderNumCount": orderBase.GetCurrentOrderCount(), | ||
| 979 | + "partnerDividendsCount": "", | ||
| 980 | + "orderAmountAdjustmentCount": orderBase.GetCurrentOrderAmount(), | ||
| 981 | + "detail": productDetail, | ||
| 982 | + } | ||
| 983 | + if hasPartnerBonusPercent { | ||
| 984 | + product["partnerDividendsCount"] = fmt.Sprint(orderBase.GetCurrentPartnerBonus()) | ||
| 985 | + } | ||
| 986 | + //订单描述 | ||
| 987 | + order := map[string]interface{}{ | ||
| 988 | + "orderId": orderBase.Id, | ||
| 989 | + "orderState": orderBestshop.OrderState, | ||
| 990 | + "customers": orderBestshop.BuyerName, | ||
| 991 | + "address": orderBestshop.BuyerAddress, | ||
| 992 | + "remarks": orderBestshop.BuyerRemark, | ||
| 993 | + "partner": orderBase.PartnerInfo.PartnerName, | ||
| 994 | + "phone": orderBestshop.BuyerPhone, | ||
| 995 | + "orderTime": orderBestshop.OrderTime, | ||
| 996 | + "shippingStatus": orderBestshop.DeliveryState, | ||
| 997 | + "partnerDividends": "", | ||
| 998 | + "receivedDividends": "", | ||
| 999 | + "notReceivedDividend": "", | ||
| 1000 | + "dividendSpending": "", | ||
| 1001 | + "orderNumber": orderBase.OrderCode, | ||
| 1002 | + } | ||
| 1003 | + if hasPartnerBonusPercent { | ||
| 1004 | + order["partnerDividends"] = fmt.Sprint(orderBase.GetCurrentPartnerBonus()) | ||
| 1005 | + order["receivedDividends"] = fmt.Sprint(orderBase.OrderCompute.PartnerBonusHas) | ||
| 1006 | + order["notReceivedDividend"] = fmt.Sprint(orderBase.OrderCompute.PartnerBonusNot) | ||
| 1007 | + order["dividendSpending"] = fmt.Sprint(orderBase.OrderCompute.PartnerBonusExpense) | ||
| 1008 | + } | ||
| 1009 | + modifyLog := []map[string]interface{}{} | ||
| 1010 | + for i := range orderLogs { | ||
| 1011 | + m := map[string]interface{}{ | ||
| 1012 | + "title": orderLogs[i].LogAction, | ||
| 1013 | + "time": orderLogs[i].AlterTime.Local().Format("2006-01-02 15:04:05"), | ||
| 1014 | + "userName": orderLogs[i].Operator, | ||
| 1015 | + "id": orderLogs[i].Id, | ||
| 1016 | + } | ||
| 1017 | + detail := []map[string]string{} | ||
| 1018 | + for ii, vv := range orderLogs[i].Descript { | ||
| 1019 | + d := map[string]string{ | ||
| 1020 | + "updateTitle": vv.Title, | ||
| 1021 | + "id": fmt.Sprint(ii), | ||
| 1022 | + "content": vv.Item, | ||
| 1023 | + } | ||
| 1024 | + if len(vv.Action) > 0 { | ||
| 1025 | + d["content"] = vv.Item + ":" + strings.Join(vv.Action, ";") | ||
| 1026 | + } | ||
| 1027 | + detail = append(detail, d) | ||
| 1028 | + } | ||
| 1029 | + m["updateList"] = detail | ||
| 1030 | + modifyLog = append(modifyLog, m) | ||
| 1031 | + } | ||
| 1032 | + | ||
| 1033 | + result := map[string]interface{}{ | ||
| 1034 | + "order": order, | ||
| 1035 | + "product": product, | ||
| 1036 | + "modify": modifyLog, | ||
| 1037 | + "remark": orderBase.Remark.RemarkBonus, | ||
| 1038 | + } | ||
| 1039 | + return result | ||
| 1040 | +} | ||
| 1041 | + | ||
| 1042 | +//UpdateBounsWithGoodNumber 分红时,因修改订单中商品的数量发生分红变动 | ||
| 1043 | +func (service OrderInfoService) UpdateBonusByGoodNumber(orderId int64, goodId int64, adminId int64, goodNumber int, reason string) error { | ||
| 1044 | + var ( | ||
| 1045 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 1046 | + err error | ||
| 1047 | + ) | ||
| 1048 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 1049 | + return lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 1050 | + } | ||
| 1051 | + defer func() { | ||
| 1052 | + transactionContext.RollbackTransaction() | ||
| 1053 | + }() | ||
| 1054 | + var ( | ||
| 1055 | + orderBonuSrv domainService.OrderBonusService | ||
| 1056 | + ) | ||
| 1057 | + orderBonuSrv, err = factory.CreateOrderBonusService(map[string]interface{}{ | ||
| 1058 | + "transactionContext": transactionContext, | ||
| 1059 | + }) | ||
| 1060 | + if err != nil { | ||
| 1061 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1062 | + } | ||
| 1063 | + orderBonuSrv.Subscribe(&subscriber.OrderLogSubscriber{ | ||
| 1064 | + TransactionContext: transactionContext.(*transaction.TransactionContext), | ||
| 1065 | + }) | ||
| 1066 | + err = orderBonuSrv.UpdateBounsByGoodNumber(orderId, adminId, goodId, goodNumber, reason) | ||
| 1067 | + if err != nil { | ||
| 1068 | + return err | ||
| 1069 | + } | ||
| 1070 | + err = transactionContext.CommitTransaction() | ||
| 1071 | + if err != nil { | ||
| 1072 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1073 | + } | ||
| 1074 | + return nil | ||
| 1075 | +} | ||
| 1076 | + | ||
| 1077 | +//UpdateBounsByPartnerBonusPercent 分红时,因修改订单中商品的合伙人分行比例发生分红变动 | ||
| 1078 | +func (service OrderInfoService) UpdateBonusByPartnerBonusPercent(orderId int64, goodId int64, adminId int64, percent float64, reason string) error { | ||
| 1079 | + var ( | ||
| 1080 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 1081 | + err error | ||
| 1082 | + ) | ||
| 1083 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 1084 | + return lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 1085 | + } | ||
| 1086 | + defer func() { | ||
| 1087 | + transactionContext.RollbackTransaction() | ||
| 1088 | + }() | ||
| 1089 | + var ( | ||
| 1090 | + orderBonuSrv domainService.OrderBonusService | ||
| 1091 | + ) | ||
| 1092 | + orderBonuSrv, err = factory.CreateOrderBonusService(map[string]interface{}{ | ||
| 1093 | + "transactionContext": transactionContext, | ||
| 1094 | + }) | ||
| 1095 | + if err != nil { | ||
| 1096 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1097 | + } | ||
| 1098 | + orderBonuSrv.Subscribe(&subscriber.OrderLogSubscriber{ | ||
| 1099 | + TransactionContext: transactionContext.(*transaction.TransactionContext), | ||
| 1100 | + }) | ||
| 1101 | + err = orderBonuSrv.UpdateBounsByPartnerBonusPercent(orderId, adminId, goodId, percent, reason) | ||
| 1102 | + if err != nil { | ||
| 1103 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1104 | + } | ||
| 1105 | + err = transactionContext.CommitTransaction() | ||
| 1106 | + if err != nil { | ||
| 1107 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1108 | + } | ||
| 1109 | + return nil | ||
| 1110 | +} | ||
| 1111 | + | ||
| 1112 | +//PayPartnerBonusWithOrderBestshop 支付分红,海鲜干货的订单 (orderType=domain.OrderTypeBestShop) | ||
| 1113 | +func (service OrderInfoService) PayPartnerBonusWithOrderBestshop(orderId int64, goodId int64, adminId int64) error { | ||
| 1114 | + var ( | ||
| 1115 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 1116 | + err error | ||
| 1117 | + ) | ||
| 1118 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 1119 | + return lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 1120 | + } | ||
| 1121 | + defer func() { | ||
| 1122 | + transactionContext.RollbackTransaction() | ||
| 1123 | + }() | ||
| 1124 | + var ( | ||
| 1125 | + orderBonuSrv domainService.OrderBonusService | ||
| 1126 | + ) | ||
| 1127 | + orderBonuSrv, err = factory.CreateOrderBonusService(map[string]interface{}{ | ||
| 1128 | + "transactionContext": transactionContext, | ||
| 1129 | + }) | ||
| 1130 | + if err != nil { | ||
| 1131 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1132 | + } | ||
| 1133 | + orderBonuSrv.Subscribe(&subscriber.OrderLogSubscriber{ | ||
| 1134 | + TransactionContext: transactionContext.(*transaction.TransactionContext), | ||
| 1135 | + }) | ||
| 1136 | + err = orderBonuSrv.PayOrderGoodBonus(orderId, goodId, adminId) | ||
| 1137 | + if err != nil { | ||
| 1138 | + return err | ||
| 1139 | + } | ||
| 1140 | + err = transactionContext.CommitTransaction() | ||
| 1141 | + if err != nil { | ||
| 1142 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1143 | + } | ||
| 1144 | + return nil | ||
| 1145 | +} | ||
| 1146 | + | ||
| 1147 | +//PayPartnerBonusWithOrderBestshop 支付分红,海鲜干货的订单 (orderType=domain.OrderTypeBestShop) | ||
| 1148 | +func (service OrderInfoService) UpdateOrderRemarkBonus(orderId int64, adminId int64, remark string) error { | ||
| 1149 | + var ( | ||
| 1150 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 1151 | + err error | ||
| 1152 | + ) | ||
| 1153 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 1154 | + return lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 1155 | + } | ||
| 1156 | + defer func() { | ||
| 1157 | + transactionContext.RollbackTransaction() | ||
| 1158 | + }() | ||
| 1159 | + var ( | ||
| 1160 | + orderBonuSrv domainService.OrderBonusService | ||
| 1161 | + ) | ||
| 1162 | + orderBonuSrv, err = factory.CreateOrderBonusService(map[string]interface{}{ | ||
| 1163 | + "transactionContext": transactionContext, | ||
| 1164 | + }) | ||
| 1165 | + if err != nil { | ||
| 1166 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1167 | + } | ||
| 1168 | + orderBonuSrv.Subscribe(&subscriber.OrderLogSubscriber{ | ||
| 1169 | + TransactionContext: transactionContext.(*transaction.TransactionContext), | ||
| 1170 | + }) | ||
| 1171 | + err = orderBonuSrv.UpdateOrderRemarkBonus(orderId, adminId, remark) | ||
| 1172 | + if err != nil { | ||
| 1173 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1174 | + } | ||
| 1175 | + err = transactionContext.CommitTransaction() | ||
| 1176 | + if err != nil { | ||
| 1177 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 1178 | + } | ||
| 1179 | + return nil | ||
| 1180 | +} |
| @@ -44,16 +44,16 @@ func (command CreatePartnerInfoCommand) ValidateCommand() error { | @@ -44,16 +44,16 @@ func (command CreatePartnerInfoCommand) ValidateCommand() error { | ||
| 44 | if command.RegionInfo == nil { | 44 | if command.RegionInfo == nil { |
| 45 | return lib.ThrowError(lib.ARG_ERROR, "区域必填") | 45 | return lib.ThrowError(lib.ARG_ERROR, "区域必填") |
| 46 | } | 46 | } |
| 47 | - if len(command.Salesman) == 0 { | ||
| 48 | - return lib.ThrowError(lib.ARG_ERROR, "关联业务员必填") | ||
| 49 | - } | ||
| 50 | - for i := range command.Salesman { | ||
| 51 | - if len(command.Salesman[i].Name) == 0 { | ||
| 52 | - return lib.ThrowError(lib.ARG_ERROR, "关联业务员名称必填") | ||
| 53 | - } | ||
| 54 | - if len(command.Salesman[i].Telephone) == 0 { | ||
| 55 | - return lib.ThrowError(lib.ARG_ERROR, "关联业务员电话必填") | ||
| 56 | - } | ||
| 57 | - } | 47 | + // if len(command.Salesman) == 0 { |
| 48 | + // return lib.ThrowError(lib.ARG_ERROR, "关联业务员必填") | ||
| 49 | + // } | ||
| 50 | + // for i := range command.Salesman { | ||
| 51 | + // if len(command.Salesman[i].Name) == 0 { | ||
| 52 | + // return lib.ThrowError(lib.ARG_ERROR, "关联业务员名称必填") | ||
| 53 | + // } | ||
| 54 | + // if len(command.Salesman[i].Telephone) == 0 { | ||
| 55 | + // return lib.ThrowError(lib.ARG_ERROR, "关联业务员电话必填") | ||
| 56 | + // } | ||
| 57 | + // } | ||
| 58 | return nil | 58 | return nil |
| 59 | } | 59 | } |
| @@ -31,19 +31,20 @@ func (command *UpdatePartnerInfoCommand) ValidateCommand() error { | @@ -31,19 +31,20 @@ func (command *UpdatePartnerInfoCommand) ValidateCommand() error { | ||
| 31 | if command.RegionInfo == nil { | 31 | if command.RegionInfo == nil { |
| 32 | return lib.ThrowError(lib.ARG_ERROR, "区域必填") | 32 | return lib.ThrowError(lib.ARG_ERROR, "区域必填") |
| 33 | } | 33 | } |
| 34 | - if len(command.Salesman) == 0 { | ||
| 35 | - return lib.ThrowError(lib.ARG_ERROR, "关联业务员必填") | ||
| 36 | - } | 34 | + |
| 37 | if command.Id == 0 { | 35 | if command.Id == 0 { |
| 38 | return lib.ThrowError(lib.ARG_ERROR, "合伙人id错误") | 36 | return lib.ThrowError(lib.ARG_ERROR, "合伙人id错误") |
| 39 | } | 37 | } |
| 40 | - for i := range command.Salesman { | ||
| 41 | - if len(command.Salesman[i].Name) == 0 { | ||
| 42 | - return lib.ThrowError(lib.ARG_ERROR, "关联业务员名称必填") | ||
| 43 | - } | ||
| 44 | - if len(command.Salesman[i].Telephone) == 0 { | ||
| 45 | - return lib.ThrowError(lib.ARG_ERROR, "关联业务员电话必填") | ||
| 46 | - } | ||
| 47 | - } | 38 | + // if len(command.Salesman) == 0 { |
| 39 | + // return lib.ThrowError(lib.ARG_ERROR, "关联业务员必填") | ||
| 40 | + // } | ||
| 41 | + // for i := range command.Salesman { | ||
| 42 | + // if len(command.Salesman[i].Name) == 0 { | ||
| 43 | + // return lib.ThrowError(lib.ARG_ERROR, "关联业务员名称必填") | ||
| 44 | + // } | ||
| 45 | + // if len(command.Salesman[i].Telephone) == 0 { | ||
| 46 | + // return lib.ThrowError(lib.ARG_ERROR, "关联业务员电话必填") | ||
| 47 | + // } | ||
| 48 | + // } | ||
| 48 | return nil | 49 | return nil |
| 49 | } | 50 | } |
| @@ -222,6 +222,7 @@ func (PartnerInfoService *PartnerInfoService) UpdatePartnerInfo(cmd *command.Upd | @@ -222,6 +222,7 @@ func (PartnerInfoService *PartnerInfoService) UpdatePartnerInfo(cmd *command.Upd | ||
| 222 | }); err != nil { | 222 | }); err != nil { |
| 223 | return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | 223 | return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) |
| 224 | } | 224 | } |
| 225 | + //TODO 修改为本地消息订阅 | ||
| 225 | err = businessBonusSrv.EnableOrDisable(partnerInfo.Partner.Id) | 226 | err = businessBonusSrv.EnableOrDisable(partnerInfo.Partner.Id) |
| 226 | if err != nil { | 227 | if err != nil { |
| 227 | e := fmt.Sprintf("更新业务分红(partner_id=%d)数据失败:%s", partnerInfo.Partner.Id, err) | 228 | e := fmt.Sprintf("更新业务分红(partner_id=%d)数据失败:%s", partnerInfo.Partner.Id, err) |
| 1 | +package command | ||
| 2 | + | ||
| 3 | +//接收海鲜干货的订单 | ||
| 4 | +type CreateOrderFromBestshop struct { | ||
| 5 | + //订单编号 | ||
| 6 | + OrderCode string `json:"orderCode"` | ||
| 7 | + //下单时间 | ||
| 8 | + OrderTime string `json:"orderTime"` | ||
| 9 | + //公司id | ||
| 10 | + CompanyId int64 `json:"companyId"` | ||
| 11 | + //订单状态 | ||
| 12 | + OrderState int8 `json:"orderState"` | ||
| 13 | + //发货状态 | ||
| 14 | + DeliveryState int8 `json:"deliveryState"` | ||
| 15 | + //买家名称 | ||
| 16 | + BuyerName string `json:"buyerName"` | ||
| 17 | + BuyerId int64 `json:"buyerId"` | ||
| 18 | + //买家电话 | ||
| 19 | + BuyerPhone string `json:"buyerPhone"` | ||
| 20 | + //买家地址 | ||
| 21 | + BuyerAddress string `json:"buyerAddress"` | ||
| 22 | + //买家备注 | ||
| 23 | + BuyerRemark string `json:"buyerRemark"` | ||
| 24 | + //商品总数 | ||
| 25 | + OrderCount int `json:"orderCount"` | ||
| 26 | + //d订单总额 | ||
| 27 | + OrderAmount float64 `json:"orderAmount"` | ||
| 28 | + //发货时间 | ||
| 29 | + DeliveryTime string `json:"deliveryTime"` | ||
| 30 | + PartnerId int64 `json:"partnerId"` | ||
| 31 | + Goods []struct { | ||
| 32 | + Id int64 `json:"id"` | ||
| 33 | + //货品编号 | ||
| 34 | + Sn string `json:"sn"` | ||
| 35 | + //商品编号 | ||
| 36 | + Bn string `json:"bn"` | ||
| 37 | + //货品名称 | ||
| 38 | + Name string `json:"name"` | ||
| 39 | + //单价 | ||
| 40 | + Price float64 `json:"price"` | ||
| 41 | + //货品数量 | ||
| 42 | + Nums int `json:"nums"` | ||
| 43 | + //订单总价 | ||
| 44 | + Amount float64 `json:"amount"` | ||
| 45 | + } `json:"goods"` | ||
| 46 | +} |
| 1 | +package service | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "fmt" | ||
| 5 | + "time" | ||
| 6 | + | ||
| 7 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/dao" | ||
| 8 | + | ||
| 9 | + "github.com/astaxie/beego/logs" | ||
| 10 | + | ||
| 11 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/factory" | ||
| 12 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/syncOrder/command" | ||
| 13 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 14 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/lib" | ||
| 15 | +) | ||
| 16 | + | ||
| 17 | +//从其他系统接收订单数据 | ||
| 18 | +const ( | ||
| 19 | + BEST_SHOP_UNIONID string = "gh_18eb644002fb" //海鲜干货小程序原始id | ||
| 20 | +) | ||
| 21 | + | ||
| 22 | +type SyncOrderService struct { | ||
| 23 | +} | ||
| 24 | + | ||
| 25 | +func NewOrderInfoService(option map[string]interface{}) *SyncOrderService { | ||
| 26 | + newService := new(SyncOrderService) | ||
| 27 | + return newService | ||
| 28 | +} | ||
| 29 | + | ||
| 30 | +//SyncOrderFromBestshop 接收来源于xiangmi小程序的订单数据 | ||
| 31 | +func (s SyncOrderService) SyncOrderFromBestshop(cmd command.CreateOrderFromBestshop) error { | ||
| 32 | + var ( | ||
| 33 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 34 | + err error | ||
| 35 | + ) | ||
| 36 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 37 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 38 | + } | ||
| 39 | + defer func() { | ||
| 40 | + transactionContext.RollbackTransaction() | ||
| 41 | + }() | ||
| 42 | + | ||
| 43 | + //检查账号是否存在 | ||
| 44 | + var ( | ||
| 45 | + orderBestshopDao *dao.OrderBestshopDao | ||
| 46 | + orderExist bool | ||
| 47 | + partnerRepository domain.PartnerInfoRepository | ||
| 48 | + partnerData *domain.PartnerInfo | ||
| 49 | + ) | ||
| 50 | + if orderBestshopDao, err = factory.CreateOrderBestshopDao(map[string]interface{}{ | ||
| 51 | + "transactionContext": transactionContext, | ||
| 52 | + }); err != nil { | ||
| 53 | + return lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 54 | + } | ||
| 55 | + orderExist, err = orderBestshopDao.OrderExist(cmd.OrderCode) | ||
| 56 | + if err != nil { | ||
| 57 | + return lib.ThrowError(lib.TRANSACTION_ERROR, "orderBestshopDao.OrderExist err:"+err.Error()) | ||
| 58 | + } | ||
| 59 | + //数据检查 | ||
| 60 | + if partnerRepository, err = factory.CreatePartnerInfoRepository(map[string]interface{}{ | ||
| 61 | + "transactionContext": transactionContext, | ||
| 62 | + }); err != nil { | ||
| 63 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 64 | + } | ||
| 65 | + partnerData, err = partnerRepository.FindOne(domain.PartnerFindOneQuery{UserId: cmd.PartnerId}) | ||
| 66 | + if err != nil { | ||
| 67 | + e := fmt.Sprintf("未找到指定的合伙人(id=%d)数据,%s", cmd.PartnerId, err) | ||
| 68 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 69 | + } | ||
| 70 | + if partnerData.CompanyId != cmd.CompanyId { | ||
| 71 | + e := fmt.Sprintf("合伙人(partnerId)的公司(companyId=%d)和传递的参数中的companyId 不一致", partnerData.CompanyId) | ||
| 72 | + logs.Warning(e) | ||
| 73 | + } | ||
| 74 | + err = transactionContext.CommitTransaction() | ||
| 75 | + if err != nil { | ||
| 76 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 77 | + } | ||
| 78 | + if orderExist { | ||
| 79 | + // | ||
| 80 | + logs.Warning("订单数据已存在:order_code=%s", cmd.OrderCode) | ||
| 81 | + } else { | ||
| 82 | + err = s.CreateOrderFromBestshop(cmd) | ||
| 83 | + } | ||
| 84 | + return err | ||
| 85 | +} | ||
| 86 | + | ||
| 87 | +func (s SyncOrderService) CreateOrderFromBestshop(cmd command.CreateOrderFromBestshop) error { | ||
| 88 | + var ( | ||
| 89 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 90 | + err error | ||
| 91 | + ) | ||
| 92 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 93 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 94 | + } | ||
| 95 | + defer func() { | ||
| 96 | + transactionContext.RollbackTransaction() | ||
| 97 | + }() | ||
| 98 | + var ( | ||
| 99 | + orderBestshopRepository domain.OrderBestshopRepository | ||
| 100 | + orderGoodBestshopRepository domain.OrderGoodBestshopRepository | ||
| 101 | + ) | ||
| 102 | + if orderBestshopRepository, err = factory.CreateOrderBestshopRepository(map[string]interface{}{ | ||
| 103 | + "transactionContext": transactionContext, | ||
| 104 | + }); err != nil { | ||
| 105 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 106 | + } | ||
| 107 | + if orderGoodBestshopRepository, err = factory.CreateOrderGoodBestshopRepository(map[string]interface{}{ | ||
| 108 | + "transactionContext": transactionContext, | ||
| 109 | + }); err != nil { | ||
| 110 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 111 | + } | ||
| 112 | + order := domain.OrderBestShop{ | ||
| 113 | + OrderCode: cmd.OrderCode, | ||
| 114 | + OrderTime: cmd.OrderTime, | ||
| 115 | + OrderState: cmd.OrderState, | ||
| 116 | + OrderCount: cmd.OrderCount, | ||
| 117 | + OrderAmount: cmd.OrderAmount, | ||
| 118 | + CreateTime: time.Now(), | ||
| 119 | + PartnerId: cmd.PartnerId, | ||
| 120 | + BuyerName: cmd.BuyerName, | ||
| 121 | + BuyerPhone: cmd.BuyerPhone, | ||
| 122 | + BuyerAddress: cmd.BuyerAddress, | ||
| 123 | + BuyerRemark: cmd.BuyerRemark, | ||
| 124 | + BuyerId: cmd.BuyerId, | ||
| 125 | + DeliveryState: cmd.DeliveryState, | ||
| 126 | + DeliveryTime: cmd.DeliveryTime, | ||
| 127 | + IsCopy: false, | ||
| 128 | + CompanyId: cmd.CompanyId, | ||
| 129 | + } | ||
| 130 | + err = orderBestshopRepository.Add(&order) | ||
| 131 | + if err != nil { | ||
| 132 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "添加order_bestshop失败:"+err.Error()) | ||
| 133 | + } | ||
| 134 | + goods := []domain.OrderGoodBestShop{} | ||
| 135 | + for i := range cmd.Goods { | ||
| 136 | + good := domain.OrderGoodBestShop{ | ||
| 137 | + Id: cmd.Goods[i].Id, | ||
| 138 | + OrderId: order.Id, | ||
| 139 | + Sn: cmd.Goods[i].Sn, | ||
| 140 | + Bn: cmd.Goods[i].Bn, | ||
| 141 | + Name: cmd.Goods[i].Name, | ||
| 142 | + Price: cmd.Goods[i].Price, | ||
| 143 | + Nums: cmd.Goods[i].Nums, | ||
| 144 | + Amount: cmd.Goods[i].Amount, | ||
| 145 | + } | ||
| 146 | + err = orderGoodBestshopRepository.Add(&good) | ||
| 147 | + if err != nil { | ||
| 148 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "添加order_good失败:"+err.Error()) | ||
| 149 | + } | ||
| 150 | + goods = append(goods, good) | ||
| 151 | + } | ||
| 152 | + order.Goods = goods | ||
| 153 | + err = transactionContext.CommitTransaction() | ||
| 154 | + if err != nil { | ||
| 155 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 156 | + } | ||
| 157 | + if cmd.PartnerId <= 0 { | ||
| 158 | + logs.Info("[SyncOrderFromBestshop] PartnerId<=0 ,不复制订单数据") | ||
| 159 | + return nil | ||
| 160 | + } | ||
| 161 | + err = s.copyOrderBestshopToOrderBase(&order) | ||
| 162 | + return err | ||
| 163 | +} | ||
| 164 | + | ||
| 165 | +//copyOrderBestshopToOrderBase 复制数据 | ||
| 166 | +func (s SyncOrderService) copyOrderBestshopToOrderBase(orderBestshop *domain.OrderBestShop) error { | ||
| 167 | + var ( | ||
| 168 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 169 | + err error | ||
| 170 | + ) | ||
| 171 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 172 | + return lib.ThrowError(lib.TRANSACTION_ERROR, err.Error()) | ||
| 173 | + } | ||
| 174 | + defer func() { | ||
| 175 | + transactionContext.RollbackTransaction() | ||
| 176 | + }() | ||
| 177 | + var ( | ||
| 178 | + orderBaseRepository domain.OrderBaseRepository | ||
| 179 | + orderGoodRepository domain.OrderGoodRepository | ||
| 180 | + orderBestshopRepository domain.OrderBestshopRepository | ||
| 181 | + partnerRepository domain.PartnerInfoRepository | ||
| 182 | + companyRepository domain.CompanyRepository | ||
| 183 | + ) | ||
| 184 | + if orderBaseRepository, err = factory.CreateOrderBaseRepository(map[string]interface{}{ | ||
| 185 | + "transactionContext": transactionContext, | ||
| 186 | + }); err != nil { | ||
| 187 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 188 | + } | ||
| 189 | + if orderGoodRepository, err = factory.CreateOrderGoodRepository(map[string]interface{}{ | ||
| 190 | + "transactionContext": transactionContext, | ||
| 191 | + }); err != nil { | ||
| 192 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 193 | + } | ||
| 194 | + if partnerRepository, err = factory.CreatePartnerInfoRepository(map[string]interface{}{ | ||
| 195 | + "transactionContext": transactionContext, | ||
| 196 | + }); err != nil { | ||
| 197 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 198 | + } | ||
| 199 | + if companyRepository, err = factory.CreateCompanyRepository(map[string]interface{}{ | ||
| 200 | + "transactionContext": transactionContext, | ||
| 201 | + }); err != nil { | ||
| 202 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 203 | + } | ||
| 204 | + if orderBestshopRepository, err = factory.CreateOrderBestshopRepository(map[string]interface{}{ | ||
| 205 | + "transactionContext": transactionContext, | ||
| 206 | + }); err != nil { | ||
| 207 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 208 | + } | ||
| 209 | + var ( | ||
| 210 | + partnerData *domain.PartnerInfo | ||
| 211 | + companyData domain.Company | ||
| 212 | + canCopyOrder bool | ||
| 213 | + ) | ||
| 214 | + partnerData, err = partnerRepository.FindOne(domain.PartnerFindOneQuery{UserId: orderBestshop.PartnerId}) | ||
| 215 | + if err != nil { | ||
| 216 | + e := fmt.Sprintf("未找到指定的合伙人(id=%d)数据,%s", orderBestshop.PartnerId, err) | ||
| 217 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 218 | + } | ||
| 219 | + companyData, err = companyRepository.FindOne(domain.CompanyFindOneOptions{ | ||
| 220 | + Id: partnerData.CompanyId, | ||
| 221 | + }) | ||
| 222 | + if err != nil { | ||
| 223 | + e := fmt.Sprintf("未找到指定的合伙人的公司(partner_id=%d,company_id=%d)数据,%s", orderBestshop.PartnerId, partnerData.CompanyId, err) | ||
| 224 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 225 | + } | ||
| 226 | + for _, v := range companyData.Applets { | ||
| 227 | + if v.Id == BEST_SHOP_UNIONID { | ||
| 228 | + canCopyOrder = true | ||
| 229 | + } | ||
| 230 | + } | ||
| 231 | + if !canCopyOrder { | ||
| 232 | + logs.Warning("公司未设置xiangmi小程序原始id; order_bestshop.id=%d", orderBestshop.Id) | ||
| 233 | + return nil | ||
| 234 | + } | ||
| 235 | + var ( | ||
| 236 | + orderbase domain.OrderBase | ||
| 237 | + ordergoods []domain.OrderGood | ||
| 238 | + ) | ||
| 239 | + //TODO 添加orderBase | ||
| 240 | + orderBestshop.CopyToOrderBase(&orderbase) | ||
| 241 | + orderbase.CompanyId = companyData.Id | ||
| 242 | + for i := range orderBestshop.Goods { | ||
| 243 | + good := domain.NewOrderGood() | ||
| 244 | + orderBestshop.Goods[i].CopyToOrderGood(&good) | ||
| 245 | + good.CompanyId = partnerData.CompanyId | ||
| 246 | + good.Compute() | ||
| 247 | + good.CurrentBonusStatus.WartPayPartnerBonus(&good) | ||
| 248 | + ordergoods = append(ordergoods, good) | ||
| 249 | + } | ||
| 250 | + orderbase.Goods = ordergoods | ||
| 251 | + orderbase.PartnerId = partnerData.Partner.Id | ||
| 252 | + orderbase.CompanyId = partnerData.CompanyId | ||
| 253 | + orderbase.Compute() | ||
| 254 | + err = orderBaseRepository.Save(&orderbase) | ||
| 255 | + if err != nil { | ||
| 256 | + e := fmt.Sprintf("添加order_base数据失败%s", err) | ||
| 257 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 258 | + } | ||
| 259 | + for i := range ordergoods { | ||
| 260 | + ordergoods[i].OrderId = orderbase.Id | ||
| 261 | + } | ||
| 262 | + // 添加goods | ||
| 263 | + err = orderGoodRepository.Save(ordergoods) | ||
| 264 | + if err != nil { | ||
| 265 | + e := fmt.Sprintf("添加order_good数据失败%s", err) | ||
| 266 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 267 | + } | ||
| 268 | + // 更新isCopy | ||
| 269 | + orderBestshop.IsCopy = true | ||
| 270 | + err = orderBestshopRepository.Edit(orderBestshop) | ||
| 271 | + if err != nil { | ||
| 272 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 273 | + } | ||
| 274 | + err = transactionContext.CommitTransaction() | ||
| 275 | + if err != nil { | ||
| 276 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 277 | + } | ||
| 278 | + return nil | ||
| 279 | +} | ||
| 280 | + | ||
| 281 | +func (s SyncOrderService) UpdateOrderFromBestshop(cmd command.CreateOrderFromBestshop) error { | ||
| 282 | + var ( | ||
| 283 | + transactionContext, _ = factory.CreateTransactionContext(nil) | ||
| 284 | + err error | ||
| 285 | + ) | ||
| 286 | + if err = transactionContext.StartTransaction(); err != nil { | ||
| 287 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 288 | + } | ||
| 289 | + defer func() { | ||
| 290 | + transactionContext.RollbackTransaction() | ||
| 291 | + }() | ||
| 292 | + var ( | ||
| 293 | + orderBestshopRepository domain.OrderBestshopRepository | ||
| 294 | + orderGoodBestshopRepository domain.OrderGoodBestshopRepository | ||
| 295 | + ) | ||
| 296 | + if orderBestshopRepository, err = factory.CreateOrderBestshopRepository(map[string]interface{}{ | ||
| 297 | + "transactionContext": transactionContext, | ||
| 298 | + }); err != nil { | ||
| 299 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 300 | + } | ||
| 301 | + if orderGoodBestshopRepository, err = factory.CreateOrderGoodBestshopRepository(map[string]interface{}{ | ||
| 302 | + "transactionContext": transactionContext, | ||
| 303 | + }); err != nil { | ||
| 304 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 305 | + } | ||
| 306 | + var ( | ||
| 307 | + orderData *domain.OrderBestShop | ||
| 308 | + orderGoods []domain.OrderGoodBestShop | ||
| 309 | + ) | ||
| 310 | + orderData, err = orderBestshopRepository.FindOne(domain.OrderBestshopFindOneQuery{ | ||
| 311 | + OrderCode: cmd.OrderCode, | ||
| 312 | + }) | ||
| 313 | + if err != nil { | ||
| 314 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "获取orderBestshop(order_code=%s)数据失败,err=%s", cmd.OrderCode, err.Error()) | ||
| 315 | + } | ||
| 316 | + | ||
| 317 | + orderData.OrderCode = cmd.OrderCode | ||
| 318 | + orderData.OrderTime = cmd.OrderTime | ||
| 319 | + orderData.OrderState = cmd.OrderState | ||
| 320 | + orderData.OrderCount = cmd.OrderCount | ||
| 321 | + orderData.OrderAmount = cmd.OrderAmount | ||
| 322 | + orderData.PartnerId = cmd.PartnerId | ||
| 323 | + orderData.BuyerName = cmd.BuyerName | ||
| 324 | + orderData.BuyerPhone = cmd.BuyerPhone | ||
| 325 | + orderData.BuyerAddress = cmd.BuyerAddress | ||
| 326 | + orderData.BuyerRemark = cmd.BuyerRemark | ||
| 327 | + orderData.BuyerId = cmd.BuyerId | ||
| 328 | + orderData.DeliveryState = cmd.DeliveryState | ||
| 329 | + orderData.DeliveryTime = cmd.DeliveryTime | ||
| 330 | + orderData.CompanyId = cmd.CompanyId | ||
| 331 | + err = orderBestshopRepository.Edit(orderData) | ||
| 332 | + if err != nil { | ||
| 333 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "编辑order_bestshop失败:"+err.Error()) | ||
| 334 | + } | ||
| 335 | + orderGoods, err = orderGoodBestshopRepository.Find(domain.OrderGoodBestshopFindQuery{ | ||
| 336 | + OrderId: orderData.Id, | ||
| 337 | + }) | ||
| 338 | + if err != nil { | ||
| 339 | + e := fmt.Sprintf("获取orderGoodBestshop(order_id=%d)数据失败,err=%s", orderData.Id, err.Error()) | ||
| 340 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 341 | + } | ||
| 342 | + | ||
| 343 | + for i := range orderGoods { | ||
| 344 | + var updated bool | ||
| 345 | + for ii := range cmd.Goods { | ||
| 346 | + if cmd.Goods[ii].Id != orderGoods[i].Id { | ||
| 347 | + continue | ||
| 348 | + } | ||
| 349 | + orderGoods[i].Sn = cmd.Goods[ii].Sn | ||
| 350 | + orderGoods[i].Bn = cmd.Goods[ii].Bn | ||
| 351 | + orderGoods[i].Name = cmd.Goods[ii].Name | ||
| 352 | + orderGoods[i].Price = cmd.Goods[ii].Price | ||
| 353 | + orderGoods[i].Nums = cmd.Goods[ii].Nums | ||
| 354 | + orderGoods[i].Amount = cmd.Goods[ii].Amount | ||
| 355 | + updated = true | ||
| 356 | + } | ||
| 357 | + if updated { | ||
| 358 | + err = orderGoodBestshopRepository.Edit(&orderGoods[i]) | ||
| 359 | + if err != nil { | ||
| 360 | + logs.Error("更新order_good_bestshop失败:" + err.Error()) | ||
| 361 | + } | ||
| 362 | + } | ||
| 363 | + } | ||
| 364 | + err = transactionContext.CommitTransaction() | ||
| 365 | + if err != nil { | ||
| 366 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 367 | + } | ||
| 368 | + return nil | ||
| 369 | +} |
| @@ -16,6 +16,12 @@ type SyncCompanyService struct{} | @@ -16,6 +16,12 @@ type SyncCompanyService struct{} | ||
| 16 | 16 | ||
| 17 | var _ SyncAction = (*SyncCompanyService)(nil) | 17 | var _ SyncAction = (*SyncCompanyService)(nil) |
| 18 | 18 | ||
| 19 | +type CompanyBaseApplet struct { | ||
| 20 | + Name string `json:"name"` | ||
| 21 | + URL string `json:"url"` | ||
| 22 | + Id string `json:"id"` | ||
| 23 | +} | ||
| 24 | + | ||
| 19 | //企业平台的公司基础数据 | 25 | //企业平台的公司基础数据 |
| 20 | type CompanyBase struct { | 26 | type CompanyBase struct { |
| 21 | Id int64 `json:"id"` //id | 27 | Id int64 `json:"id"` //id |
| @@ -23,7 +29,8 @@ type CompanyBase struct { | @@ -23,7 +29,8 @@ type CompanyBase struct { | ||
| 23 | AdminCompanyId int `json:"admin_company_id"` //总后台的公司id | 29 | AdminCompanyId int `json:"admin_company_id"` //总后台的公司id |
| 24 | Logo string `json:"logo"` //公司图标 | 30 | Logo string `json:"logo"` //公司图标 |
| 25 | Remarks string `json:"remarks"` //备注 | 31 | Remarks string `json:"remarks"` //备注 |
| 26 | - Abbreviation string `json:"abbreviation"` | 32 | + Abbreviation string `json:"abbreviation"` //公司简称 |
| 33 | + Applets []CompanyBaseApplet `json:"applets"` //公司对接的小程序 | ||
| 27 | } | 34 | } |
| 28 | 35 | ||
| 29 | // CompanytData 企业平台发送过来的公司数据数据 | 36 | // CompanytData 企业平台发送过来的公司数据数据 |
| @@ -104,6 +111,15 @@ func (service SyncCompanyService) addCompany(data CompanytData) error { | @@ -104,6 +111,15 @@ func (service SyncCompanyService) addCompany(data CompanytData) error { | ||
| 104 | }); err != nil { | 111 | }); err != nil { |
| 105 | return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | 112 | return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) |
| 106 | } | 113 | } |
| 114 | + applets := []domain.CompanyApplets{} | ||
| 115 | + for _, v := range data.Company.Applets { | ||
| 116 | + app := domain.CompanyApplets{ | ||
| 117 | + Name: v.Name, | ||
| 118 | + URL: v.URL, | ||
| 119 | + Id: v.Id, | ||
| 120 | + } | ||
| 121 | + applets = append(applets, app) | ||
| 122 | + } | ||
| 107 | comany := domain.Company{ | 123 | comany := domain.Company{ |
| 108 | Id: data.Company.Id, | 124 | Id: data.Company.Id, |
| 109 | Name: data.Company.Name, | 125 | Name: data.Company.Name, |
| @@ -114,7 +130,9 @@ func (service SyncCompanyService) addCompany(data CompanytData) error { | @@ -114,7 +130,9 @@ func (service SyncCompanyService) addCompany(data CompanytData) error { | ||
| 114 | //Status: data.Company.Status, | 130 | //Status: data.Company.Status, |
| 115 | Enable: domain.CompanyEnableYes, //默认初始化值 | 131 | Enable: domain.CompanyEnableYes, //默认初始化值 |
| 116 | Abbreviation: data.Company.Abbreviation, | 132 | Abbreviation: data.Company.Abbreviation, |
| 133 | + Applets: applets, | ||
| 117 | } | 134 | } |
| 135 | + | ||
| 118 | err = companyRespository.Add(&comany) | 136 | err = companyRespository.Add(&comany) |
| 119 | if err != nil { | 137 | if err != nil { |
| 120 | return fmt.Errorf("添加公司数据失败,%s", err) | 138 | return fmt.Errorf("添加公司数据失败,%s", err) |
| @@ -186,12 +204,22 @@ func (service SyncCompanyService) updateCompany(data CompanytData) error { | @@ -186,12 +204,22 @@ func (service SyncCompanyService) updateCompany(data CompanytData) error { | ||
| 186 | newUser, err = userRespository.FindOne(domain.UsersFindOneQuery{ | 204 | newUser, err = userRespository.FindOne(domain.UsersFindOneQuery{ |
| 187 | Id: data.User.Id, | 205 | Id: data.User.Id, |
| 188 | }) | 206 | }) |
| 207 | + applets := []domain.CompanyApplets{} | ||
| 208 | + for _, v := range data.Company.Applets { | ||
| 209 | + app := domain.CompanyApplets{ | ||
| 210 | + Name: v.Name, | ||
| 211 | + URL: v.URL, | ||
| 212 | + Id: v.Id, | ||
| 213 | + } | ||
| 214 | + applets = append(applets, app) | ||
| 215 | + } | ||
| 189 | oldCompany.Update(map[string]interface{}{ | 216 | oldCompany.Update(map[string]interface{}{ |
| 190 | "Name": data.Company.Name, | 217 | "Name": data.Company.Name, |
| 191 | "Logo": data.Company.Logo, | 218 | "Logo": data.Company.Logo, |
| 192 | "Remarks": data.Company.Remarks, | 219 | "Remarks": data.Company.Remarks, |
| 193 | "AdminCompanyId": data.Company.AdminCompanyId, | 220 | "AdminCompanyId": data.Company.AdminCompanyId, |
| 194 | "Abbreviation": data.Company.Abbreviation, | 221 | "Abbreviation": data.Company.Abbreviation, |
| 222 | + "Applets": applets, | ||
| 195 | }) | 223 | }) |
| 196 | for i := range oldCompanyAdmins { | 224 | for i := range oldCompanyAdmins { |
| 197 | oldCompanyAdmins[i].Update(map[string]interface{}{ | 225 | oldCompanyAdmins[i].Update(map[string]interface{}{ |
pkg/constant/kafka.go
0 → 100644
| 1 | +package constant | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "os" | ||
| 5 | + "strings" | ||
| 6 | +) | ||
| 7 | + | ||
| 8 | +type KafkaConfig struct { | ||
| 9 | + Servers []string `json:"servers"` | ||
| 10 | + ConsumerId string `json:"consumerGroup"` | ||
| 11 | +} | ||
| 12 | + | ||
| 13 | +var KafkaCfg KafkaConfig | ||
| 14 | + | ||
| 15 | +func init() { | ||
| 16 | + KafkaCfg = KafkaConfig{ | ||
| 17 | + Servers: []string{"192.168.190.136:9092"}, | ||
| 18 | + ConsumerId: "partnermg_local", | ||
| 19 | + } | ||
| 20 | + if os.Getenv("KAFKA_HOST") != "" { | ||
| 21 | + kafkaHost := os.Getenv("KAFKA_HOST") | ||
| 22 | + KafkaCfg.Servers = strings.Split(kafkaHost, ";") | ||
| 23 | + } | ||
| 24 | + if os.Getenv("KAFKA_CONSUMER_ID") != "" { | ||
| 25 | + consumerId := os.Getenv("KAFKA_CONSUMER_ID") | ||
| 26 | + KafkaCfg.ConsumerId = consumerId | ||
| 27 | + } | ||
| 28 | +} | ||
| 29 | + | ||
| 30 | +// "192.168.190.136:9092", | ||
| 31 | +// "106.52.15.41:9092" |
| @@ -17,6 +17,12 @@ const ( | @@ -17,6 +17,12 @@ const ( | ||
| 17 | CompanyEnableNo int8 = 2 | 17 | CompanyEnableNo int8 = 2 |
| 18 | ) | 18 | ) |
| 19 | 19 | ||
| 20 | +type CompanyApplets struct { | ||
| 21 | + Name string `json:"name"` | ||
| 22 | + URL string `json:"url"` | ||
| 23 | + Id string `json:"id"` | ||
| 24 | +} | ||
| 25 | + | ||
| 20 | // 公司信息 | 26 | // 公司信息 |
| 21 | type Company struct { | 27 | type Company struct { |
| 22 | // 唯一标识 | 28 | // 唯一标识 |
| @@ -41,12 +47,9 @@ type Company struct { | @@ -41,12 +47,9 @@ type Company struct { | ||
| 41 | UpdateAt time.Time `json:"updateAt"` | 47 | UpdateAt time.Time `json:"updateAt"` |
| 42 | // 删除时间 | 48 | // 删除时间 |
| 43 | DeleteAt time.Time `json:"deleteAt"` | 49 | DeleteAt time.Time `json:"deleteAt"` |
| 50 | + Applets []CompanyApplets `json:"applets"` | ||
| 44 | } | 51 | } |
| 45 | 52 | ||
| 46 | -// func (c Company) StatusIsOk() bool { | ||
| 47 | -// return c.Status == companyStatusUsable | ||
| 48 | -// } | ||
| 49 | - | ||
| 50 | func (c Company) EnableIsOk() bool { | 53 | func (c Company) EnableIsOk() bool { |
| 51 | return c.Enable == CompanyEnableYes | 54 | return c.Enable == CompanyEnableYes |
| 52 | } | 55 | } |
| @@ -76,6 +79,9 @@ func (c *Company) Update(m map[string]interface{}) error { | @@ -76,6 +79,9 @@ func (c *Company) Update(m map[string]interface{}) error { | ||
| 76 | if v, ok := m["Abbreviation"]; ok { | 79 | if v, ok := m["Abbreviation"]; ok { |
| 77 | c.Abbreviation = v.(string) | 80 | c.Abbreviation = v.(string) |
| 78 | } | 81 | } |
| 82 | + if v, ok := m["Applets"]; ok { | ||
| 83 | + c.Applets = v.([]CompanyApplets) | ||
| 84 | + } | ||
| 79 | return nil | 85 | return nil |
| 80 | } | 86 | } |
| 81 | 87 |
pkg/domain/event/modifyOrderGoodBonus.go
0 → 100644
| 1 | +package event | ||
| 2 | + | ||
| 3 | +const ( | ||
| 4 | + //订单分红因为货品的数量变动而发送改变 | ||
| 5 | + UPDATE_BONUS_BY_GOOD_NUMBER_EVENT string = "UpdateBonusByGoodNumber" | ||
| 6 | + //订单分红因为合伙人分红比例变动而发送改变 | ||
| 7 | + UPDATE_BONUS_BY_PARTENT_BONUS_PERCENT_EVENT string = "UpdateBounsByPartnerBonusPercent" | ||
| 8 | + //更新订单的备注 | ||
| 9 | + UPDATE_ORDER_REMARK string = "UpdateOrderRemark" | ||
| 10 | +) | ||
| 11 | + | ||
| 12 | +//UpdateBonusByGoodNumber | ||
| 13 | +//订单分红因为货品的数量变动而发送改变 | ||
| 14 | +type UpdateBonusByGoodNumber struct { | ||
| 15 | + //订单id | ||
| 16 | + OrderId int64 | ||
| 17 | + //管理员id | ||
| 18 | + AdminId int64 | ||
| 19 | + //货品id | ||
| 20 | + GoodId int64 | ||
| 21 | + //货品名称 | ||
| 22 | + GoodName string | ||
| 23 | + //旧的货品数量 | ||
| 24 | + FormerNumber string | ||
| 25 | + //新的货品数量 | ||
| 26 | + NewNumber string | ||
| 27 | + //旧的货品总额 | ||
| 28 | + FormerAmount string | ||
| 29 | + //新的货品总额 | ||
| 30 | + NewAmount string | ||
| 31 | +} | ||
| 32 | + | ||
| 33 | +//EventType 事件名称 | ||
| 34 | +func (m UpdateBonusByGoodNumber) EventType() string { | ||
| 35 | + return UPDATE_BONUS_BY_GOOD_NUMBER_EVENT | ||
| 36 | +} | ||
| 37 | + | ||
| 38 | +//UpdateBounsByPartnerBonusPercent | ||
| 39 | +//订单分红因为合伙人分红比例变动而发送改变 | ||
| 40 | +type UpdateBounsByPartnerBonusPercent struct { | ||
| 41 | + //订单id | ||
| 42 | + OrderId int64 | ||
| 43 | + //管理员id | ||
| 44 | + AdminId int64 | ||
| 45 | + //货品id | ||
| 46 | + GoodId int64 | ||
| 47 | + //货品名称 | ||
| 48 | + GoodName string | ||
| 49 | + //旧的合伙人分红比例 | ||
| 50 | + FormerPartnerBonusPercent string | ||
| 51 | + //新的合伙人分红比例 | ||
| 52 | + NewPartnerBonusPercent string | ||
| 53 | + //旧的合伙人分红 | ||
| 54 | + FormerPartnerBonus string | ||
| 55 | + //新的合伙人分红 | ||
| 56 | + NewPartnerBonus string | ||
| 57 | +} | ||
| 58 | + | ||
| 59 | +//EventType 事件名称 | ||
| 60 | +func (m UpdateBounsByPartnerBonusPercent) EventType() string { | ||
| 61 | + return UPDATE_BONUS_BY_PARTENT_BONUS_PERCENT_EVENT | ||
| 62 | +} | ||
| 63 | + | ||
| 64 | +//UpdateOrderRemark 更新订单的备注 | ||
| 65 | +type UpdateOrderRemark struct { | ||
| 66 | + //订单id | ||
| 67 | + OrderId int64 | ||
| 68 | + //管理员id | ||
| 69 | + AdminId int64 | ||
| 70 | + //旧的备注 | ||
| 71 | + FormerRemark string | ||
| 72 | + //新的备注 | ||
| 73 | + NewRemark string | ||
| 74 | +} | ||
| 75 | + | ||
| 76 | +//EventType 事件名称 | ||
| 77 | +func (m UpdateOrderRemark) EventType() string { | ||
| 78 | + return UPDATE_ORDER_REMARK | ||
| 79 | +} |
pkg/domain/event/payOrderGoodBonus.go
0 → 100644
| 1 | +package event | ||
| 2 | + | ||
| 3 | +const ( | ||
| 4 | + //支付订单中货品的分红 | ||
| 5 | + PAY_ORDER_GOOD_BONUS_EVENT string = "PayOrderGoodBonus" | ||
| 6 | +) | ||
| 7 | + | ||
| 8 | +//PayOrderGoodBonus | ||
| 9 | +//事件:支付订单中货品的分红 | ||
| 10 | +type PayOrderGoodBonus struct { | ||
| 11 | + //订单id | ||
| 12 | + OrderId int64 | ||
| 13 | + //货品名称 | ||
| 14 | + GoodName string | ||
| 15 | + //订单中的货品id | ||
| 16 | + GoodId int64 | ||
| 17 | + //管理员id | ||
| 18 | + AdminId int64 | ||
| 19 | + // | ||
| 20 | + PartnerBonus float64 | ||
| 21 | +} | ||
| 22 | + | ||
| 23 | +func (p PayOrderGoodBonus) EventType() string { | ||
| 24 | + return PAY_ORDER_GOOD_BONUS_EVENT | ||
| 25 | +} |
| @@ -9,8 +9,22 @@ import ( | @@ -9,8 +9,22 @@ import ( | ||
| 9 | const ( | 9 | const ( |
| 10 | OrderReal = iota + 1 //实发订单 | 10 | OrderReal = iota + 1 //实发订单 |
| 11 | OrderIntention //意向订单 | 11 | OrderIntention //意向订单 |
| 12 | + OrderTypeBestShop //来自小程序海鲜干货的订单 | ||
| 12 | ) | 13 | ) |
| 13 | 14 | ||
| 15 | +func GetOrderBaseTypeName(orderType int) string { | ||
| 16 | + var name string | ||
| 17 | + switch orderType { | ||
| 18 | + case OrderReal: | ||
| 19 | + name = "自建订单" | ||
| 20 | + case OrderTypeBestShop: | ||
| 21 | + name = "小程序订单" | ||
| 22 | + case OrderIntention: | ||
| 23 | + name = "意向订单" | ||
| 24 | + } | ||
| 25 | + return name | ||
| 26 | +} | ||
| 27 | + | ||
| 14 | const ( | 28 | const ( |
| 15 | OrderDisableNot = iota //订单未关闭 | 29 | OrderDisableNot = iota //订单未关闭 |
| 16 | OrderDisableYes //订单已关闭 | 30 | OrderDisableYes //订单已关闭 |
| @@ -24,6 +38,41 @@ type Buyer struct { | @@ -24,6 +38,41 @@ type Buyer struct { | ||
| 24 | ContactInfo string `json:"contactInfo"` | 38 | ContactInfo string `json:"contactInfo"` |
| 25 | //收获地址 | 39 | //收获地址 |
| 26 | ShippingAddress string `json:"shippingAddress"` | 40 | ShippingAddress string `json:"shippingAddress"` |
| 41 | + //买家备注 | ||
| 42 | + Remark string `json:"remark"` | ||
| 43 | +} | ||
| 44 | + | ||
| 45 | +type OrderCompute struct { | ||
| 46 | + //合伙人应收分红 | ||
| 47 | + PlanPartnerBonus float64 `json:"planPartnerBonus"` | ||
| 48 | + //调整后的合伙人应收分红 (初始值=-1); | ||
| 49 | + //业务判定时0是有效值, | ||
| 50 | + //所以用空串表示无值,转换到数据库中为负值 | ||
| 51 | + UsePartnerBonus float64 `json:"usePartnerBonus"` | ||
| 52 | + //合伙人已收分红 | ||
| 53 | + PartnerBonusHas float64 `json:"partnerBonusHas"` | ||
| 54 | + //合伙人未收分红 | ||
| 55 | + PartnerBonusNot float64 `json:"partnerBonusNot"` | ||
| 56 | + //合伙人分红支出 | ||
| 57 | + PartnerBonusExpense float64 `json:"partnerBonusExpense"` | ||
| 58 | + //业务员抽成 | ||
| 59 | + SalesmanBonus float64 `json:"salesmanBonus"` | ||
| 60 | + //预计的订单内货品总数 | ||
| 61 | + PlanOrderCount int `json:"planOrderCount"` | ||
| 62 | + //预计的订单的总金额 | ||
| 63 | + PlanOrderAmount float64 `json:"planOrderAmount"` | ||
| 64 | + //按需使用的订单内货品总数 (初始值=-1) | ||
| 65 | + //业务判定时0是有效值, | ||
| 66 | + //所以用空串表示无值,转换到数据库中为负值 | ||
| 67 | + UseOrderCount int `json:"useOrderCount"` | ||
| 68 | + //按需使用的订单内货总金额 (初始值=-1) | ||
| 69 | + //业务判定时0是有效值, | ||
| 70 | + //所以用空串表示无值,转换到数据库中为负值 | ||
| 71 | + UseOrderAmount float64 `json:"useOrderAmount"` | ||
| 72 | +} | ||
| 73 | + | ||
| 74 | +type OrderBaseRemark struct { | ||
| 75 | + RemarkBonus string `json:"remarkBonus"` | ||
| 27 | } | 76 | } |
| 28 | 77 | ||
| 29 | //OrderBase 订单基础 | 78 | //OrderBase 订单基础 |
| @@ -61,35 +110,87 @@ type OrderBase struct { | @@ -61,35 +110,87 @@ type OrderBase struct { | ||
| 61 | BonusStatus int `json:"bonusStatus"` | 110 | BonusStatus int `json:"bonusStatus"` |
| 62 | //公司 | 111 | //公司 |
| 63 | CompanyId int64 `json:"companyId"` | 112 | CompanyId int64 `json:"companyId"` |
| 113 | + //数据来源 | ||
| 114 | + DataFrom OrderDataFrom `json:"dataFrom"` | ||
| 115 | + //备注 | ||
| 116 | + Remark OrderBaseRemark `json:"remark"` | ||
| 64 | } | 117 | } |
| 65 | 118 | ||
| 66 | -type OrderCompute struct { | ||
| 67 | - //合伙人应收分红 | ||
| 68 | - PlanPartnerBonus float64 `json:"planPartnerBonus"` | ||
| 69 | - //调整后的合伙人应收分红 (初始值=-1); | ||
| 70 | - //业务判定时0是有效值, | ||
| 71 | - //所以用空串表示无值,转换到数据库中为负值 | ||
| 72 | - UsePartnerBonus float64 `json:"usePartnerBonus"` | ||
| 73 | - //合伙人已收分红 | ||
| 74 | - PartnerBonusHas float64 `json:"partnerBonusHas"` | ||
| 75 | - //合伙人未收分红 | ||
| 76 | - PartnerBonusNot float64 `json:"partnerBonusNot"` | ||
| 77 | - //合伙人分红支出 | ||
| 78 | - PartnerBonusExpense float64 `json:"partnerBonusExpense"` | ||
| 79 | - //业务员抽成 | ||
| 80 | - SalesmanBonus float64 `json:"salesmanBonus"` | ||
| 81 | - //预计的订单内货品总数 | ||
| 82 | - PlanOrderCount int `json:"planOrderCount"` | ||
| 83 | - //预计的订单的总金额 | ||
| 84 | - PlanOrderAmount float64 `json:"planOrderAmount"` | ||
| 85 | - //按需使用的订单内货品总数 (初始值=-1) | ||
| 86 | - //业务判定时0是有效值, | ||
| 87 | - //所以用空串表示无值,转换到数据库中为负值 | ||
| 88 | - UseOrderCount int `json:"useOrderCount"` | ||
| 89 | - //按需使用的订单内货总金额 (初始值=-1) | ||
| 90 | - //业务判定时0是有效值, | ||
| 91 | - //所以用空串表示无值,转换到数据库中为负值 | ||
| 92 | - UseOrderAmount float64 `json:"useOrderAmount"` | 119 | +//GetCurrentPartnerBonus 获取当前合伙人应收分红 |
| 120 | +func (order *OrderBase) GetCurrentPartnerBonus() float64 { | ||
| 121 | + if order.OrderCompute.UsePartnerBonus >= 0 { | ||
| 122 | + return order.OrderCompute.UsePartnerBonus | ||
| 123 | + } | ||
| 124 | + return order.OrderCompute.PlanPartnerBonus | ||
| 125 | +} | ||
| 126 | + | ||
| 127 | +//GetCurrentOrderCount 获取当前订单商品总数 | ||
| 128 | +func (order *OrderBase) GetCurrentOrderCount() int { | ||
| 129 | + if order.OrderCompute.UseOrderCount >= 0 { | ||
| 130 | + return order.OrderCompute.UseOrderCount | ||
| 131 | + } | ||
| 132 | + return order.OrderCompute.PlanOrderCount | ||
| 133 | +} | ||
| 134 | + | ||
| 135 | +// GetCurrentOrderAmount 获取当前订单的总额 | ||
| 136 | +func (order *OrderBase) GetCurrentOrderAmount() float64 { | ||
| 137 | + if order.OrderCompute.UseOrderAmount >= 0 { | ||
| 138 | + return order.OrderCompute.UseOrderAmount | ||
| 139 | + } | ||
| 140 | + return order.OrderCompute.PlanOrderAmount | ||
| 141 | +} | ||
| 142 | + | ||
| 143 | +//Update 更新订单数据 | ||
| 144 | +//orderData 订单数据 | ||
| 145 | +//goodsMap 货品的数据,以货品的id做键,map[id]map[string]interface{} | ||
| 146 | +func (order *OrderBase) Update(orderData map[string]interface{}, goodsMap map[int64]map[string]interface{}) error { | ||
| 147 | + if v, ok := orderData["OrderCode"]; ok { | ||
| 148 | + order.OrderCode = v.(string) | ||
| 149 | + } | ||
| 150 | + if v, ok := orderData["DeliveryCode"]; ok { | ||
| 151 | + order.DeliveryCode = v.(string) | ||
| 152 | + } | ||
| 153 | + if v, ok := orderData["Buyer"]; ok { | ||
| 154 | + order.Buyer = v.(Buyer) | ||
| 155 | + } | ||
| 156 | + if v, ok := orderData["SalesmanBonusPercent"]; ok { | ||
| 157 | + order.SalesmanBonusPercent = v.(float64) | ||
| 158 | + } | ||
| 159 | + if v, ok := orderData["DeliveryTime"]; ok { | ||
| 160 | + order.DeliveryTime = v.(time.Time) | ||
| 161 | + } | ||
| 162 | + if v, ok := orderData["IsDisable"]; ok { | ||
| 163 | + order.IsDisable = v.(int) | ||
| 164 | + } | ||
| 165 | + for i := range order.Goods { | ||
| 166 | + goodId := order.Goods[i].Id | ||
| 167 | + if _, ok := goodsMap[goodId]; !ok { | ||
| 168 | + continue | ||
| 169 | + } | ||
| 170 | + if err := order.Goods[i].Update(goodsMap[goodId]); err != nil { | ||
| 171 | + return err | ||
| 172 | + } | ||
| 173 | + } | ||
| 174 | + err := order.Compute() | ||
| 175 | + return err | ||
| 176 | +} | ||
| 177 | + | ||
| 178 | +func (order *OrderBase) AddGoods(goods []OrderGood) { | ||
| 179 | + order.Goods = append(order.Goods, goods...) | ||
| 180 | + order.Compute() | ||
| 181 | +} | ||
| 182 | + | ||
| 183 | +func (order *OrderBase) DeleteGoods(goodIds []int64) { | ||
| 184 | + var newGoods []OrderGood | ||
| 185 | + for i := range order.Goods { | ||
| 186 | + for _, goodId := range goodIds { | ||
| 187 | + order.Goods[i].Id = goodId | ||
| 188 | + continue | ||
| 189 | + } | ||
| 190 | + newGoods = append(newGoods, order.Goods[i]) | ||
| 191 | + } | ||
| 192 | + order.Goods = newGoods | ||
| 193 | + order.Compute() | ||
| 93 | } | 194 | } |
| 94 | 195 | ||
| 95 | //Compute 数据汇总核算 | 196 | //Compute 数据汇总核算 |
pkg/domain/order_bestshop.go
0 → 100644
| 1 | +package domain | ||
| 2 | + | ||
| 3 | +import "time" | ||
| 4 | + | ||
| 5 | +//OrderBestShop 来源海鲜干货的订单 | ||
| 6 | +type OrderBestShop struct { | ||
| 7 | + Id int64 `json:"id"` | ||
| 8 | + //订单编号 | ||
| 9 | + OrderCode string `json:"orderCode"` | ||
| 10 | + //下单时间 | ||
| 11 | + OrderTime string `json:"orderTime"` | ||
| 12 | + //订单状态 | ||
| 13 | + OrderState int8 `json:"orderState"` | ||
| 14 | + //发货状态 | ||
| 15 | + DeliveryState int8 `json:"deliveryState"` | ||
| 16 | + //买家名称 | ||
| 17 | + BuyerName string `json:"buyerName"` | ||
| 18 | + //买家电话 | ||
| 19 | + BuyerPhone string `json:"buyerPhone"` | ||
| 20 | + //买家地址 | ||
| 21 | + BuyerAddress string `json:"buyerAddress"` | ||
| 22 | + //买家备注 | ||
| 23 | + BuyerRemark string `json:"buyerRemark"` | ||
| 24 | + // | ||
| 25 | + BuyerId int64 `json:"buyerId"` | ||
| 26 | + //商品总数 | ||
| 27 | + OrderCount int `json:"orderCount"` | ||
| 28 | + //d订单总额 | ||
| 29 | + OrderAmount float64 `json:"orderAmount"` | ||
| 30 | + //发货时间 | ||
| 31 | + DeliveryTime string `json:"deliveryTime"` | ||
| 32 | + //创建时间 | ||
| 33 | + CreateTime time.Time `json:"createTime"` | ||
| 34 | + PartnerId int64 `json:"partnerId"` | ||
| 35 | + Goods []OrderGoodBestShop `json:"goods"` | ||
| 36 | + //是否将数据同步到 order_base ,order_good | ||
| 37 | + IsCopy bool `json:"isCopy"` | ||
| 38 | + CompanyId int64 `json:"companyId"` | ||
| 39 | +} | ||
| 40 | + | ||
| 41 | +func (order OrderBestShop) CopyToOrderBase(o *OrderBase) { | ||
| 42 | + o.Buyer = Buyer{ | ||
| 43 | + BuyerName: order.BuyerName, | ||
| 44 | + ContactInfo: order.BuyerPhone, | ||
| 45 | + ShippingAddress: order.BuyerAddress, | ||
| 46 | + Remark: order.BuyerRemark, | ||
| 47 | + } | ||
| 48 | + o.DataFrom = OrderDataFrom{ | ||
| 49 | + Platform: OrderDataFromBestShop, | ||
| 50 | + DataId: order.Id, | ||
| 51 | + } | ||
| 52 | + o.OrderType = OrderTypeBestShop | ||
| 53 | + o.OrderCode = order.OrderCode | ||
| 54 | + o.OrderCompute.PlanOrderAmount = order.OrderAmount | ||
| 55 | + o.OrderCompute.PlanOrderCount = order.OrderCount | ||
| 56 | + o.DeliveryTime, _ = time.Parse("2006-01-02 15:04:05", order.DeliveryTime) | ||
| 57 | + return | ||
| 58 | +} | ||
| 59 | + | ||
| 60 | +type OrderBestshopFindOneQuery struct { | ||
| 61 | + OrderId int64 | ||
| 62 | + OrderCode string | ||
| 63 | +} | ||
| 64 | + | ||
| 65 | +type OrderBestshopRepository interface { | ||
| 66 | + Add(order *OrderBestShop) error | ||
| 67 | + Edit(order *OrderBestShop) error | ||
| 68 | + FindOne(qureyOptions OrderBestshopFindOneQuery) (*OrderBestShop, error) | ||
| 69 | +} | ||
| 70 | + | ||
| 71 | +//OrderGoodBestShop 订单明细 | ||
| 72 | +type OrderGoodBestShop struct { | ||
| 73 | + Id int64 `json:"id"` | ||
| 74 | + //订单id | ||
| 75 | + OrderId int64 `json:"orderId"` | ||
| 76 | + //货品编号 | ||
| 77 | + Sn string `json:"sn"` | ||
| 78 | + //商品编号 | ||
| 79 | + Bn string `json:"bn"` | ||
| 80 | + //货品名称 | ||
| 81 | + Name string `json:"name"` | ||
| 82 | + //单价 | ||
| 83 | + Price float64 `json:"price"` | ||
| 84 | + //货品数量 | ||
| 85 | + Nums int `json:"nums"` | ||
| 86 | + //订单总价 | ||
| 87 | + Amount float64 `json:"amount"` | ||
| 88 | +} | ||
| 89 | + | ||
| 90 | +func (good OrderGoodBestShop) CopyToOrderGood(g *OrderGood) { | ||
| 91 | + g.DataFrom = OrderDataFrom{ | ||
| 92 | + Platform: OrderDataFromBestShop, | ||
| 93 | + DataId: good.Id, | ||
| 94 | + } | ||
| 95 | + g.GoodName = good.Name | ||
| 96 | + g.Price = good.Price | ||
| 97 | + g.PlanGoodNumber = good.Nums | ||
| 98 | + g.GoodCompute.PlanAmount = good.Amount | ||
| 99 | + g.BonusStatus = OrderGoodWaitPay | ||
| 100 | + g.CurrentBonusStatus = OrderGoodBonusWaitPay{} | ||
| 101 | + | ||
| 102 | + return | ||
| 103 | +} | ||
| 104 | + | ||
| 105 | +type OrderGoodBestshopFindQuery struct { | ||
| 106 | + OrderId int64 | ||
| 107 | +} | ||
| 108 | + | ||
| 109 | +type OrderGoodBestshopRepository interface { | ||
| 110 | + Add(order *OrderGoodBestShop) error | ||
| 111 | + Edit(good *OrderGoodBestShop) error | ||
| 112 | + Find(qureyOptions OrderGoodBestshopFindQuery) ([]OrderGoodBestShop, error) | ||
| 113 | +} |
pkg/domain/order_data_from.go
0 → 100644
| @@ -22,6 +22,32 @@ const ( | @@ -22,6 +22,32 @@ const ( | ||
| 22 | OrderGoodHasPay int = 2 | 22 | OrderGoodHasPay int = 2 |
| 23 | ) | 23 | ) |
| 24 | 24 | ||
| 25 | +//GoodCompute 货品中计算值 | ||
| 26 | +type GoodCompute struct { | ||
| 27 | + //预计的货品总额 | ||
| 28 | + PlanAmount float64 `json:"planAmount"` | ||
| 29 | + //调整后的货品总额 (初始值=-1) | ||
| 30 | + //业务判定时0是有效值, | ||
| 31 | + //所以用空串表示无值,转换到数据库中为负值 | ||
| 32 | + UseAmount float64 `json:"useAmount"` | ||
| 33 | + //预计的合伙人分红 | ||
| 34 | + PlanPartnerBonus float64 `json:"planPartnerBonus"` | ||
| 35 | + //合伙人应收分红调整 (初始值=-1), | ||
| 36 | + //业务判定时0是有效值, | ||
| 37 | + //所以用空串表示无值,转换到数据库中为负值 | ||
| 38 | + UsePartnerBonus float64 `json:"usePartnerBonus"` | ||
| 39 | + //合伙人已收分红 | ||
| 40 | + PartnerBonusHas float64 `json:"partnerBonusHas"` | ||
| 41 | + //合伙人未收分红 | ||
| 42 | + PartnerBonusNot float64 `json:"partnerBonusNot"` | ||
| 43 | + //合伙人分红支出 | ||
| 44 | + PartnerBonusExpense float64 `json:"partnerBonusExpense"` | ||
| 45 | +} | ||
| 46 | +type OrderGoodRemarkReason struct { | ||
| 47 | + ModifyGoodNumber string `json:"modifyGoodNumber"` //货品数量变更的理由 | ||
| 48 | + ModifyPartnerBonusPercent string `json:"modifyPartnerBonusPercent"` //合伙人分红比例变更的理由 | ||
| 49 | +} | ||
| 50 | + | ||
| 25 | //OrderGood 订单中的货品 | 51 | //OrderGood 订单中的货品 |
| 26 | type OrderGood struct { | 52 | type OrderGood struct { |
| 27 | //货品id | 53 | //货品id |
| @@ -49,28 +75,61 @@ type OrderGood struct { | @@ -49,28 +75,61 @@ type OrderGood struct { | ||
| 49 | ///核算订单相关数据 | 75 | ///核算订单相关数据 |
| 50 | GoodCompute GoodCompute `json:"goodCompute"` | 76 | GoodCompute GoodCompute `json:"goodCompute"` |
| 51 | //公司 | 77 | //公司 |
| 52 | - CompanyId int64 | 78 | + CompanyId int64 `json:"companyId"` |
| 79 | + //原因备注 | ||
| 80 | + RemarkReason OrderGoodRemarkReason `json:"remarkReason"` | ||
| 81 | + DataFrom OrderDataFrom `json:"data_from"` | ||
| 53 | } | 82 | } |
| 54 | 83 | ||
| 55 | -type GoodCompute struct { | ||
| 56 | - //预计的货品总额 | ||
| 57 | - PlanAmount float64 `json:"planAmount"` | ||
| 58 | - //调整后的货品总额 (初始值=-1) | ||
| 59 | - //业务判定时0是有效值, | ||
| 60 | - //所以用空串表示无值,转换到数据库中为负值 | ||
| 61 | - UseAmount float64 `json:"useAmount"` | ||
| 62 | - //预计的合伙人分红 | ||
| 63 | - PlanPartnerBonus float64 `json:"planPartnerBonus"` | ||
| 64 | - //合伙人应收分红调整 (初始值=-1), | ||
| 65 | - //业务判定时0是有效值, | ||
| 66 | - //所以用空串表示无值,转换到数据库中为负值 | ||
| 67 | - UsePartnerBonus float64 `json:"usePartnerBonus"` | ||
| 68 | - //合伙人已收分红 | ||
| 69 | - PartnerBonusHas float64 `json:"partnerBonusHas"` | ||
| 70 | - //合伙人未收分红 | ||
| 71 | - PartnerBonusNot float64 `json:"partnerBonusNot"` | ||
| 72 | - //合伙人分红支出 | ||
| 73 | - PartnerBonusExpense float64 `json:"partnerBonusExpense"` | 84 | +//GetCurrentGoodNumber 获取当前的商品数量 |
| 85 | +func (good OrderGood) GetCurrentGoodNumber() int { | ||
| 86 | + if good.UseGoodNumber >= 0 { | ||
| 87 | + return good.UseGoodNumber | ||
| 88 | + } | ||
| 89 | + return good.PlanGoodNumber | ||
| 90 | +} | ||
| 91 | + | ||
| 92 | +//GetCurrentAmount 获取当前的商品总额 | ||
| 93 | +func (good OrderGood) GetCurrentAmount() float64 { | ||
| 94 | + if good.GoodCompute.UseAmount >= 0 { | ||
| 95 | + return good.GoodCompute.UseAmount | ||
| 96 | + } | ||
| 97 | + return good.GoodCompute.PlanAmount | ||
| 98 | +} | ||
| 99 | + | ||
| 100 | +//GetCurrentAmount 获取当前的商品合伙人分红 | ||
| 101 | +func (good OrderGood) GetCurrentPartnerBonus() float64 { | ||
| 102 | + if good.GoodCompute.UsePartnerBonus >= 0 { | ||
| 103 | + return good.GoodCompute.UsePartnerBonus | ||
| 104 | + } | ||
| 105 | + return good.GoodCompute.PlanPartnerBonus | ||
| 106 | +} | ||
| 107 | + | ||
| 108 | +//Update 更新商品相关的数据 | ||
| 109 | +func (good *OrderGood) Update(m map[string]interface{}) error { | ||
| 110 | + if v, ok := m["GoodName"]; ok { | ||
| 111 | + good.GoodName = v.(string) | ||
| 112 | + } | ||
| 113 | + if v, ok := m["PlanGoodNumber"]; ok { | ||
| 114 | + good.PlanGoodNumber = v.(int) | ||
| 115 | + } | ||
| 116 | + if v, ok := m["UseGoodNumber"]; ok { | ||
| 117 | + good.UseGoodNumber = v.(int) | ||
| 118 | + } | ||
| 119 | + if v, ok := m["Price"]; ok { | ||
| 120 | + good.Price = v.(float64) | ||
| 121 | + } | ||
| 122 | + if v, ok := m["PartnerBonusPercent"]; ok { | ||
| 123 | + good.PartnerBonusPercent = v.(float64) | ||
| 124 | + } | ||
| 125 | + if v, ok := m["Remark"]; ok { | ||
| 126 | + good.Remark = v.(string) | ||
| 127 | + } | ||
| 128 | + if v, ok := m["RemarkReason"]; ok { | ||
| 129 | + good.RemarkReason = v.(OrderGoodRemarkReason) | ||
| 130 | + } | ||
| 131 | + err := good.Compute() | ||
| 132 | + return err | ||
| 74 | } | 133 | } |
| 75 | 134 | ||
| 76 | //OrderGoodBonusWaitPay 货品分红待支付 | 135 | //OrderGoodBonusWaitPay 货品分红待支付 |
| @@ -95,6 +154,7 @@ func (waitPay OrderGoodBonusWaitPay) WartPayPartnerBonus(good *OrderGood) error | @@ -95,6 +154,7 @@ func (waitPay OrderGoodBonusWaitPay) WartPayPartnerBonus(good *OrderGood) error | ||
| 95 | good.GoodCompute.PartnerBonusNot = good.GoodCompute.UsePartnerBonus | 154 | good.GoodCompute.PartnerBonusNot = good.GoodCompute.UsePartnerBonus |
| 96 | } | 155 | } |
| 97 | good.CurrentBonusStatus = OrderGoodBonusWaitPay{} | 156 | good.CurrentBonusStatus = OrderGoodBonusWaitPay{} |
| 157 | + good.BonusStatus = OrderGoodWaitPay | ||
| 98 | return nil | 158 | return nil |
| 99 | } | 159 | } |
| 100 | 160 | ||
| @@ -112,6 +172,7 @@ func (waitPay OrderGoodBonusWaitPay) PayPartnerBonus(good *OrderGood) error { | @@ -112,6 +172,7 @@ func (waitPay OrderGoodBonusWaitPay) PayPartnerBonus(good *OrderGood) error { | ||
| 112 | good.GoodCompute.PartnerBonusExpense = 0 | 172 | good.GoodCompute.PartnerBonusExpense = 0 |
| 113 | good.GoodCompute.PartnerBonusNot = 0 | 173 | good.GoodCompute.PartnerBonusNot = 0 |
| 114 | good.CurrentBonusStatus = OrderGoodBonusHasPay{} | 174 | good.CurrentBonusStatus = OrderGoodBonusHasPay{} |
| 175 | + good.BonusStatus = OrderGoodHasPay | ||
| 115 | return nil | 176 | return nil |
| 116 | } | 177 | } |
| 117 | 178 | ||
| @@ -125,6 +186,7 @@ func (hasPay OrderGoodBonusHasPay) PayPartnerBonus(good *OrderGood) error { | @@ -125,6 +186,7 @@ func (hasPay OrderGoodBonusHasPay) PayPartnerBonus(good *OrderGood) error { | ||
| 125 | good.GoodCompute.PartnerBonusExpense = good.GoodCompute.PartnerBonusHas - good.GoodCompute.UsePartnerBonus | 186 | good.GoodCompute.PartnerBonusExpense = good.GoodCompute.PartnerBonusHas - good.GoodCompute.UsePartnerBonus |
| 126 | } | 187 | } |
| 127 | good.CurrentBonusStatus = OrderGoodBonusHasPay{} | 188 | good.CurrentBonusStatus = OrderGoodBonusHasPay{} |
| 189 | + good.BonusStatus = OrderGoodHasPay | ||
| 128 | return nil | 190 | return nil |
| 129 | } | 191 | } |
| 130 | 192 | ||
| @@ -137,6 +199,7 @@ func NewOrderGood() OrderGood { | @@ -137,6 +199,7 @@ func NewOrderGood() OrderGood { | ||
| 137 | return OrderGood{ | 199 | return OrderGood{ |
| 138 | UseGoodNumber: -1, | 200 | UseGoodNumber: -1, |
| 139 | BonusStatus: OrderGoodWaitPay, | 201 | BonusStatus: OrderGoodWaitPay, |
| 202 | + PartnerBonusPercent: -1, | ||
| 140 | GoodCompute: GoodCompute{ | 203 | GoodCompute: GoodCompute{ |
| 141 | UsePartnerBonus: -1, | 204 | UsePartnerBonus: -1, |
| 142 | UseAmount: -1, | 205 | UseAmount: -1, |
| @@ -150,9 +213,19 @@ func (good *OrderGood) Compute() error { | @@ -150,9 +213,19 @@ func (good *OrderGood) Compute() error { | ||
| 150 | //计算预计货品总值 | 213 | //计算预计货品总值 |
| 151 | //计算预计合伙人分红 | 214 | //计算预计合伙人分红 |
| 152 | price := decimal.NewFromFloat(good.Price) | 215 | price := decimal.NewFromFloat(good.Price) |
| 153 | - planamount := price.Mul(decimal.NewFromInt(int64(good.PlanGoodNumber))) //price*planGoodNumber | 216 | + planGoodNumber := good.PlanGoodNumber |
| 217 | + if good.PlanGoodNumber < 0 { | ||
| 218 | + planGoodNumber = 0 | ||
| 219 | + } | ||
| 220 | + planamount := price.Mul(decimal.NewFromInt(int64(planGoodNumber))) //price*planGoodNumber | ||
| 221 | + var partnerBonusPercent float64 | ||
| 222 | + if good.PartnerBonusPercent < 0 { | ||
| 223 | + partnerBonusPercent = 0 | ||
| 224 | + } else { | ||
| 225 | + partnerBonusPercent = good.PartnerBonusPercent | ||
| 226 | + } | ||
| 154 | //price*useGoodNumber | 227 | //price*useGoodNumber |
| 155 | - planPartnerBonus := planamount.Mul(decimal.NewFromFloat(good.PartnerBonusPercent)).Div(decimal.NewFromInt(100)) //price*planGoodNumber*PartnerBonusPercent | 228 | + planPartnerBonus := planamount.Mul(decimal.NewFromFloat(partnerBonusPercent)).Div(decimal.NewFromInt(100)) //price*planGoodNumber*PartnerBonusPercent |
| 156 | good.GoodCompute.PlanAmount, _ = planamount.Round(2).BigFloat().Float64() | 229 | good.GoodCompute.PlanAmount, _ = planamount.Round(2).BigFloat().Float64() |
| 157 | good.GoodCompute.PlanPartnerBonus, _ = planPartnerBonus.Round(2).BigFloat().Float64() | 230 | good.GoodCompute.PlanPartnerBonus, _ = planPartnerBonus.Round(2).BigFloat().Float64() |
| 158 | if good.UseGoodNumber < 0 { | 231 | if good.UseGoodNumber < 0 { |
| @@ -163,7 +236,7 @@ func (good *OrderGood) Compute() error { | @@ -163,7 +236,7 @@ func (good *OrderGood) Compute() error { | ||
| 163 | //计算调整后的货品总值 | 236 | //计算调整后的货品总值 |
| 164 | //计算调整后的合伙人分红 | 237 | //计算调整后的合伙人分红 |
| 165 | useamount := price.Mul(decimal.NewFromInt(int64(good.UseGoodNumber))) //price*useGoodNumber/price*useGoodNumber | 238 | useamount := price.Mul(decimal.NewFromInt(int64(good.UseGoodNumber))) //price*useGoodNumber/price*useGoodNumber |
| 166 | - usePartnerBonus := useamount.Mul(decimal.NewFromFloat(good.PartnerBonusPercent)).Div(decimal.NewFromInt(100)) //price*useGoodNumber*PartnerBonusPercent | 239 | + usePartnerBonus := useamount.Mul(decimal.NewFromFloat(partnerBonusPercent)).Div(decimal.NewFromInt(100)) //price*useGoodNumber*PartnerBonusPercent |
| 167 | good.GoodCompute.UsePartnerBonus, _ = usePartnerBonus.Round(2).BigFloat().Float64() | 240 | good.GoodCompute.UsePartnerBonus, _ = usePartnerBonus.Round(2).BigFloat().Float64() |
| 168 | good.GoodCompute.UseAmount, _ = useamount.Round(2).BigFloat().Float64() | 241 | good.GoodCompute.UseAmount, _ = useamount.Round(2).BigFloat().Float64() |
| 169 | } | 242 | } |
| @@ -177,9 +250,12 @@ type OrderGoodFindQuery struct { | @@ -177,9 +250,12 @@ type OrderGoodFindQuery struct { | ||
| 177 | Limit int | 250 | Limit int |
| 178 | CompanyId int64 | 251 | CompanyId int64 |
| 179 | } | 252 | } |
| 180 | - | 253 | +type OrderGoodFindOneQuery struct { |
| 254 | + GoodId int64 | ||
| 255 | +} | ||
| 181 | type OrderGoodRepository interface { | 256 | type OrderGoodRepository interface { |
| 182 | Save(order []OrderGood) error | 257 | Save(order []OrderGood) error |
| 183 | Find(queryOptions OrderGoodFindQuery) ([]OrderGood, int, error) | 258 | Find(queryOptions OrderGoodFindQuery) ([]OrderGood, int, error) |
| 259 | + FindOne(queryOptions OrderGoodFindOneQuery) (OrderGood, error) | ||
| 184 | Remove(orderid int64, companyId int64, ids ...int64) error | 260 | Remove(orderid int64, companyId int64, ids ...int64) error |
| 185 | } | 261 | } |
pkg/domain/order_log.go
0 → 100644
| 1 | +package domain | ||
| 2 | + | ||
| 3 | +import "time" | ||
| 4 | + | ||
| 5 | +// 日志数据来源 | ||
| 6 | +const ( | ||
| 7 | + //管理后台 | ||
| 8 | + ORDER_LOG_FROM string = "web_admin" | ||
| 9 | +) | ||
| 10 | + | ||
| 11 | +//操作人员的类型 | ||
| 12 | +const ( | ||
| 13 | + //操作人类型 | ||
| 14 | + ORDER_LOG_OPERATOR_ADMIN string = "admin" | ||
| 15 | +) | ||
| 16 | + | ||
| 17 | +//OrderLogDescript 描述日志内容 | ||
| 18 | +type OrderLogDescript struct { | ||
| 19 | + Title string `json:"title"` //标题 | ||
| 20 | + Item string `json:"item"` //修改的项目 | ||
| 21 | + Action []string `json:"action"` //执行的操作 | ||
| 22 | +} | ||
| 23 | + | ||
| 24 | +//OrderLog 订单修改记录 | ||
| 25 | +type OrderLog struct { | ||
| 26 | + Id int64 | ||
| 27 | + OrderId int64 `json:"orderId"` //订单id | ||
| 28 | + GoodId int64 `json:"goodId"` | ||
| 29 | + AlterTime time.Time `json:"alterTime"` //时间 | ||
| 30 | + Operator string `json:"operator"` //操作人员 | ||
| 31 | + OperatorId int64 `json:"operatorId"` //操作人员Id | ||
| 32 | + OperatorType string `json:"operatorType"` //操作人员的类型 | ||
| 33 | + LogAction string `json:"logAction"` //执行动作 | ||
| 34 | + Descript []OrderLogDescript `json:"descript"` //描述日志内容 | ||
| 35 | + DataFrom string `json:"dataFrom"` //修改操作的来源:"web_admin" | ||
| 36 | +} | ||
| 37 | + | ||
| 38 | +type OrderLogFindQuery struct { | ||
| 39 | + OrderId int64 `json:"orderId"` | ||
| 40 | +} | ||
| 41 | + | ||
| 42 | +type OrderLogRepository interface { | ||
| 43 | + Add(*OrderLog) error | ||
| 44 | + Find(queryOptions OrderLogFindQuery) ([]OrderLog, error) | ||
| 45 | +} |
pkg/domain/order_with_bestshop.go
0 → 100644
| 1 | +package domain | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "errors" | ||
| 5 | + "fmt" | ||
| 6 | +) | ||
| 7 | + | ||
| 8 | +//类型为(orderType=OrderTypeBestShop) 海鲜干货的订单分红 | ||
| 9 | +//因页面上的对于该类型的订单分红状态处理方式 有别于原有的其他类型(OrderReal),所以单独提取出来 | ||
| 10 | + | ||
| 11 | +// OrderGoodWithBestshopBonusStatus 支付状态 | ||
| 12 | +type OrderGoodWithBestshopBonusStatus interface { | ||
| 13 | + OrderGoodBonusStatus | ||
| 14 | + UpdateOrderGoodNumber(good *OrderGood, number int) error | ||
| 15 | + UpdatePertnerBonusPercent(good *OrderGood, percent float64) error | ||
| 16 | +} | ||
| 17 | + | ||
| 18 | +//OrderGoodWithBestshop 处理订单中商品的分红相关数据 | ||
| 19 | +type OrderGoodWithBestshop struct { | ||
| 20 | + currentBonusStatus OrderGoodWithBestshopBonusStatus | ||
| 21 | +} | ||
| 22 | + | ||
| 23 | +func (o *OrderGoodWithBestshop) UpdateBonusByGoodNumber(good *OrderGood, number int) error { | ||
| 24 | + o.reset(good) | ||
| 25 | + if good.PlanGoodNumber < number { | ||
| 26 | + return fmt.Errorf("修改商品数量的值不能大于初始值%d", good.PlanGoodNumber) | ||
| 27 | + } | ||
| 28 | + err := o.currentBonusStatus.UpdateOrderGoodNumber(good, number) | ||
| 29 | + return err | ||
| 30 | +} | ||
| 31 | + | ||
| 32 | +func (o *OrderGoodWithBestshop) UpdateBonusByPertnerBonusPercent(good *OrderGood, percent float64) error { | ||
| 33 | + o.reset(good) | ||
| 34 | + err := o.currentBonusStatus.UpdatePertnerBonusPercent(good, percent) | ||
| 35 | + return err | ||
| 36 | +} | ||
| 37 | + | ||
| 38 | +func (o *OrderGoodWithBestshop) PayPartnerBonus(good *OrderGood) error { | ||
| 39 | + o.currentBonusStatus = OrderGoodBonusBestshopHasPay{} | ||
| 40 | + err := good.Compute() | ||
| 41 | + if err != nil { | ||
| 42 | + return errors.New("核算商品数据失败" + err.Error()) | ||
| 43 | + } | ||
| 44 | + err = good.CurrentBonusStatus.PayPartnerBonus(good) | ||
| 45 | + return err | ||
| 46 | +} | ||
| 47 | + | ||
| 48 | +func (o *OrderGoodWithBestshop) reset(good *OrderGood) { | ||
| 49 | + switch good.BonusStatus { | ||
| 50 | + case OrderGoodWaitPay: | ||
| 51 | + o.currentBonusStatus = OrderGoodBonusBestshopWaitPay{} | ||
| 52 | + case OrderGoodHasPay: | ||
| 53 | + o.currentBonusStatus = OrderGoodBonusBestshopHasPay{} | ||
| 54 | + } | ||
| 55 | + return | ||
| 56 | +} | ||
| 57 | + | ||
| 58 | +//OrderGoodBonusBestshopWaitPay 货品支付状态:待支付 | ||
| 59 | +type OrderGoodBonusBestshopWaitPay struct { | ||
| 60 | + OrderGoodBonusWaitPay | ||
| 61 | +} | ||
| 62 | + | ||
| 63 | +var _ OrderGoodWithBestshopBonusStatus = (*OrderGoodBonusBestshopWaitPay)(nil) | ||
| 64 | + | ||
| 65 | +func (waitPay OrderGoodBonusBestshopWaitPay) UpdateOrderGoodNumber(good *OrderGood, number int) error { | ||
| 66 | + good.UseGoodNumber = number | ||
| 67 | + //待支付状态计算 | ||
| 68 | + err := good.Compute() | ||
| 69 | + if err != nil { | ||
| 70 | + return errors.New("核算商品数据失败" + err.Error()) | ||
| 71 | + } | ||
| 72 | + err = good.CurrentBonusStatus.WartPayPartnerBonus(good) | ||
| 73 | + return err | ||
| 74 | +} | ||
| 75 | + | ||
| 76 | +func (waitPay OrderGoodBonusBestshopWaitPay) UpdatePertnerBonusPercent(good *OrderGood, percent float64) error { | ||
| 77 | + good.PartnerBonusPercent = percent | ||
| 78 | + //待支付状态计算 | ||
| 79 | + err := good.Compute() | ||
| 80 | + if err != nil { | ||
| 81 | + return errors.New("核算商品数据失败" + err.Error()) | ||
| 82 | + } | ||
| 83 | + err = good.CurrentBonusStatus.WartPayPartnerBonus(good) | ||
| 84 | + return err | ||
| 85 | +} | ||
| 86 | + | ||
| 87 | +//OrderGoodBonusBestshopHasPay 货品支付状态:已支付 | ||
| 88 | +type OrderGoodBonusBestshopHasPay struct { | ||
| 89 | + OrderGoodBonusHasPay | ||
| 90 | +} | ||
| 91 | + | ||
| 92 | +var _ OrderGoodWithBestshopBonusStatus = (*OrderGoodBonusBestshopHasPay)(nil) | ||
| 93 | + | ||
| 94 | +func (hasPay OrderGoodBonusBestshopHasPay) UpdateOrderGoodNumber(good *OrderGood, number int) error { | ||
| 95 | + return errors.New("已支付分红的货品订单,不能修改货品数量") | ||
| 96 | +} | ||
| 97 | + | ||
| 98 | +func (hasPay OrderGoodBonusBestshopHasPay) UpdatePertnerBonusPercent(good *OrderGood, percent float64) error { | ||
| 99 | + return errors.New("已支付分红的货品订单,不能修改合伙人分红比例") | ||
| 100 | +} |
pkg/domain/service/order_bonus.go
0 → 100644
| 1 | +package service | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + coreDomain "github.com/linmadan/egglib-go/core/domain" | ||
| 5 | +) | ||
| 6 | + | ||
| 7 | +type OrderBonusService interface { | ||
| 8 | + coreDomain.DomainEventPublisher | ||
| 9 | + UpdateBounsByGoodNumber(orderId int64, adminId int64, goodid int64, goodWithNumber int, reason string) error | ||
| 10 | + UpdateBounsByPartnerBonusPercent(orderId int64, adminId int64, goodId int64, partnerPercent float64, reason string) error | ||
| 11 | + UpdateOrderRemarkBonus(orderId int64, adminId int64, remark string) error | ||
| 12 | + PayOrderGoodBonus(orderId int64, goodId int64, adminId int64) error | ||
| 13 | +} |
| @@ -3,6 +3,9 @@ package dao | @@ -3,6 +3,9 @@ package dao | ||
| 3 | import ( | 3 | import ( |
| 4 | "fmt" | 4 | "fmt" |
| 5 | 5 | ||
| 6 | + "github.com/go-pg/pg/v10/orm" | ||
| 7 | + | ||
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 6 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/models" | 9 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/models" |
| 7 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | 10 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" |
| 8 | ) | 11 | ) |
| @@ -22,7 +25,7 @@ func NewOrderBaseDao(transactionContext *transaction.TransactionContext) (*Order | @@ -22,7 +25,7 @@ func NewOrderBaseDao(transactionContext *transaction.TransactionContext) (*Order | ||
| 22 | } | 25 | } |
| 23 | 26 | ||
| 24 | func (dao OrderBaseDao) OrderCodeExist(code string, notId ...int64) (bool, error) { | 27 | func (dao OrderBaseDao) OrderCodeExist(code string, notId ...int64) (bool, error) { |
| 25 | - tx := dao.transactionContext.PgDd | 28 | + tx := dao.transactionContext.GetDB() |
| 26 | m := &models.OrderBase{} | 29 | m := &models.OrderBase{} |
| 27 | query := tx.Model(m).Where("order_code=?", code) | 30 | query := tx.Model(m).Where("order_code=?", code) |
| 28 | if len(notId) > 0 { | 31 | if len(notId) > 0 { |
| @@ -33,7 +36,7 @@ func (dao OrderBaseDao) OrderCodeExist(code string, notId ...int64) (bool, error | @@ -33,7 +36,7 @@ func (dao OrderBaseDao) OrderCodeExist(code string, notId ...int64) (bool, error | ||
| 33 | } | 36 | } |
| 34 | 37 | ||
| 35 | func (dao OrderBaseDao) DeliveryCodeExist(code string, companyId int64, notId ...int64) (bool, error) { | 38 | func (dao OrderBaseDao) DeliveryCodeExist(code string, companyId int64, notId ...int64) (bool, error) { |
| 36 | - tx := dao.transactionContext.PgDd | 39 | + tx := dao.transactionContext.GetDB() |
| 37 | m := &models.OrderBase{} | 40 | m := &models.OrderBase{} |
| 38 | query := tx.Model(m).Where("delivery_code=?", code).Where("company_id=?", companyId) | 41 | query := tx.Model(m).Where("delivery_code=?", code).Where("company_id=?", companyId) |
| 39 | if len(notId) > 0 { | 42 | if len(notId) > 0 { |
| @@ -42,3 +45,32 @@ func (dao OrderBaseDao) DeliveryCodeExist(code string, companyId int64, notId .. | @@ -42,3 +45,32 @@ func (dao OrderBaseDao) DeliveryCodeExist(code string, companyId int64, notId .. | ||
| 42 | ok, err := query.Exists() | 45 | ok, err := query.Exists() |
| 43 | return ok, err | 46 | return ok, err |
| 44 | } | 47 | } |
| 48 | + | ||
| 49 | +//OrderListByCondition 根据条件获取订单分红列表 | ||
| 50 | +//orderType 订单类型 | ||
| 51 | +//partnerOrCode 合伙人姓名或订单号或发货单号 | ||
| 52 | +func (dao OrderBaseDao) OrderBonusListByCondition(companyId int64, orderType int, partnerOrCode string, limit, offset int) ([]models.OrderBase, int, error) { | ||
| 53 | + tx := dao.transactionContext.GetDB() | ||
| 54 | + var orders []models.OrderBase | ||
| 55 | + query := tx.Model(&orders).Where("order_base.company_id=?", companyId) | ||
| 56 | + if orderType > 0 { | ||
| 57 | + query = query.Where("order_base.order_type=?", orderType) | ||
| 58 | + } else { | ||
| 59 | + query = query.Where("order_base.order_type<>?", domain.OrderIntention) | ||
| 60 | + } | ||
| 61 | + if len(partnerOrCode) > 0 { | ||
| 62 | + query = query.Join("LEFT JOIN partner_info as p ON order_base.partner_id=p.id"). | ||
| 63 | + WhereGroup(func(q *orm.Query) (*orm.Query, error) { | ||
| 64 | + q = q.WhereOr("order_base.order_code like ? ", "%"+partnerOrCode+"%"). | ||
| 65 | + WhereOr("order_base.delivery_code like ? ", "%"+partnerOrCode+"%"). | ||
| 66 | + WhereOr("p.partner_name like ? ", "%"+partnerOrCode+"%") | ||
| 67 | + return q, nil | ||
| 68 | + }) | ||
| 69 | + } | ||
| 70 | + query = query.Order("order_base.update_time DESC"). | ||
| 71 | + Offset(offset). | ||
| 72 | + Limit(limit) | ||
| 73 | + | ||
| 74 | + cnt, err := query.SelectAndCount() | ||
| 75 | + return orders, cnt, err | ||
| 76 | +} |
pkg/infrastructure/dao/pg_order_bestshop.go
0 → 100644
| 1 | +package dao | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "fmt" | ||
| 5 | + | ||
| 6 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/models" | ||
| 7 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | ||
| 8 | +) | ||
| 9 | + | ||
| 10 | +type OrderBestshopDao struct { | ||
| 11 | + transactionContext *transaction.TransactionContext | ||
| 12 | +} | ||
| 13 | + | ||
| 14 | +func NewOrderBestshopDao(transactionContext *transaction.TransactionContext) (*OrderBestshopDao, error) { | ||
| 15 | + if transactionContext == nil { | ||
| 16 | + return nil, fmt.Errorf("transactionContext参数不能为nil") | ||
| 17 | + } else { | ||
| 18 | + return &OrderBestshopDao{ | ||
| 19 | + transactionContext: transactionContext, | ||
| 20 | + }, nil | ||
| 21 | + } | ||
| 22 | +} | ||
| 23 | + | ||
| 24 | +func (dao OrderBestshopDao) OrderExist(orderCode string) (bool, error) { | ||
| 25 | + tx := dao.transactionContext.GetDB() | ||
| 26 | + m := models.OrderBestshop{} | ||
| 27 | + query := tx.Model(&m).Where("order_code=?", orderCode) | ||
| 28 | + ok, err := query.Exists() | ||
| 29 | + return ok, err | ||
| 30 | +} |
| @@ -16,6 +16,7 @@ func NewBusinessBonusService(tcx *transaction.TransactionContext) *BusinessBonus | @@ -16,6 +16,7 @@ func NewBusinessBonusService(tcx *transaction.TransactionContext) *BusinessBonus | ||
| 16 | transactionContext: tcx, | 16 | transactionContext: tcx, |
| 17 | } | 17 | } |
| 18 | } | 18 | } |
| 19 | + | ||
| 19 | func (srv BusinessBonusService) EnableOrDisable(parntnerId int64) error { | 20 | func (srv BusinessBonusService) EnableOrDisable(parntnerId int64) error { |
| 20 | var ( | 21 | var ( |
| 21 | bonusDao, _ = dao.NewBusinessBonusDao(srv.transactionContext) | 22 | bonusDao, _ = dao.NewBusinessBonusDao(srv.transactionContext) |
| 1 | +package domainService | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "errors" | ||
| 5 | + "fmt" | ||
| 6 | + | ||
| 7 | + coreDomain "github.com/linmadan/egglib-go/core/domain" | ||
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 9 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain/event" | ||
| 10 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain/service" | ||
| 11 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | ||
| 12 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/repository" | ||
| 13 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/lib" | ||
| 14 | +) | ||
| 15 | + | ||
| 16 | +//OrderBonusServices 处理订单分红的相关操作 | ||
| 17 | +type OrderBonusService struct { | ||
| 18 | + coreDomain.BaseEventPublisher | ||
| 19 | + transactionContext *transaction.TransactionContext | ||
| 20 | +} | ||
| 21 | + | ||
| 22 | +var _ service.OrderBonusService = (*OrderBonusService)(nil) | ||
| 23 | + | ||
| 24 | +func NewOrderBonusService(tcx *transaction.TransactionContext) *OrderBonusService { | ||
| 25 | + return &OrderBonusService{ | ||
| 26 | + transactionContext: tcx, | ||
| 27 | + } | ||
| 28 | +} | ||
| 29 | + | ||
| 30 | +//UpdateBounsWithGoodNumber 分红时,因修改订单中商品的数量发生分红变动 | ||
| 31 | +//目前只处理 xiangmi的订单 即 order_type = OrderTypeBestShop (3) | ||
| 32 | +func (serve *OrderBonusService) UpdateBounsByGoodNumber(orderId int64, adminId int64, goodId int64, goodWithNumber int, reason string) error { | ||
| 33 | + var ( | ||
| 34 | + userRepository domain.UsersRepository | ||
| 35 | + orderBaseReponsitory domain.OrderBaseRepository | ||
| 36 | + orderGoodRepository domain.OrderGoodRepository | ||
| 37 | + oldOrder *domain.OrderBase | ||
| 38 | + adminUser domain.Users | ||
| 39 | + err error | ||
| 40 | + ) | ||
| 41 | + if orderGoodRepository, err = repository.NewOrderGoodRepository(serve.transactionContext); err != nil { | ||
| 42 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 43 | + } | ||
| 44 | + if orderBaseReponsitory, err = repository.NewOrderBaseRepository(serve.transactionContext); err != nil { | ||
| 45 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 46 | + } | ||
| 47 | + if userRepository, err = repository.NewUsersRepository(serve.transactionContext); err != nil { | ||
| 48 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 49 | + } | ||
| 50 | + oldOrder, err = orderBaseReponsitory.FindOne(domain.OrderBaseFindOneQuery{OrderId: orderId}) | ||
| 51 | + if err != nil { | ||
| 52 | + e := fmt.Sprintf("获取订单(id=%d)数据失败,%s", orderId, err) | ||
| 53 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 54 | + } | ||
| 55 | + if oldOrder.OrderType != domain.OrderTypeBestShop { | ||
| 56 | + return lib.ThrowError(lib.BUSINESS_ERROR, "订单类型错误") | ||
| 57 | + } | ||
| 58 | + oldOrder.Goods, _, err = orderGoodRepository.Find(domain.OrderGoodFindQuery{OrderId: orderId}) | ||
| 59 | + if err != nil { | ||
| 60 | + e := fmt.Sprintf("获取订单(id=%d)中的货品数据失败,%s", orderId, err) | ||
| 61 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 62 | + } | ||
| 63 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: adminId}) | ||
| 64 | + if err != nil { | ||
| 65 | + e := fmt.Sprintf("获取管理员用户(id=%d)数据失败,%s", adminId, err) | ||
| 66 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 67 | + } | ||
| 68 | + if ok := adminUser.InCompany(oldOrder.CompanyId); !ok { | ||
| 69 | + return lib.ThrowError(lib.BUSINESS_ERROR, "用户不能更新非自己公司的订单") | ||
| 70 | + } | ||
| 71 | + var ( | ||
| 72 | + updateGood domain.OrderGood | ||
| 73 | + formerNumber int | ||
| 74 | + formerAmount float64 | ||
| 75 | + newAmount float64 | ||
| 76 | + goodExist bool | ||
| 77 | + ) | ||
| 78 | + for i := range oldOrder.Goods { | ||
| 79 | + if oldOrder.Goods[i].Id != goodId { | ||
| 80 | + continue | ||
| 81 | + } | ||
| 82 | + updateGood = oldOrder.Goods[i] | ||
| 83 | + formerNumber = updateGood.GetCurrentGoodNumber() | ||
| 84 | + formerAmount = updateGood.GetCurrentAmount() | ||
| 85 | + err := new(domain.OrderGoodWithBestshop). | ||
| 86 | + UpdateBonusByGoodNumber(&updateGood, goodWithNumber) | ||
| 87 | + if err != nil { | ||
| 88 | + return lib.ThrowError(lib.BUSINESS_ERROR, err.Error()) | ||
| 89 | + } | ||
| 90 | + updateGood.RemarkReason.ModifyGoodNumber = reason | ||
| 91 | + newAmount = updateGood.GetCurrentAmount() | ||
| 92 | + goodExist = true | ||
| 93 | + oldOrder.Goods[i] = updateGood | ||
| 94 | + } | ||
| 95 | + if !goodExist { | ||
| 96 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "未找到指定的货品") | ||
| 97 | + } | ||
| 98 | + if err := oldOrder.Compute(); err != nil { | ||
| 99 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "核算订单数据失败"+err.Error()) | ||
| 100 | + } | ||
| 101 | + //更新商品数据 | ||
| 102 | + err = orderGoodRepository.Save([]domain.OrderGood{updateGood}) | ||
| 103 | + if err != nil { | ||
| 104 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "更新商品数据失败,"+err.Error()) | ||
| 105 | + } | ||
| 106 | + //更新订单数据 | ||
| 107 | + err = orderBaseReponsitory.Save(oldOrder) | ||
| 108 | + if err != nil { | ||
| 109 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "更新订单数据失败,"+err.Error()) | ||
| 110 | + } | ||
| 111 | + if formerNumber != goodWithNumber { | ||
| 112 | + // 事件发布 | ||
| 113 | + modifyEvent := event.UpdateBonusByGoodNumber{ | ||
| 114 | + OrderId: oldOrder.Id, | ||
| 115 | + AdminId: adminId, | ||
| 116 | + GoodId: oldOrder.Id, | ||
| 117 | + GoodName: updateGood.GoodName, | ||
| 118 | + FormerNumber: fmt.Sprint(formerNumber), | ||
| 119 | + NewNumber: fmt.Sprint(goodWithNumber), | ||
| 120 | + FormerAmount: fmt.Sprint(formerAmount), | ||
| 121 | + NewAmount: fmt.Sprint(newAmount), | ||
| 122 | + } | ||
| 123 | + if err = serve.Publish(modifyEvent); err != nil { | ||
| 124 | + return err | ||
| 125 | + } | ||
| 126 | + } | ||
| 127 | + return nil | ||
| 128 | +} | ||
| 129 | + | ||
| 130 | +//UpdateBounsByPartnerBonusPercent 分红时,因修改订单中商品的合伙人分行比例发生分红变动 | ||
| 131 | +////目前只处理 xiangmi的订单 即 order_type = OrderTypeBestShop (3) | ||
| 132 | +func (serve *OrderBonusService) UpdateBounsByPartnerBonusPercent(orderId int64, adminId int64, goodId int64, partnerPercent float64, reason string) error { | ||
| 133 | + var ( | ||
| 134 | + userRepository domain.UsersRepository | ||
| 135 | + orderBaseReponsitory domain.OrderBaseRepository | ||
| 136 | + orderGoodRepository domain.OrderGoodRepository | ||
| 137 | + oldOrder *domain.OrderBase | ||
| 138 | + adminUser domain.Users | ||
| 139 | + err error | ||
| 140 | + ) | ||
| 141 | + if orderGoodRepository, err = repository.NewOrderGoodRepository(serve.transactionContext); err != nil { | ||
| 142 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 143 | + } | ||
| 144 | + if orderBaseReponsitory, err = repository.NewOrderBaseRepository(serve.transactionContext); err != nil { | ||
| 145 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 146 | + } | ||
| 147 | + if userRepository, err = repository.NewUsersRepository(serve.transactionContext); err != nil { | ||
| 148 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 149 | + } | ||
| 150 | + oldOrder, err = orderBaseReponsitory.FindOne(domain.OrderBaseFindOneQuery{OrderId: orderId}) | ||
| 151 | + if err != nil { | ||
| 152 | + e := fmt.Sprintf("获取订单(id=%d)数据失败,%s", orderId, err) | ||
| 153 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 154 | + } | ||
| 155 | + if oldOrder.OrderType != domain.OrderTypeBestShop { | ||
| 156 | + return lib.ThrowError(lib.BUSINESS_ERROR, "订单类型错误") | ||
| 157 | + } | ||
| 158 | + oldOrder.Goods, _, err = orderGoodRepository.Find(domain.OrderGoodFindQuery{OrderId: orderId}) | ||
| 159 | + if err != nil { | ||
| 160 | + e := fmt.Sprintf("获取订单中(id=%d)的货品数据失败,%s", orderId, err) | ||
| 161 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 162 | + } | ||
| 163 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: adminId}) | ||
| 164 | + if err != nil { | ||
| 165 | + e := fmt.Sprintf("获取管理员用户(id=%d)数据失败,%s", adminId, err) | ||
| 166 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 167 | + } | ||
| 168 | + if ok := adminUser.InCompany(oldOrder.CompanyId); !ok { | ||
| 169 | + return lib.ThrowError(lib.BUSINESS_ERROR, "用户不能更新非自己公司的订单") | ||
| 170 | + } | ||
| 171 | + var ( | ||
| 172 | + updateGood domain.OrderGood | ||
| 173 | + formerPartnerBonusPercent float64 | ||
| 174 | + formerPartnerBonus float64 | ||
| 175 | + newPartnerBonus float64 | ||
| 176 | + goodExist bool | ||
| 177 | + ) | ||
| 178 | + for i := range oldOrder.Goods { | ||
| 179 | + if oldOrder.Goods[i].Id != goodId { | ||
| 180 | + continue | ||
| 181 | + } | ||
| 182 | + updateGood = oldOrder.Goods[i] | ||
| 183 | + formerPartnerBonusPercent = updateGood.PartnerBonusPercent | ||
| 184 | + formerPartnerBonus = updateGood.GetCurrentPartnerBonus() | ||
| 185 | + err := new(domain.OrderGoodWithBestshop). | ||
| 186 | + UpdateBonusByPertnerBonusPercent(&updateGood, partnerPercent) | ||
| 187 | + if err != nil { | ||
| 188 | + return lib.ThrowError(lib.BUSINESS_ERROR, err.Error()) | ||
| 189 | + } | ||
| 190 | + updateGood.RemarkReason.ModifyPartnerBonusPercent = reason | ||
| 191 | + newPartnerBonus = updateGood.GetCurrentPartnerBonus() | ||
| 192 | + goodExist = true | ||
| 193 | + oldOrder.Goods[i] = updateGood | ||
| 194 | + } | ||
| 195 | + if !goodExist { | ||
| 196 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "未找到指定的货品") | ||
| 197 | + } | ||
| 198 | + if err := oldOrder.Compute(); err != nil { | ||
| 199 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "核算订单数据失败"+err.Error()) | ||
| 200 | + } | ||
| 201 | + //更新商品数据 | ||
| 202 | + err = orderGoodRepository.Save([]domain.OrderGood{updateGood}) | ||
| 203 | + if err != nil { | ||
| 204 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "更新商品数据失败,"+err.Error()) | ||
| 205 | + } | ||
| 206 | + //更新订单数据 | ||
| 207 | + err = orderBaseReponsitory.Save(oldOrder) | ||
| 208 | + if err != nil { | ||
| 209 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "更新订单数据失败,"+err.Error()) | ||
| 210 | + } | ||
| 211 | + //事件发布 | ||
| 212 | + modifyEvent := event.UpdateBounsByPartnerBonusPercent{ | ||
| 213 | + OrderId: oldOrder.Id, | ||
| 214 | + AdminId: adminUser.Id, | ||
| 215 | + GoodId: updateGood.Id, | ||
| 216 | + GoodName: updateGood.GoodName, | ||
| 217 | + FormerPartnerBonusPercent: fmt.Sprint(formerPartnerBonusPercent), | ||
| 218 | + NewPartnerBonusPercent: fmt.Sprint(partnerPercent), | ||
| 219 | + FormerPartnerBonus: fmt.Sprint(formerPartnerBonus), | ||
| 220 | + NewPartnerBonus: fmt.Sprint(newPartnerBonus), | ||
| 221 | + } | ||
| 222 | + if formerPartnerBonusPercent < 0 { | ||
| 223 | + modifyEvent.FormerPartnerBonus = "-" | ||
| 224 | + modifyEvent.FormerPartnerBonusPercent = "-" | ||
| 225 | + } | ||
| 226 | + if err = serve.Publish(modifyEvent); err != nil { | ||
| 227 | + return err | ||
| 228 | + } | ||
| 229 | + return nil | ||
| 230 | +} | ||
| 231 | + | ||
| 232 | +//PayOrderGoodBonus 支付订单中货品的分红 | ||
| 233 | +//目前只处理 海鲜干货的订单 即 order_type = OrderTypeBestShop (3) | ||
| 234 | +func (serve *OrderBonusService) PayOrderGoodBonus(orderId int64, goodId int64, adminId int64) error { | ||
| 235 | + var ( | ||
| 236 | + userRepository domain.UsersRepository | ||
| 237 | + orderBaseReponsitory domain.OrderBaseRepository | ||
| 238 | + orderGoodRepository domain.OrderGoodRepository | ||
| 239 | + oldOrder *domain.OrderBase | ||
| 240 | + adminUser domain.Users | ||
| 241 | + err error | ||
| 242 | + ) | ||
| 243 | + if orderGoodRepository, err = repository.NewOrderGoodRepository(serve.transactionContext); err != nil { | ||
| 244 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 245 | + } | ||
| 246 | + if orderBaseReponsitory, err = repository.NewOrderBaseRepository(serve.transactionContext); err != nil { | ||
| 247 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 248 | + } | ||
| 249 | + if userRepository, err = repository.NewUsersRepository(serve.transactionContext); err != nil { | ||
| 250 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 251 | + } | ||
| 252 | + oldOrder, err = orderBaseReponsitory.FindOne(domain.OrderBaseFindOneQuery{OrderId: orderId}) | ||
| 253 | + if err != nil { | ||
| 254 | + e := fmt.Sprintf("获取订单(id=%d)数据失败,%s", orderId, err) | ||
| 255 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 256 | + } | ||
| 257 | + if oldOrder.OrderType != domain.OrderTypeBestShop { | ||
| 258 | + return lib.ThrowError(lib.BUSINESS_ERROR, "订单类型错误") | ||
| 259 | + } | ||
| 260 | + oldOrder.Goods, _, err = orderGoodRepository.Find(domain.OrderGoodFindQuery{OrderId: orderId}) | ||
| 261 | + if err != nil { | ||
| 262 | + e := fmt.Sprintf("获取订单中(id=%d)的货品数据失败,%s", orderId, err) | ||
| 263 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 264 | + } | ||
| 265 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: adminId}) | ||
| 266 | + if err != nil { | ||
| 267 | + e := fmt.Sprintf("获取管理员用户(id=%d)数据失败,%s", adminId, err) | ||
| 268 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 269 | + } | ||
| 270 | + if ok := adminUser.InCompany(oldOrder.CompanyId); !ok { | ||
| 271 | + return lib.ThrowError(lib.BUSINESS_ERROR, "用户不能更新非自己公司的订单") | ||
| 272 | + } | ||
| 273 | + var ( | ||
| 274 | + updateGood domain.OrderGood | ||
| 275 | + goodExist bool | ||
| 276 | + ) | ||
| 277 | + for i := range oldOrder.Goods { | ||
| 278 | + if oldOrder.Goods[i].Id != goodId { | ||
| 279 | + continue | ||
| 280 | + } | ||
| 281 | + updateGood = oldOrder.Goods[i] | ||
| 282 | + err := new(domain.OrderGoodWithBestshop).PayPartnerBonus(&updateGood) | ||
| 283 | + if err != nil { | ||
| 284 | + return lib.ThrowError(lib.BUSINESS_ERROR, err.Error()) | ||
| 285 | + } | ||
| 286 | + goodExist = true | ||
| 287 | + oldOrder.Goods[i] = updateGood | ||
| 288 | + } | ||
| 289 | + if !goodExist { | ||
| 290 | + return errors.New("未找到指定的货品") | ||
| 291 | + } | ||
| 292 | + //计算订单的总数据 | ||
| 293 | + if err := oldOrder.Compute(); err != nil { | ||
| 294 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, "核算订单数据失败"+err.Error()) | ||
| 295 | + } | ||
| 296 | + //更新商品数据 | ||
| 297 | + err = orderGoodRepository.Save([]domain.OrderGood{updateGood}) | ||
| 298 | + if err != nil { | ||
| 299 | + return fmt.Errorf("更新商品数据失败,%s", err) | ||
| 300 | + } | ||
| 301 | + //更新订单数据 | ||
| 302 | + err = orderBaseReponsitory.Save(oldOrder) | ||
| 303 | + if err != nil { | ||
| 304 | + return fmt.Errorf("更新订单数据失败,%s", err) | ||
| 305 | + } | ||
| 306 | + // | ||
| 307 | + payEvent := event.PayOrderGoodBonus{ | ||
| 308 | + OrderId: orderId, | ||
| 309 | + GoodId: goodId, | ||
| 310 | + AdminId: adminId, | ||
| 311 | + GoodName: updateGood.GoodName, | ||
| 312 | + PartnerBonus: updateGood.GetCurrentPartnerBonus(), | ||
| 313 | + } | ||
| 314 | + if err = serve.Publish(payEvent); err != nil { | ||
| 315 | + return err | ||
| 316 | + } | ||
| 317 | + return nil | ||
| 318 | +} | ||
| 319 | + | ||
| 320 | +//UpdateOrderRemarkBonus 更新备注 | ||
| 321 | +//目前只处理 海鲜干货的订单 即 order_type = OrderTypeBestShop (3) | ||
| 322 | +func (serve *OrderBonusService) UpdateOrderRemarkBonus(orderId int64, adminId int64, remark string) error { | ||
| 323 | + var ( | ||
| 324 | + userRepository domain.UsersRepository | ||
| 325 | + orderBaseReponsitory domain.OrderBaseRepository | ||
| 326 | + oldOrder *domain.OrderBase | ||
| 327 | + adminUser domain.Users | ||
| 328 | + err error | ||
| 329 | + ) | ||
| 330 | + if orderBaseReponsitory, err = repository.NewOrderBaseRepository(serve.transactionContext); err != nil { | ||
| 331 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 332 | + } | ||
| 333 | + if userRepository, err = repository.NewUsersRepository(serve.transactionContext); err != nil { | ||
| 334 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, err.Error()) | ||
| 335 | + } | ||
| 336 | + oldOrder, err = orderBaseReponsitory.FindOne(domain.OrderBaseFindOneQuery{OrderId: orderId}) | ||
| 337 | + if err != nil { | ||
| 338 | + e := fmt.Sprintf("获取订单(id=%d)数据失败,%s", orderId, err) | ||
| 339 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 340 | + } | ||
| 341 | + if oldOrder.OrderType != domain.OrderTypeBestShop { | ||
| 342 | + return lib.ThrowError(lib.BUSINESS_ERROR, "订单类型错误") | ||
| 343 | + } | ||
| 344 | + adminUser, err = userRepository.FindOne(domain.UsersFindOneQuery{Id: adminId}) | ||
| 345 | + if err != nil { | ||
| 346 | + e := fmt.Sprintf("获取管理员用户(id=%d)数据失败,%s", adminId, err) | ||
| 347 | + return lib.ThrowError(lib.INTERNAL_SERVER_ERROR, e) | ||
| 348 | + } | ||
| 349 | + if ok := adminUser.InCompany(oldOrder.CompanyId); !ok { | ||
| 350 | + return lib.ThrowError(lib.BUSINESS_ERROR, "用户不能更新非自己公司的订单") | ||
| 351 | + } | ||
| 352 | + formerRemark := oldOrder.Remark.RemarkBonus | ||
| 353 | + oldOrder.Remark.RemarkBonus = remark | ||
| 354 | + //更新订单数据 | ||
| 355 | + err = orderBaseReponsitory.Save(oldOrder) | ||
| 356 | + if err != nil { | ||
| 357 | + return fmt.Errorf("更新订单数据失败,%s", err) | ||
| 358 | + } | ||
| 359 | + if formerRemark != remark { | ||
| 360 | + //事件发布 | ||
| 361 | + modifyEvent := event.UpdateOrderRemark{ | ||
| 362 | + OrderId: oldOrder.Id, | ||
| 363 | + AdminId: adminUser.Id, | ||
| 364 | + FormerRemark: formerRemark, | ||
| 365 | + NewRemark: remark, | ||
| 366 | + } | ||
| 367 | + if err = serve.Publish(modifyEvent); err != nil { | ||
| 368 | + return err | ||
| 369 | + } | ||
| 370 | + } | ||
| 371 | + | ||
| 372 | + return nil | ||
| 373 | +} |
| @@ -5,6 +5,7 @@ import ( | @@ -5,6 +5,7 @@ import ( | ||
| 5 | "time" | 5 | "time" |
| 6 | 6 | ||
| 7 | "github.com/go-pg/pg/v10" | 7 | "github.com/go-pg/pg/v10" |
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 8 | ) | 9 | ) |
| 9 | 10 | ||
| 10 | // 公司信息 | 11 | // 公司信息 |
| @@ -34,6 +35,8 @@ type Company struct { | @@ -34,6 +35,8 @@ type Company struct { | ||
| 34 | UpdateAt time.Time | 35 | UpdateAt time.Time |
| 35 | // 删除时间 | 36 | // 删除时间 |
| 36 | DeleteAt time.Time | 37 | DeleteAt time.Time |
| 38 | + | ||
| 39 | + Applets []domain.CompanyApplets | ||
| 37 | } | 40 | } |
| 38 | 41 | ||
| 39 | var _ pg.BeforeUpdateHook = (*Company)(nil) | 42 | var _ pg.BeforeUpdateHook = (*Company)(nil) |
| @@ -63,6 +63,10 @@ type OrderBase struct { | @@ -63,6 +63,10 @@ type OrderBase struct { | ||
| 63 | //分红支付状态 | 63 | //分红支付状态 |
| 64 | BonusStatus int | 64 | BonusStatus int |
| 65 | CompanyId int64 | 65 | CompanyId int64 |
| 66 | + //数据来源 | ||
| 67 | + DataFrom domain.OrderDataFrom `` | ||
| 68 | + //备注 | ||
| 69 | + Remark domain.OrderBaseRemark `` | ||
| 66 | } | 70 | } |
| 67 | 71 | ||
| 68 | var _ pg.BeforeUpdateHook = (*OrderBase)(nil) | 72 | var _ pg.BeforeUpdateHook = (*OrderBase)(nil) |
| 1 | +package models | ||
| 2 | + | ||
| 3 | +import "time" | ||
| 4 | + | ||
| 5 | +type OrderBestshop struct { | ||
| 6 | + tableName struct{} `pg:"order_bestshop"` | ||
| 7 | + Id int64 | ||
| 8 | + //订单编号 | ||
| 9 | + OrderCode string | ||
| 10 | + //下单时间 | ||
| 11 | + OrderTime string | ||
| 12 | + //订单状态 | ||
| 13 | + OrderState int8 | ||
| 14 | + //发货状态 | ||
| 15 | + DeliveryState int8 | ||
| 16 | + //买家名称 | ||
| 17 | + BuyerName string | ||
| 18 | + //买家电话 | ||
| 19 | + BuyerPhone string | ||
| 20 | + //买家地址 | ||
| 21 | + BuyerAddress string | ||
| 22 | + //买家备注 | ||
| 23 | + BuyerRemark string | ||
| 24 | + // | ||
| 25 | + BuyerId int64 | ||
| 26 | + //订单总数 | ||
| 27 | + OrderCount int | ||
| 28 | + //d订单总额 | ||
| 29 | + OrderAmount float64 | ||
| 30 | + //发货时间 | ||
| 31 | + DeliveryTime string | ||
| 32 | + //创建时间 | ||
| 33 | + CreateTime time.Time | ||
| 34 | + PartnerId int64 | ||
| 35 | + //是否将数据同步到 order_base ,order_good | ||
| 36 | + IsCopy bool `pg:",use_zero"` | ||
| 37 | + CompanyId int64 | ||
| 38 | +} |
| 1 | package models | 1 | package models |
| 2 | 2 | ||
| 3 | +import "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 4 | + | ||
| 3 | //OrderGood 订单中的货品 | 5 | //OrderGood 订单中的货品 |
| 4 | type OrderGood struct { | 6 | type OrderGood struct { |
| 5 | tableName struct{} `pg:"order_good"` | 7 | tableName struct{} `pg:"order_good"` |
| @@ -37,5 +39,10 @@ type OrderGood struct { | @@ -37,5 +39,10 @@ type OrderGood struct { | ||
| 37 | BonusStatus int | 39 | BonusStatus int |
| 38 | //备注信息 | 40 | //备注信息 |
| 39 | Remark string | 41 | Remark string |
| 42 | + //公司id | ||
| 40 | CompanyId int64 | 43 | CompanyId int64 |
| 44 | + //原因备注 | ||
| 45 | + RemarkReason domain.OrderGoodRemarkReason `` | ||
| 46 | + | ||
| 47 | + DataFrom domain.OrderDataFrom `` | ||
| 41 | } | 48 | } |
| 1 | +package models | ||
| 2 | + | ||
| 3 | +type OrderGoodBestshop struct { | ||
| 4 | + tableName struct{} `pg:"order_good_bestshop"` | ||
| 5 | + Id int64 | ||
| 6 | + //订单id | ||
| 7 | + OrderId int64 | ||
| 8 | + //货品编号 | ||
| 9 | + Sn string | ||
| 10 | + //商品编号 | ||
| 11 | + Bn string | ||
| 12 | + //货品名称 | ||
| 13 | + Name string | ||
| 14 | + //单价 | ||
| 15 | + Price float64 | ||
| 16 | + //货品数量 | ||
| 17 | + Nums int | ||
| 18 | + //订单总价 | ||
| 19 | + Amount float64 | ||
| 20 | +} |
pkg/infrastructure/pg/models/order_log.go
0 → 100644
| 1 | +package models | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "context" | ||
| 5 | + "time" | ||
| 6 | + | ||
| 7 | + "github.com/go-pg/pg/v10" | ||
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 9 | +) | ||
| 10 | + | ||
| 11 | +//OrderLog 订单修改记录 | ||
| 12 | +type OrderLog struct { | ||
| 13 | + tableName struct{} `pg:"order_log"` | ||
| 14 | + Id int64 | ||
| 15 | + OrderId int64 `` //订单id | ||
| 16 | + AlterTime time.Time `` //时间 | ||
| 17 | + Operator string `` //操作人员 | ||
| 18 | + OperatorId int64 `` //操作人员Id | ||
| 19 | + OperatorType string `` //操作人员的类型 | ||
| 20 | + LogAction string `` //执行动作 | ||
| 21 | + Descript []domain.OrderLogDescript `` //描述日志内容 | ||
| 22 | + DataFrom string `` //修改操作的来源:"web_admin" | ||
| 23 | +} | ||
| 24 | + | ||
| 25 | +var _ pg.BeforeInsertHook = (*OrderBase)(nil) | ||
| 26 | + | ||
| 27 | +func (l *OrderLog) BeforeInsert(ctx context.Context) (context.Context, error) { | ||
| 28 | + l.AlterTime = time.Now() | ||
| 29 | + return ctx, nil | ||
| 30 | +} |
| @@ -36,6 +36,7 @@ func (repository CompanyRepository) transformPgModelToDomainModel(m *models.Comp | @@ -36,6 +36,7 @@ func (repository CompanyRepository) transformPgModelToDomainModel(m *models.Comp | ||
| 36 | CreateAt: m.CreateAt, | 36 | CreateAt: m.CreateAt, |
| 37 | UpdateAt: m.UpdateAt, | 37 | UpdateAt: m.UpdateAt, |
| 38 | Abbreviation: m.Abbreviation, | 38 | Abbreviation: m.Abbreviation, |
| 39 | + Applets: m.Applets, | ||
| 39 | }, nil | 40 | }, nil |
| 40 | } | 41 | } |
| 41 | 42 | ||
| @@ -55,6 +56,7 @@ func (reponsitory CompanyRepository) Add(m *domain.Company) error { | @@ -55,6 +56,7 @@ func (reponsitory CompanyRepository) Add(m *domain.Company) error { | ||
| 55 | CreateAt: m.CreateAt, | 56 | CreateAt: m.CreateAt, |
| 56 | UpdateAt: m.UpdateAt, | 57 | UpdateAt: m.UpdateAt, |
| 57 | Abbreviation: m.Abbreviation, | 58 | Abbreviation: m.Abbreviation, |
| 59 | + Applets: m.Applets, | ||
| 58 | } | 60 | } |
| 59 | _, err = tx.Model(&companyModel).Insert() | 61 | _, err = tx.Model(&companyModel).Insert() |
| 60 | return err | 62 | return err |
| @@ -77,6 +79,7 @@ func (reponsitory CompanyRepository) Edit(m *domain.Company) error { | @@ -77,6 +79,7 @@ func (reponsitory CompanyRepository) Edit(m *domain.Company) error { | ||
| 77 | DeleteAt: m.DeleteAt, | 79 | DeleteAt: m.DeleteAt, |
| 78 | UpdateAt: m.UpdateAt, | 80 | UpdateAt: m.UpdateAt, |
| 79 | Abbreviation: m.Abbreviation, | 81 | Abbreviation: m.Abbreviation, |
| 82 | + Applets: m.Applets, | ||
| 80 | } | 83 | } |
| 81 | _, err = tx.Model(&companyModel).WherePK().Update() | 84 | _, err = tx.Model(&companyModel).WherePK().Update() |
| 82 | return err | 85 | return err |
| @@ -42,6 +42,8 @@ func (reponsitory OrderBaseRepository) transformPgModelToDomainModel(orderModel | @@ -42,6 +42,8 @@ func (reponsitory OrderBaseRepository) transformPgModelToDomainModel(orderModel | ||
| 42 | }, | 42 | }, |
| 43 | BonusStatus: orderModel.BonusStatus, | 43 | BonusStatus: orderModel.BonusStatus, |
| 44 | CompanyId: orderModel.CompanyId, | 44 | CompanyId: orderModel.CompanyId, |
| 45 | + DataFrom: orderModel.DataFrom, | ||
| 46 | + Remark: orderModel.Remark, | ||
| 45 | } | 47 | } |
| 46 | return order, nil | 48 | return order, nil |
| 47 | } | 49 | } |
| @@ -62,7 +64,8 @@ func (repository OrderBaseRepository) Save(orderInfo *domain.OrderBase) error { | @@ -62,7 +64,8 @@ func (repository OrderBaseRepository) Save(orderInfo *domain.OrderBase) error { | ||
| 62 | PartnerBonusHas: orderInfo.OrderCompute.PartnerBonusHas, PartnerBonusNot: orderInfo.OrderCompute.PartnerBonusNot, | 64 | PartnerBonusHas: orderInfo.OrderCompute.PartnerBonusHas, PartnerBonusNot: orderInfo.OrderCompute.PartnerBonusNot, |
| 63 | PartnerBonusExpense: orderInfo.OrderCompute.PartnerBonusExpense, IsDisable: orderInfo.IsDisable, | 65 | PartnerBonusExpense: orderInfo.OrderCompute.PartnerBonusExpense, IsDisable: orderInfo.IsDisable, |
| 64 | CreateTime: orderInfo.CreateTime, BonusStatus: orderInfo.BonusStatus, | 66 | CreateTime: orderInfo.CreateTime, BonusStatus: orderInfo.BonusStatus, |
| 65 | - CompanyId: orderInfo.CompanyId, | 67 | + CompanyId: orderInfo.CompanyId, DataFrom: orderInfo.DataFrom, |
| 68 | + Remark: orderInfo.Remark, | ||
| 66 | } | 69 | } |
| 67 | if m.Id == 0 { | 70 | if m.Id == 0 { |
| 68 | _, err = tx.Model(m). | 71 | _, err = tx.Model(m). |
| @@ -82,7 +85,7 @@ func (repository OrderBaseRepository) Save(orderInfo *domain.OrderBase) error { | @@ -82,7 +85,7 @@ func (repository OrderBaseRepository) Save(orderInfo *domain.OrderBase) error { | ||
| 82 | } | 85 | } |
| 83 | 86 | ||
| 84 | func (repository OrderBaseRepository) Find(queryOption domain.OrderBaseFindQuery) ([]domain.OrderBase, int, error) { | 87 | func (repository OrderBaseRepository) Find(queryOption domain.OrderBaseFindQuery) ([]domain.OrderBase, int, error) { |
| 85 | - db := repository.transactionContext.PgDd | 88 | + db := repository.transactionContext.GetDB() |
| 86 | orderModels := []models.OrderBase{} | 89 | orderModels := []models.OrderBase{} |
| 87 | query := db.Model(&orderModels) | 90 | query := db.Model(&orderModels) |
| 88 | if queryOption.PartnerId > 0 { | 91 | if queryOption.PartnerId > 0 { |
| 1 | +package repository | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "fmt" | ||
| 5 | + "time" | ||
| 6 | + | ||
| 7 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/models" | ||
| 9 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | ||
| 10 | +) | ||
| 11 | + | ||
| 12 | +type OrderBestshopRepository struct { | ||
| 13 | + transactionContext *transaction.TransactionContext | ||
| 14 | +} | ||
| 15 | + | ||
| 16 | +var ( | ||
| 17 | + _ domain.OrderBestshopRepository = (*OrderBestshopRepository)(nil) | ||
| 18 | +) | ||
| 19 | + | ||
| 20 | +func NewOrderBestshopRepository(transactionContext *transaction.TransactionContext) (*OrderBestshopRepository, error) { | ||
| 21 | + if transactionContext == nil { | ||
| 22 | + return nil, fmt.Errorf("transactionContext参数不能为nil") | ||
| 23 | + } | ||
| 24 | + return &OrderBestshopRepository{transactionContext: transactionContext}, nil | ||
| 25 | +} | ||
| 26 | + | ||
| 27 | +func (respository OrderBestshopRepository) transformPgModelToDomainModel(orderModel *models.OrderBestshop) (order domain.OrderBestShop, err error) { | ||
| 28 | + return domain.OrderBestShop{ | ||
| 29 | + Id: orderModel.Id, | ||
| 30 | + OrderCode: orderModel.OrderCode, | ||
| 31 | + OrderTime: orderModel.OrderTime, | ||
| 32 | + OrderState: orderModel.OrderState, | ||
| 33 | + DeliveryState: orderModel.DeliveryState, | ||
| 34 | + BuyerName: orderModel.BuyerName, | ||
| 35 | + BuyerPhone: orderModel.BuyerPhone, | ||
| 36 | + BuyerAddress: orderModel.BuyerAddress, | ||
| 37 | + BuyerRemark: orderModel.BuyerRemark, | ||
| 38 | + BuyerId: orderModel.BuyerId, | ||
| 39 | + OrderCount: orderModel.OrderCount, | ||
| 40 | + OrderAmount: orderModel.OrderAmount, | ||
| 41 | + DeliveryTime: orderModel.DeliveryTime, | ||
| 42 | + CreateTime: orderModel.CreateTime, | ||
| 43 | + PartnerId: orderModel.PartnerId, | ||
| 44 | + IsCopy: orderModel.IsCopy, | ||
| 45 | + CompanyId: orderModel.CompanyId, | ||
| 46 | + }, nil | ||
| 47 | +} | ||
| 48 | + | ||
| 49 | +func (respository OrderBestshopRepository) Add(order *domain.OrderBestShop) error { | ||
| 50 | + tx := respository.transactionContext.GetDB() | ||
| 51 | + m := models.OrderBestshop{ | ||
| 52 | + OrderCode: order.OrderCode, | ||
| 53 | + OrderTime: order.OrderTime, | ||
| 54 | + OrderState: order.OrderState, | ||
| 55 | + DeliveryState: order.DeliveryState, | ||
| 56 | + BuyerName: order.BuyerName, | ||
| 57 | + BuyerPhone: order.BuyerPhone, | ||
| 58 | + BuyerAddress: order.BuyerAddress, | ||
| 59 | + BuyerRemark: order.BuyerRemark, | ||
| 60 | + BuyerId: order.BuyerId, | ||
| 61 | + OrderCount: order.OrderCount, | ||
| 62 | + OrderAmount: order.OrderAmount, | ||
| 63 | + DeliveryTime: order.DeliveryTime, | ||
| 64 | + CreateTime: time.Now(), | ||
| 65 | + PartnerId: order.PartnerId, | ||
| 66 | + IsCopy: order.IsCopy, | ||
| 67 | + CompanyId: order.CompanyId, | ||
| 68 | + } | ||
| 69 | + _, err := tx.Model(&m).Insert() | ||
| 70 | + order.Id = m.Id | ||
| 71 | + return err | ||
| 72 | +} | ||
| 73 | + | ||
| 74 | +func (respository OrderBestshopRepository) Edit(order *domain.OrderBestShop) error { | ||
| 75 | + tx := respository.transactionContext.GetDB() | ||
| 76 | + m := models.OrderBestshop{ | ||
| 77 | + Id: order.Id, | ||
| 78 | + OrderCode: order.OrderCode, | ||
| 79 | + OrderTime: order.OrderTime, | ||
| 80 | + OrderState: order.OrderState, | ||
| 81 | + DeliveryState: order.DeliveryState, | ||
| 82 | + BuyerName: order.BuyerName, | ||
| 83 | + BuyerPhone: order.BuyerPhone, | ||
| 84 | + BuyerAddress: order.BuyerAddress, | ||
| 85 | + BuyerRemark: order.BuyerRemark, | ||
| 86 | + BuyerId: order.BuyerId, | ||
| 87 | + OrderCount: order.OrderCount, | ||
| 88 | + OrderAmount: order.OrderAmount, | ||
| 89 | + DeliveryTime: order.DeliveryTime, | ||
| 90 | + CreateTime: order.CreateTime, | ||
| 91 | + PartnerId: order.PartnerId, | ||
| 92 | + IsCopy: order.IsCopy, | ||
| 93 | + CompanyId: order.CompanyId, | ||
| 94 | + } | ||
| 95 | + _, err := tx.Model(&m).Where("id=?", order.Id).Update() | ||
| 96 | + order.Id = m.Id | ||
| 97 | + return err | ||
| 98 | +} | ||
| 99 | + | ||
| 100 | +func (respository OrderBestshopRepository) FindOne(queryOption domain.OrderBestshopFindOneQuery) (*domain.OrderBestShop, error) { | ||
| 101 | + tx := respository.transactionContext.GetDB() | ||
| 102 | + m := models.OrderBestshop{} | ||
| 103 | + err := tx.Model(&m). | ||
| 104 | + Where("id=?", queryOption.OrderId). | ||
| 105 | + First() | ||
| 106 | + if err != nil { | ||
| 107 | + return nil, err | ||
| 108 | + } | ||
| 109 | + var order domain.OrderBestShop | ||
| 110 | + order, err = respository.transformPgModelToDomainModel(&m) | ||
| 111 | + if err != nil { | ||
| 112 | + return nil, fmt.Errorf("OrderBestshop domain 数据结构转换失败:%s", err) | ||
| 113 | + } | ||
| 114 | + return &order, nil | ||
| 115 | +} |
| 1 | +package repository | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "fmt" | ||
| 5 | + | ||
| 6 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 7 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/models" | ||
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | ||
| 9 | +) | ||
| 10 | + | ||
| 11 | +type OrderGoodBestshopRepository struct { | ||
| 12 | + transactionContext *transaction.TransactionContext | ||
| 13 | +} | ||
| 14 | + | ||
| 15 | +var ( | ||
| 16 | + _ domain.OrderGoodBestshopRepository = (*OrderGoodBestshopRepository)(nil) | ||
| 17 | +) | ||
| 18 | + | ||
| 19 | +func NewOrderGoodBestshopRepository(transactionContext *transaction.TransactionContext) (*OrderGoodBestshopRepository, error) { | ||
| 20 | + if transactionContext == nil { | ||
| 21 | + return nil, fmt.Errorf("transactionContext参数不能为nil") | ||
| 22 | + } | ||
| 23 | + return &OrderGoodBestshopRepository{transactionContext: transactionContext}, nil | ||
| 24 | +} | ||
| 25 | + | ||
| 26 | +func (respository OrderGoodBestshopRepository) transformPgModelToDomainModel(orderGoodModel *models.OrderGoodBestshop) (orderGood domain.OrderGoodBestShop, err error) { | ||
| 27 | + return domain.OrderGoodBestShop{ | ||
| 28 | + Id: orderGoodModel.Id, | ||
| 29 | + OrderId: orderGoodModel.OrderId, | ||
| 30 | + Sn: orderGoodModel.Sn, | ||
| 31 | + Bn: orderGoodModel.Bn, | ||
| 32 | + Name: orderGoodModel.Name, | ||
| 33 | + Price: orderGoodModel.Price, | ||
| 34 | + Nums: orderGoodModel.Nums, | ||
| 35 | + Amount: orderGoodModel.Amount, | ||
| 36 | + }, nil | ||
| 37 | +} | ||
| 38 | + | ||
| 39 | +func (respository OrderGoodBestshopRepository) Add(good *domain.OrderGoodBestShop) error { | ||
| 40 | + tx := respository.transactionContext.GetDB() | ||
| 41 | + m := models.OrderGoodBestshop{ | ||
| 42 | + Id: good.Id, | ||
| 43 | + OrderId: good.OrderId, | ||
| 44 | + Sn: good.Sn, | ||
| 45 | + Bn: good.Bn, | ||
| 46 | + Name: good.Name, | ||
| 47 | + Price: good.Price, | ||
| 48 | + Nums: good.Nums, | ||
| 49 | + Amount: good.Amount, | ||
| 50 | + } | ||
| 51 | + _, err := tx.Model(&m).Insert() | ||
| 52 | + good.Id = m.Id | ||
| 53 | + return err | ||
| 54 | +} | ||
| 55 | + | ||
| 56 | +func (respository OrderGoodBestshopRepository) Edit(good *domain.OrderGoodBestShop) error { | ||
| 57 | + tx := respository.transactionContext.GetDB() | ||
| 58 | + m := models.OrderGoodBestshop{ | ||
| 59 | + Id: good.Id, | ||
| 60 | + OrderId: good.OrderId, | ||
| 61 | + Sn: good.Sn, | ||
| 62 | + Bn: good.Bn, | ||
| 63 | + Name: good.Name, | ||
| 64 | + Price: good.Price, | ||
| 65 | + Nums: good.Nums, | ||
| 66 | + Amount: good.Amount, | ||
| 67 | + } | ||
| 68 | + _, err := tx.Model(&m).Update() | ||
| 69 | + return err | ||
| 70 | +} | ||
| 71 | + | ||
| 72 | +func (respository OrderGoodBestshopRepository) Find(queryOption domain.OrderGoodBestshopFindQuery) ([]domain.OrderGoodBestShop, error) { | ||
| 73 | + tx := respository.transactionContext.GetDB() | ||
| 74 | + goodModels := []models.OrderGoodBestshop{} | ||
| 75 | + query := tx.Model(&goodModels) | ||
| 76 | + if queryOption.OrderId > 0 { | ||
| 77 | + query = query.Where("order_id=?", queryOption.OrderId) | ||
| 78 | + } | ||
| 79 | + query = query.Limit(1000) | ||
| 80 | + err := query.Select() | ||
| 81 | + if err != nil { | ||
| 82 | + return nil, err | ||
| 83 | + } | ||
| 84 | + goods := []domain.OrderGoodBestShop{} | ||
| 85 | + for i := range goodModels { | ||
| 86 | + g, _ := respository.transformPgModelToDomainModel(&goodModels[i]) | ||
| 87 | + goods = append(goods, g) | ||
| 88 | + } | ||
| 89 | + return goods, nil | ||
| 90 | +} |
| 1 | package repository | 1 | package repository |
| 2 | 2 | ||
| 3 | import ( | 3 | import ( |
| 4 | + "errors" | ||
| 4 | "fmt" | 5 | "fmt" |
| 5 | 6 | ||
| 6 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | 7 | "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" |
| @@ -39,6 +40,8 @@ func (reponsitory OrderGoodRepository) transformPgModelToDomainModel(orderModel | @@ -39,6 +40,8 @@ func (reponsitory OrderGoodRepository) transformPgModelToDomainModel(orderModel | ||
| 39 | PartnerBonusExpense: orderModel.PartnerBonusExpense, | 40 | PartnerBonusExpense: orderModel.PartnerBonusExpense, |
| 40 | }, | 41 | }, |
| 41 | CompanyId: orderModel.CompanyId, | 42 | CompanyId: orderModel.CompanyId, |
| 43 | + RemarkReason: orderModel.RemarkReason, | ||
| 44 | + DataFrom: orderModel.DataFrom, | ||
| 42 | } | 45 | } |
| 43 | switch orderModel.BonusStatus { | 46 | switch orderModel.BonusStatus { |
| 44 | case domain.OrderGoodWaitPay: | 47 | case domain.OrderGoodWaitPay: |
| @@ -63,8 +66,9 @@ func (repository OrderGoodRepository) Save(data []domain.OrderGood) error { | @@ -63,8 +66,9 @@ func (repository OrderGoodRepository) Save(data []domain.OrderGood) error { | ||
| 63 | PlanPartnerBonus: v.GoodCompute.PlanPartnerBonus, UsePartnerBonus: v.GoodCompute.UsePartnerBonus, | 66 | PlanPartnerBonus: v.GoodCompute.PlanPartnerBonus, UsePartnerBonus: v.GoodCompute.UsePartnerBonus, |
| 64 | PartnerBonusHas: v.GoodCompute.PartnerBonusHas, PartnerBonusNot: v.GoodCompute.PartnerBonusNot, | 67 | PartnerBonusHas: v.GoodCompute.PartnerBonusHas, PartnerBonusNot: v.GoodCompute.PartnerBonusNot, |
| 65 | PartnerBonusExpense: v.GoodCompute.PartnerBonusExpense, BonusStatus: v.BonusStatus, | 68 | PartnerBonusExpense: v.GoodCompute.PartnerBonusExpense, BonusStatus: v.BonusStatus, |
| 66 | - Remark: v.Remark, | ||
| 67 | - CompanyId: v.CompanyId, | 69 | + Remark: v.Remark, CompanyId: v.CompanyId, |
| 70 | + RemarkReason: v.RemarkReason, | ||
| 71 | + DataFrom: v.DataFrom, | ||
| 68 | } | 72 | } |
| 69 | if v.Id == 0 { | 73 | if v.Id == 0 { |
| 70 | _, err = tx.Model(m). | 74 | _, err = tx.Model(m). |
| @@ -138,3 +142,27 @@ func (repository OrderGoodRepository) Remove(orderId int64, companyId int64, goo | @@ -138,3 +142,27 @@ func (repository OrderGoodRepository) Remove(orderId int64, companyId int64, goo | ||
| 138 | _, err = query.Delete() | 142 | _, err = query.Delete() |
| 139 | return err | 143 | return err |
| 140 | } | 144 | } |
| 145 | + | ||
| 146 | +func (repository OrderGoodRepository) FindOne(queryOption domain.OrderGoodFindOneQuery) (domain.OrderGood, error) { | ||
| 147 | + var ( | ||
| 148 | + good domain.OrderGood | ||
| 149 | + goodModel models.OrderGood | ||
| 150 | + err error | ||
| 151 | + hasCondition bool | ||
| 152 | + ) | ||
| 153 | + tx := repository.transactionContext.GetDB() | ||
| 154 | + query := tx.Model(&goodModel) | ||
| 155 | + if queryOption.GoodId > 0 { | ||
| 156 | + query = query.Where("id=?", queryOption.GoodId) | ||
| 157 | + hasCondition = true | ||
| 158 | + } | ||
| 159 | + if !hasCondition { | ||
| 160 | + return good, errors.New("OrderGoodRepository.FindOne 必须使用查询条件") | ||
| 161 | + } | ||
| 162 | + err = query.First() | ||
| 163 | + if err != nil { | ||
| 164 | + return good, fmt.Errorf("获取订单的货品数据失败,%s", err) | ||
| 165 | + } | ||
| 166 | + good, err = repository.transformPgModelToDomainModel(&goodModel) | ||
| 167 | + return good, err | ||
| 168 | +} |
| 1 | +package repository | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "fmt" | ||
| 5 | + | ||
| 6 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 7 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/models" | ||
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/infrastructure/pg/transaction" | ||
| 9 | +) | ||
| 10 | + | ||
| 11 | +//订单日志 | ||
| 12 | +type OrderLogRepository struct { | ||
| 13 | + transactionContext *transaction.TransactionContext | ||
| 14 | +} | ||
| 15 | + | ||
| 16 | +var _ domain.OrderLogRepository = (*OrderLogRepository)(nil) | ||
| 17 | + | ||
| 18 | +func NewOrderLogRepository(transactionContext *transaction.TransactionContext) (*OrderLogRepository, error) { | ||
| 19 | + if transactionContext == nil { | ||
| 20 | + return nil, fmt.Errorf("transactionContext参数不能为nil") | ||
| 21 | + } | ||
| 22 | + return &OrderLogRepository{transactionContext: transactionContext}, nil | ||
| 23 | +} | ||
| 24 | + | ||
| 25 | +func (repository OrderLogRepository) transformPgModelToDomainModel(m *models.OrderLog) (data domain.OrderLog, err error) { | ||
| 26 | + return domain.OrderLog{ | ||
| 27 | + Id: m.Id, | ||
| 28 | + OrderId: m.OrderId, | ||
| 29 | + Operator: m.Operator, | ||
| 30 | + OperatorId: m.OperatorId, | ||
| 31 | + OperatorType: m.OperatorType, | ||
| 32 | + AlterTime: m.AlterTime, | ||
| 33 | + LogAction: m.LogAction, | ||
| 34 | + Descript: m.Descript, | ||
| 35 | + DataFrom: m.DataFrom, | ||
| 36 | + }, nil | ||
| 37 | +} | ||
| 38 | + | ||
| 39 | +func (repository OrderLogRepository) Add(data *domain.OrderLog) error { | ||
| 40 | + db := repository.transactionContext.GetDB() | ||
| 41 | + m := models.OrderLog{ | ||
| 42 | + OrderId: data.OrderId, | ||
| 43 | + Operator: data.Operator, | ||
| 44 | + OperatorId: data.OperatorId, | ||
| 45 | + OperatorType: data.OperatorType, | ||
| 46 | + LogAction: data.LogAction, | ||
| 47 | + Descript: data.Descript, | ||
| 48 | + DataFrom: data.DataFrom, | ||
| 49 | + } | ||
| 50 | + _, err := db.Model(&m).Insert() | ||
| 51 | + data.AlterTime = m.AlterTime | ||
| 52 | + return err | ||
| 53 | +} | ||
| 54 | + | ||
| 55 | +func (repository OrderLogRepository) Find(queryOptions domain.OrderLogFindQuery) ([]domain.OrderLog, error) { | ||
| 56 | + db := repository.transactionContext.GetDB() | ||
| 57 | + logModels := []models.OrderLog{} | ||
| 58 | + var err error | ||
| 59 | + query := db.Model(&logModels) | ||
| 60 | + if queryOptions.OrderId > 0 { | ||
| 61 | + query = query.Where("order_id=?", queryOptions.OrderId) | ||
| 62 | + } | ||
| 63 | + query = query.Order("order_log.id") | ||
| 64 | + query = query.Limit(1000) | ||
| 65 | + err = query.Select() | ||
| 66 | + if err != nil { | ||
| 67 | + return nil, err | ||
| 68 | + } | ||
| 69 | + logReturn := []domain.OrderLog{} | ||
| 70 | + for i := range logModels { | ||
| 71 | + domainLog, err := repository.transformPgModelToDomainModel(&logModels[i]) | ||
| 72 | + if err != nil { | ||
| 73 | + return logReturn, err | ||
| 74 | + } | ||
| 75 | + logReturn = append(logReturn, domainLog) | ||
| 76 | + } | ||
| 77 | + return logReturn, nil | ||
| 78 | +} |
| @@ -141,7 +141,7 @@ func (reponsitory UsersRepository) FindOne(queryOptions domain.UsersFindOneQuery | @@ -141,7 +141,7 @@ func (reponsitory UsersRepository) FindOne(queryOptions domain.UsersFindOneQuery | ||
| 141 | query = query.Where("open_id=?", queryOptions.OpenId) | 141 | query = query.Where("open_id=?", queryOptions.OpenId) |
| 142 | } | 142 | } |
| 143 | if !hasCondition { | 143 | if !hasCondition { |
| 144 | - return domain.Users{}, errors.New("FindOne 必须要有查询条件") | 144 | + return domain.Users{}, errors.New("UsersRepository.FindOne 必须要有查询条件") |
| 145 | } | 145 | } |
| 146 | err = query.First() | 146 | err = query.First() |
| 147 | if err != nil { | 147 | if err != nil { |
| @@ -5,6 +5,7 @@ import ( | @@ -5,6 +5,7 @@ import ( | ||
| 5 | categoryService "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/partnerCategory/service" | 5 | categoryService "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/partnerCategory/service" |
| 6 | partnerQuery "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/partnerInfo/query" | 6 | partnerQuery "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/partnerInfo/query" |
| 7 | partnerInfoService "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/partnerInfo/service" | 7 | partnerInfoService "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/partnerInfo/service" |
| 8 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/domain" | ||
| 8 | ) | 9 | ) |
| 9 | 10 | ||
| 10 | type CommonController struct { | 11 | type CommonController struct { |
| @@ -64,3 +65,18 @@ func (c *CommonController) GetPartnerCategory() { | @@ -64,3 +65,18 @@ func (c *CommonController) GetPartnerCategory() { | ||
| 64 | } | 65 | } |
| 65 | c.ResponseData(resp) | 66 | c.ResponseData(resp) |
| 66 | } | 67 | } |
| 68 | + | ||
| 69 | +// GetOrderType 下拉选项数据通用接口,获取订单类型列表 | ||
| 70 | +func (c *CommonController) GetOrderType() { | ||
| 71 | + resp := []map[string]interface{}{ | ||
| 72 | + map[string]interface{}{ | ||
| 73 | + "id": domain.OrderReal, | ||
| 74 | + "name": domain.GetOrderBaseTypeName(domain.OrderReal), | ||
| 75 | + }, | ||
| 76 | + map[string]interface{}{ | ||
| 77 | + "id": domain.OrderTypeBestShop, | ||
| 78 | + "name": domain.GetOrderBaseTypeName(domain.OrderTypeBestShop), | ||
| 79 | + }, | ||
| 80 | + } | ||
| 81 | + c.ResponseData(resp) | ||
| 82 | +} |
| @@ -31,8 +31,8 @@ func (c *OrderDividendController) Prepare() { | @@ -31,8 +31,8 @@ func (c *OrderDividendController) Prepare() { | ||
| 31 | //PageListOrderDividend 获取实发订单分红列表 | 31 | //PageListOrderDividend 获取实发订单分红列表 |
| 32 | func (c *OrderDividendController) PageListOrderDividend() { | 32 | func (c *OrderDividendController) PageListOrderDividend() { |
| 33 | type Parameter struct { | 33 | type Parameter struct { |
| 34 | - SearchText string `json:"searchText"` | ||
| 35 | - Partner int64 `json:"partner"` | 34 | + SearchWord string `json:"searchWord"` |
| 35 | + OrderType int `json:"orderType"` | ||
| 36 | PageSize int `json:"pageSize"` | 36 | PageSize int `json:"pageSize"` |
| 37 | PageNumber int `json:"pageNumber"` | 37 | PageNumber int `json:"pageNumber"` |
| 38 | } | 38 | } |
| @@ -45,6 +45,12 @@ func (c *OrderDividendController) PageListOrderDividend() { | @@ -45,6 +45,12 @@ func (c *OrderDividendController) PageListOrderDividend() { | ||
| 45 | c.ResponseError(errors.New("json数据解析失败")) | 45 | c.ResponseError(errors.New("json数据解析失败")) |
| 46 | return | 46 | return |
| 47 | } | 47 | } |
| 48 | + if !(param.OrderType == 0 || | ||
| 49 | + param.OrderType == domain.OrderReal || | ||
| 50 | + param.OrderType == domain.OrderTypeBestShop) { | ||
| 51 | + c.ResponseError(errors.New("参数异常")) | ||
| 52 | + return | ||
| 53 | + } | ||
| 48 | if param.PageNumber == 0 { | 54 | if param.PageNumber == 0 { |
| 49 | param.PageNumber = 1 | 55 | param.PageNumber = 1 |
| 50 | } | 56 | } |
| @@ -53,10 +59,9 @@ func (c *OrderDividendController) PageListOrderDividend() { | @@ -53,10 +59,9 @@ func (c *OrderDividendController) PageListOrderDividend() { | ||
| 53 | } | 59 | } |
| 54 | companyId := c.GetUserCompany() | 60 | companyId := c.GetUserCompany() |
| 55 | orderSrv := orderService.NewOrderInfoService(nil) | 61 | orderSrv := orderService.NewOrderInfoService(nil) |
| 56 | - orderinfos, cnt, err := orderSrv.PageListOrderBase(orderQuery.ListOrderBaseQuery{ | ||
| 57 | - PartnerId: param.Partner, | ||
| 58 | - DeliveryCode: param.SearchText, | ||
| 59 | - OrderType: domain.OrderReal, | 62 | + resp, cnt, err := orderSrv.PageListOrderBonus(orderQuery.ListOrderBonusQuery{ |
| 63 | + OrderType: param.OrderType, | ||
| 64 | + PartnerOrCode: param.SearchWord, | ||
| 60 | Limit: param.PageSize, | 65 | Limit: param.PageSize, |
| 61 | Offset: (param.PageNumber - 1) * param.PageSize, | 66 | Offset: (param.PageNumber - 1) * param.PageSize, |
| 62 | CompanyId: companyId, | 67 | CompanyId: companyId, |
| @@ -65,26 +70,7 @@ func (c *OrderDividendController) PageListOrderDividend() { | @@ -65,26 +70,7 @@ func (c *OrderDividendController) PageListOrderDividend() { | ||
| 65 | c.ResponseError(err) | 70 | c.ResponseError(err) |
| 66 | return | 71 | return |
| 67 | } | 72 | } |
| 68 | - rsp := []map[string]interface{}{} | ||
| 69 | - for i := range orderinfos { | ||
| 70 | - orderinfo := orderinfos[i] | ||
| 71 | - m := map[string]interface{}{ | ||
| 72 | - "updateTime": orderinfo.UpdateTime.Local().Format("2006-01-02 15:04:05"), | ||
| 73 | - "id": orderinfo.Id, | ||
| 74 | - "shipmentsId": orderinfo.DeliveryCode, | ||
| 75 | - "partner": orderinfo.PartnerInfo.PartnerName, | ||
| 76 | - "dividendsReceivable": orderinfo.OrderCompute.PlanPartnerBonus, | ||
| 77 | - "dividendSpending": orderinfo.OrderCompute.PartnerBonusExpense, | ||
| 78 | - "receiveDividends": orderinfo.OrderCompute.PartnerBonusHas, | ||
| 79 | - "uncollectedDividends": orderinfo.OrderCompute.PartnerBonusNot, | ||
| 80 | - "stateOfPayment": orderinfo.BonusStatus, | ||
| 81 | - } | ||
| 82 | - if orderinfo.OrderCompute.UsePartnerBonus >= 0 { | ||
| 83 | - m["dividendsReceivable"] = orderinfo.OrderCompute.UsePartnerBonus | ||
| 84 | - } | ||
| 85 | - rsp = append(rsp, m) | ||
| 86 | - } | ||
| 87 | - c.ResponsePageList(rsp, cnt, param.PageNumber) | 73 | + c.ResponsePageList(resp, cnt, param.PageNumber) |
| 88 | return | 74 | return |
| 89 | } | 75 | } |
| 90 | 76 | ||
| @@ -269,3 +255,147 @@ func (c *OrderDividendController) EditOrderDividend() { | @@ -269,3 +255,147 @@ func (c *OrderDividendController) EditOrderDividend() { | ||
| 269 | c.ResponseData(nil) | 255 | c.ResponseData(nil) |
| 270 | return | 256 | return |
| 271 | } | 257 | } |
| 258 | + | ||
| 259 | +//OrderDividendDetailForBestshop 海鲜干货的订单分红详情 | ||
| 260 | +func (c *OrderDividendController) OrderDividendDetailForBestshop() { | ||
| 261 | + type Parameter struct { | ||
| 262 | + Id string `json:"id"` | ||
| 263 | + } | ||
| 264 | + var ( | ||
| 265 | + param Parameter | ||
| 266 | + err error | ||
| 267 | + ) | ||
| 268 | + if err = c.BindJsonData(¶m); err != nil { | ||
| 269 | + logs.Error(err) | ||
| 270 | + c.ResponseError(errors.New("json数据解析失败")) | ||
| 271 | + return | ||
| 272 | + } | ||
| 273 | + orderid, _ := strconv.ParseInt(param.Id, 10, 64) | ||
| 274 | + if orderid == 0 { | ||
| 275 | + c.ResponseError(errors.New("参数错误")) | ||
| 276 | + return | ||
| 277 | + } | ||
| 278 | + companyId := c.GetUserCompany() | ||
| 279 | + orderSrv := orderService.NewOrderInfoService(nil) | ||
| 280 | + respData, err := orderSrv.GetOrderBestshopInfoWithBonus(orderid, companyId) | ||
| 281 | + if err != nil { | ||
| 282 | + c.ResponseError(err) | ||
| 283 | + return | ||
| 284 | + } | ||
| 285 | + c.ResponseData(respData) | ||
| 286 | + return | ||
| 287 | +} | ||
| 288 | + | ||
| 289 | +//EditOrderForBestshop 编辑海鲜干货的订单 中的 货品数量和分红比例 | ||
| 290 | +func (c *OrderDividendController) EditOrderDividendForBestshop() { | ||
| 291 | + type Parameter struct { | ||
| 292 | + State int `json:"state"` | ||
| 293 | + OrderId string `json:"orderId"` | ||
| 294 | + ProductId string `json:"productId"` | ||
| 295 | + Reason string `json:"reason"` | ||
| 296 | + GoodNumber int `json:"goodNumber"` | ||
| 297 | + PartnerBonusPercent float64 `json:"partnerBonusPercent"` | ||
| 298 | + } | ||
| 299 | + var ( | ||
| 300 | + param Parameter | ||
| 301 | + err error | ||
| 302 | + ) | ||
| 303 | + if err = c.BindJsonData(¶m); err != nil { | ||
| 304 | + logs.Error(err) | ||
| 305 | + c.ResponseError(errors.New("json数据解析失败")) | ||
| 306 | + return | ||
| 307 | + } | ||
| 308 | + orderid, _ := strconv.ParseInt(param.OrderId, 10, 64) | ||
| 309 | + if orderid == 0 { | ||
| 310 | + c.ResponseError(errors.New("参数错误")) | ||
| 311 | + return | ||
| 312 | + } | ||
| 313 | + productId, _ := strconv.ParseInt(param.ProductId, 10, 64) | ||
| 314 | + if productId == 0 { | ||
| 315 | + c.ResponseError(errors.New("参数错误")) | ||
| 316 | + return | ||
| 317 | + } | ||
| 318 | + adminId := c.GetUserId() | ||
| 319 | + orderSrv := orderService.NewOrderInfoService(nil) | ||
| 320 | + | ||
| 321 | + switch param.State { | ||
| 322 | + case 1: | ||
| 323 | + err = orderSrv.UpdateBonusByGoodNumber(orderid, productId, adminId, param.GoodNumber, param.Reason) | ||
| 324 | + case 2: | ||
| 325 | + err = orderSrv.UpdateBonusByPartnerBonusPercent(orderid, productId, adminId, param.PartnerBonusPercent, param.Reason) | ||
| 326 | + } | ||
| 327 | + if err != nil { | ||
| 328 | + c.ResponseError(err) | ||
| 329 | + return | ||
| 330 | + } | ||
| 331 | + c.ResponseData(nil) | ||
| 332 | + return | ||
| 333 | +} | ||
| 334 | + | ||
| 335 | +//PayOrderGoodBonusForBestshop 支付海鲜干货订单中的分红 | ||
| 336 | +func (c *OrderDividendController) PayOrderGoodBonusForBestshop() { | ||
| 337 | + type Parameter struct { | ||
| 338 | + OrderId string `json:"orderId"` | ||
| 339 | + ProductId string `json:"productId"` | ||
| 340 | + } | ||
| 341 | + var ( | ||
| 342 | + param Parameter | ||
| 343 | + err error | ||
| 344 | + ) | ||
| 345 | + if err = c.BindJsonData(¶m); err != nil { | ||
| 346 | + logs.Error(err) | ||
| 347 | + c.ResponseError(errors.New("json数据解析失败")) | ||
| 348 | + return | ||
| 349 | + } | ||
| 350 | + orderid, _ := strconv.ParseInt(param.OrderId, 10, 64) | ||
| 351 | + if orderid == 0 { | ||
| 352 | + c.ResponseError(errors.New("参数错误")) | ||
| 353 | + return | ||
| 354 | + } | ||
| 355 | + productId, _ := strconv.ParseInt(param.ProductId, 10, 64) | ||
| 356 | + if productId == 0 { | ||
| 357 | + c.ResponseError(errors.New("参数错误")) | ||
| 358 | + return | ||
| 359 | + } | ||
| 360 | + adminId := c.GetUserId() | ||
| 361 | + orderSrv := orderService.NewOrderInfoService(nil) | ||
| 362 | + err = orderSrv.PayPartnerBonusWithOrderBestshop(orderid, productId, adminId) | ||
| 363 | + if err != nil { | ||
| 364 | + c.ResponseError(err) | ||
| 365 | + return | ||
| 366 | + } | ||
| 367 | + c.ResponseData(nil) | ||
| 368 | + return | ||
| 369 | +} | ||
| 370 | + | ||
| 371 | +//EditOrderRemarkBonusForBestshop 编辑海鲜干货订单中的备注 | ||
| 372 | +func (c *OrderDividendController) EditOrderRemarkBonusForBestshop() { | ||
| 373 | + type Parameter struct { | ||
| 374 | + OrderId string `json:"orderId"` | ||
| 375 | + Remark string `json:"remark"` | ||
| 376 | + } | ||
| 377 | + var ( | ||
| 378 | + param Parameter | ||
| 379 | + err error | ||
| 380 | + ) | ||
| 381 | + if err = c.BindJsonData(¶m); err != nil { | ||
| 382 | + logs.Error(err) | ||
| 383 | + c.ResponseError(errors.New("json数据解析失败")) | ||
| 384 | + return | ||
| 385 | + } | ||
| 386 | + orderid, _ := strconv.ParseInt(param.OrderId, 10, 64) | ||
| 387 | + if orderid == 0 { | ||
| 388 | + c.ResponseError(errors.New("参数错误")) | ||
| 389 | + return | ||
| 390 | + } | ||
| 391 | + | ||
| 392 | + adminId := c.GetUserId() | ||
| 393 | + orderSrv := orderService.NewOrderInfoService(nil) | ||
| 394 | + err = orderSrv.UpdateOrderRemarkBonus(orderid, adminId, param.Remark) | ||
| 395 | + if err != nil { | ||
| 396 | + c.ResponseError(err) | ||
| 397 | + return | ||
| 398 | + } | ||
| 399 | + c.ResponseData(nil) | ||
| 400 | + return | ||
| 401 | +} |
| @@ -68,13 +68,15 @@ func (c *PartnerInfoController) CreatePartnerInfo() { | @@ -68,13 +68,15 @@ func (c *PartnerInfoController) CreatePartnerInfo() { | ||
| 68 | Status: param.State, | 68 | Status: param.State, |
| 69 | PartnerCategory: param.PartnerType, | 69 | PartnerCategory: param.PartnerType, |
| 70 | CooperateTime: cooperateTime, | 70 | CooperateTime: cooperateTime, |
| 71 | - Salesman: []domain.Salesman{ | 71 | + CompanyId: companyId, |
| 72 | + } | ||
| 73 | + if len(param.SalesmanName) > 0 || len(param.Phone) > 0 { | ||
| 74 | + cmd.Salesman = []domain.Salesman{ | ||
| 72 | domain.Salesman{ | 75 | domain.Salesman{ |
| 73 | Name: param.SalesmanName, | 76 | Name: param.SalesmanName, |
| 74 | Telephone: param.Phone, | 77 | Telephone: param.Phone, |
| 75 | }, | 78 | }, |
| 76 | - }, | ||
| 77 | - CompanyId: companyId, | 79 | + } |
| 78 | } | 80 | } |
| 79 | if len(param.Area) > 0 { | 81 | if len(param.Area) > 0 { |
| 80 | cmd.RegionInfo = &domain.RegionInfo{ | 82 | cmd.RegionInfo = &domain.RegionInfo{ |
| @@ -29,6 +29,10 @@ func init() { | @@ -29,6 +29,10 @@ func init() { | ||
| 29 | beego.NSRouter("/list", &controllers.OrderDividendController{}, "POST:PageListOrderDividend"), | 29 | beego.NSRouter("/list", &controllers.OrderDividendController{}, "POST:PageListOrderDividend"), |
| 30 | beego.NSRouter("/edit", &controllers.OrderDividendController{}, "POST:EditOrderDividend"), | 30 | beego.NSRouter("/edit", &controllers.OrderDividendController{}, "POST:EditOrderDividend"), |
| 31 | beego.NSRouter("/detail", &controllers.OrderDividendController{}, "POST:OrderDividendDetail"), | 31 | beego.NSRouter("/detail", &controllers.OrderDividendController{}, "POST:OrderDividendDetail"), |
| 32 | + beego.NSRouter("/mini-program/detail", &controllers.OrderDividendController{}, "POST:OrderDividendDetailForBestshop"), | ||
| 33 | + beego.NSRouter("/mini-program/modify", &controllers.OrderDividendController{}, "POST:EditOrderDividendForBestshop"), | ||
| 34 | + beego.NSRouter("/mini-program/payDividends", &controllers.OrderDividendController{}, "POST:PayOrderGoodBonusForBestshop"), | ||
| 35 | + beego.NSRouter("/mini-program/remarks", &controllers.OrderDividendController{}, "POST:EditOrderRemarkBonusForBestshop"), | ||
| 32 | 36 | ||
| 33 | beego.NSRouter("/business/detail", &controllers.BusinessBonusController{}, "POST:GetBusinessBonus"), | 37 | beego.NSRouter("/business/detail", &controllers.BusinessBonusController{}, "POST:GetBusinessBonus"), |
| 34 | beego.NSRouter("/business/edit", &controllers.BusinessBonusController{}, "POST:UpdateBusinessBonus"), | 38 | beego.NSRouter("/business/edit", &controllers.BusinessBonusController{}, "POST:UpdateBusinessBonus"), |
| @@ -50,6 +54,7 @@ func init() { | @@ -50,6 +54,7 @@ func init() { | ||
| 50 | beego.NSNamespace("/common", | 54 | beego.NSNamespace("/common", |
| 51 | beego.NSRouter("/partner", &controllers.CommonController{}, "POST:GetPartnerList"), | 55 | beego.NSRouter("/partner", &controllers.CommonController{}, "POST:GetPartnerList"), |
| 52 | beego.NSRouter("/partnerType", &controllers.CommonController{}, "POST:GetPartnerCategory"), | 56 | beego.NSRouter("/partnerType", &controllers.CommonController{}, "POST:GetPartnerCategory"), |
| 57 | + beego.NSRouter("/orderType", &controllers.CommonController{}, "POST:GetOrderType"), | ||
| 53 | ), | 58 | ), |
| 54 | 59 | ||
| 55 | beego.NSNamespace("/enterprises", | 60 | beego.NSNamespace("/enterprises", |
pkg/port/consumer/configs/config.go
0 → 100644
| 1 | +package configs | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/constant" | ||
| 5 | +) | ||
| 6 | + | ||
| 7 | +type MqConfig struct { | ||
| 8 | + Servers []string `json:"servers"` | ||
| 9 | + ConsumerId string `json:"consumerGroup"` | ||
| 10 | +} | ||
| 11 | + | ||
| 12 | +var Cfg = MqConfig{ | ||
| 13 | + Servers: constant.KafkaCfg.Servers, | ||
| 14 | + ConsumerId: constant.KafkaCfg.ConsumerId, | ||
| 15 | +} | ||
| 16 | + | ||
| 17 | +// "192.168.190.136:9092", | ||
| 18 | +// "106.52.15.41:9092" |
pkg/port/consumer/consumer.go
0 → 100644
| 1 | +package consumer | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "context" | ||
| 5 | + "errors" | ||
| 6 | + "fmt" | ||
| 7 | + "time" | ||
| 8 | + | ||
| 9 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/port/consumer/configs" | ||
| 10 | + | ||
| 11 | + "github.com/Shopify/sarama" | ||
| 12 | + "github.com/astaxie/beego/logs" | ||
| 13 | + cluster "github.com/bsm/sarama-cluster" | ||
| 14 | +) | ||
| 15 | + | ||
| 16 | +//MessageConsumer 消息消费者 | ||
| 17 | +type MessageConsumer struct { | ||
| 18 | + ready chan struct{} | ||
| 19 | + kafkaHosts []string | ||
| 20 | + groupId string | ||
| 21 | + topics []string | ||
| 22 | + topicsHandles map[string]TopicHandle | ||
| 23 | + // beforeHandles []TopicHandle | ||
| 24 | + // afterHandles []TopicHandle | ||
| 25 | +} | ||
| 26 | + | ||
| 27 | +//实现对应的接口 | ||
| 28 | +var _ sarama.ConsumerGroupHandler = (*MessageConsumer)(nil) | ||
| 29 | + | ||
| 30 | +func (c *MessageConsumer) Setup(groupSession sarama.ConsumerGroupSession) error { | ||
| 31 | + close(c.ready) | ||
| 32 | + return nil | ||
| 33 | +} | ||
| 34 | + | ||
| 35 | +func (c *MessageConsumer) Cleanup(groupSession sarama.ConsumerGroupSession) error { | ||
| 36 | + return nil | ||
| 37 | +} | ||
| 38 | + | ||
| 39 | +func (c *MessageConsumer) ConsumeClaim(groupSession sarama.ConsumerGroupSession, | ||
| 40 | + groupClaim sarama.ConsumerGroupClaim) error { | ||
| 41 | + var ( | ||
| 42 | + topicHandle TopicHandle | ||
| 43 | + err error | ||
| 44 | + ) | ||
| 45 | + for message := range groupClaim.Messages() { | ||
| 46 | + logs.Debug("Done Message claimed: timestamp = %v, topic = %s offset = %v value = %v \n", | ||
| 47 | + message.Timestamp, message.Topic, message.Offset, string(message.Value)) | ||
| 48 | + if topicHandle, err = c.FindTopichandle(groupClaim.Topic()); err != nil { | ||
| 49 | + logs.Error("FindTopichandle err:%s \n", err) | ||
| 50 | + continue | ||
| 51 | + } | ||
| 52 | + if err = topicHandle(message); err != nil { | ||
| 53 | + logs.Error("Message claimed: kafka消息处理错误 topic =", message.Topic, message.Offset, err) | ||
| 54 | + } | ||
| 55 | + groupSession.MarkMessage(message, "") | ||
| 56 | + } | ||
| 57 | + return nil | ||
| 58 | +} | ||
| 59 | + | ||
| 60 | +func (c *MessageConsumer) FindTopichandle(topic string) (TopicHandle, error) { | ||
| 61 | + if v, ok := c.topicsHandles[topic]; ok { | ||
| 62 | + return v, nil | ||
| 63 | + } | ||
| 64 | + return nil, errors.New("TopicHandle not found") | ||
| 65 | +} | ||
| 66 | + | ||
| 67 | +type Runer struct { | ||
| 68 | + msgConsumer *MessageConsumer | ||
| 69 | + consumerGroup sarama.ConsumerGroup | ||
| 70 | + Consumer *cluster.Consumer | ||
| 71 | +} | ||
| 72 | + | ||
| 73 | +func NewRuner() *Runer { | ||
| 74 | + topics := []string{} | ||
| 75 | + for key := range TopicHandleRouters { | ||
| 76 | + topics = append(topics, key) | ||
| 77 | + } | ||
| 78 | + r := &Runer{ | ||
| 79 | + msgConsumer: &MessageConsumer{ | ||
| 80 | + ready: make(chan struct{}), | ||
| 81 | + kafkaHosts: configs.Cfg.Servers, | ||
| 82 | + groupId: configs.Cfg.ConsumerId, | ||
| 83 | + topicsHandles: TopicHandleRouters, | ||
| 84 | + topics: topics, | ||
| 85 | + }, | ||
| 86 | + } | ||
| 87 | + logs.Debug("kafka_host=%v; topic=%v;groupid=%s ", r.msgConsumer.kafkaHosts, | ||
| 88 | + r.msgConsumer.topics, r.msgConsumer.groupId) | ||
| 89 | + return r | ||
| 90 | +} | ||
| 91 | + | ||
| 92 | +func (r *Runer) InitConsumer() error { | ||
| 93 | + config := sarama.NewConfig() | ||
| 94 | + //config.Consumer.Group.Rebalance.Strategy = sarama.BalanceStrategyRoundRobin | ||
| 95 | + config.Consumer.Offsets.Initial = sarama.OffsetNewest | ||
| 96 | + config.Version = sarama.V0_10_2_1 | ||
| 97 | + if err := config.Validate(); err != nil { | ||
| 98 | + msg := fmt.Sprintf("Kafka producer config invalidate. config: %v. err: %v", configs.Cfg, err) | ||
| 99 | + logs.Error(msg) | ||
| 100 | + panic(msg) | ||
| 101 | + } | ||
| 102 | + | ||
| 103 | + consumerGroup, err := sarama.NewConsumerGroup(r.msgConsumer.kafkaHosts, r.msgConsumer.groupId, config) | ||
| 104 | + if err != nil { | ||
| 105 | + return err | ||
| 106 | + } | ||
| 107 | + r.consumerGroup = consumerGroup | ||
| 108 | + return nil | ||
| 109 | +} | ||
| 110 | + | ||
| 111 | +// func (r *Runer) InitConsumer() error { | ||
| 112 | +// clusterCfg := cluster.NewConfig() | ||
| 113 | +// clusterCfg.Consumer.Return.Errors = true | ||
| 114 | +// clusterCfg.Consumer.Offsets.Initial = sarama.OffsetOldest | ||
| 115 | +// clusterCfg.Group.Return.Notifications = true | ||
| 116 | +// clusterCfg.Version = sarama.V0_10_2_1 | ||
| 117 | +// // khosts := []string{"192.168.0.252:9092", "192.168.0.251:9092", "192.168.0.250:9092"} | ||
| 118 | +// // groupid := "partnermg_dev" | ||
| 119 | +// // topic := []string{"topic_test"} | ||
| 120 | +// logs.Debug(r.msgConsumer.kafkaHosts, r.msgConsumer.groupId, r.msgConsumer.topics) | ||
| 121 | +// consumer, err := cluster.NewConsumer(r.msgConsumer.kafkaHosts, r.msgConsumer.groupId, r.msgConsumer.topics, clusterCfg) | ||
| 122 | +// // consumer, err := cluster.NewConsumer(khosts, groupid, topic, clusterCfg) | ||
| 123 | +// if err != nil { | ||
| 124 | +// msg := fmt.Sprintf("Create kafka consumer error: %v. config: %v", err, clusterCfg) | ||
| 125 | +// logs.Error(msg) | ||
| 126 | +// panic(msg) | ||
| 127 | +// } | ||
| 128 | +// r.Consumer = consumer | ||
| 129 | +// return nil | ||
| 130 | +// } | ||
| 131 | + | ||
| 132 | +func (r *Runer) Start(ctx context.Context) { | ||
| 133 | + defer func() { | ||
| 134 | + if e := recover(); e != nil { | ||
| 135 | + logs.Error(e) | ||
| 136 | + } | ||
| 137 | + }() | ||
| 138 | + if len(r.msgConsumer.topics) == 0 { | ||
| 139 | + logs.Error("there has no topics") | ||
| 140 | + return | ||
| 141 | + } | ||
| 142 | + for { | ||
| 143 | + select { | ||
| 144 | + case <-ctx.Done(): | ||
| 145 | + logs.Warning("ctx cancel;consumerGroup.Close()") | ||
| 146 | + r.consumerGroup.Close() | ||
| 147 | + return | ||
| 148 | + default: | ||
| 149 | + if err := r.consumerGroup.Consume(ctx, r.msgConsumer.topics, r.msgConsumer); err != nil { | ||
| 150 | + logs.Error("consumerGroup err:%s \n", err) | ||
| 151 | + //等待重试 | ||
| 152 | + timer := time.NewTimer(5 * time.Second) | ||
| 153 | + <-timer.C | ||
| 154 | + } | ||
| 155 | + r.msgConsumer.ready = make(chan struct{}) | ||
| 156 | + } | ||
| 157 | + | ||
| 158 | + } | ||
| 159 | +} | ||
| 160 | + | ||
| 161 | +// func (r *Runer) Start(ctx context.Context) { | ||
| 162 | +// for { | ||
| 163 | +// select { | ||
| 164 | +// case msg, more := <-r.Consumer.Messages(): | ||
| 165 | +// if more { | ||
| 166 | +// logs.Info("Partition:%d, Offset:%d, Key:%s, Value:%s Timestamp:%s\n", msg.Partition, msg.Offset, string(msg.Key), string(msg.Value), msg.Timestamp) | ||
| 167 | +// r.Consumer.MarkOffset(msg, "") // mark message as processed | ||
| 168 | +// } | ||
| 169 | +// case err, more := <-r.Consumer.Errors(): | ||
| 170 | +// if more { | ||
| 171 | +// logs.Info("Kafka consumer error: %v", err.Error()) | ||
| 172 | +// } | ||
| 173 | +// case ntf, more := <-r.Consumer.Notifications(): | ||
| 174 | +// if more { | ||
| 175 | +// logs.Info("Kafka consumer rebalance: %v", ntf) | ||
| 176 | +// } | ||
| 177 | +// case <-ctx.Done(): | ||
| 178 | +// logs.Info("Stop consumer server...") | ||
| 179 | +// r.Consumer.Close() | ||
| 180 | +// return | ||
| 181 | +// } | ||
| 182 | +// } | ||
| 183 | +// } | ||
| 184 | + | ||
| 185 | +func (r *Runer) IsReady() <-chan struct{} { | ||
| 186 | + return r.msgConsumer.ready | ||
| 187 | +} |
pkg/port/consumer/handles/messageValue.go
0 → 100644
pkg/port/consumer/handles/xiangmi.go
0 → 100644
| 1 | +package handles | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "encoding/json" | ||
| 5 | + "fmt" | ||
| 6 | + | ||
| 7 | + "github.com/Shopify/sarama" | ||
| 8 | + "github.com/astaxie/beego/logs" | ||
| 9 | + syncOrderCmd "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/syncOrder/command" | ||
| 10 | + syncOrderSrv "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/application/syncOrder/service" | ||
| 11 | +) | ||
| 12 | + | ||
| 13 | +func DataFromXiangMi(message *sarama.ConsumerMessage) error { | ||
| 14 | + logs.Info("Done Message claimed: timestamp = %v, topic = %s offset = %v value = %v \n", | ||
| 15 | + message.Timestamp, message.Topic, message.Offset, string(message.Value)) | ||
| 16 | + var ( | ||
| 17 | + msgData DataFromMessage | ||
| 18 | + err error | ||
| 19 | + ) | ||
| 20 | + err = json.Unmarshal(message.Value, &msgData) | ||
| 21 | + if err != nil { | ||
| 22 | + return fmt.Errorf("[Consumer][SyncBestshopOrder] 解析kafka数据失败;%s", err) | ||
| 23 | + } | ||
| 24 | + dataAction := msgData.Module + "/" + msgData.Action | ||
| 25 | + switch dataAction { | ||
| 26 | + case "xiangmi.order/ship": | ||
| 27 | + err = syncBestshopOrder(msgData.Data) | ||
| 28 | + if err != nil { | ||
| 29 | + e := fmt.Errorf("[Consumer][SyncBestshopOrder] %s", err) | ||
| 30 | + return e | ||
| 31 | + } | ||
| 32 | + default: | ||
| 33 | + logs.Error("未找到执行动作:Module=%s,Action=%s", msgData.Module, msgData.Action) | ||
| 34 | + } | ||
| 35 | + return nil | ||
| 36 | +} | ||
| 37 | + | ||
| 38 | +//SyncBestshopOrder 同步 | ||
| 39 | +func syncBestshopOrder(data []byte) error { | ||
| 40 | + var ( | ||
| 41 | + cmd syncOrderCmd.CreateOrderFromBestshop | ||
| 42 | + err error | ||
| 43 | + ) | ||
| 44 | + err = json.Unmarshal(data, &cmd) | ||
| 45 | + if err != nil { | ||
| 46 | + return fmt.Errorf("[Consumer][syncBestshopOrder] 解析kafka数据失败;%s", err) | ||
| 47 | + } | ||
| 48 | + if cmd.PartnerId <= 0 { | ||
| 49 | + logs.Info("[Consumer][syncBestshopOrder] PartnerId<=0 ,不处理消息") | ||
| 50 | + return nil | ||
| 51 | + } | ||
| 52 | + srv := syncOrderSrv.NewOrderInfoService(nil) | ||
| 53 | + err = srv.SyncOrderFromBestshop(cmd) | ||
| 54 | + if err != nil { | ||
| 55 | + e := fmt.Errorf("[Consumer][syncBestshopOrder] %s", err) | ||
| 56 | + return e | ||
| 57 | + } | ||
| 58 | + return err | ||
| 59 | +} |
pkg/port/consumer/topic_handle_router.go
0 → 100644
| 1 | +package consumer | ||
| 2 | + | ||
| 3 | +import ( | ||
| 4 | + "os" | ||
| 5 | + | ||
| 6 | + "github.com/Shopify/sarama" | ||
| 7 | + "gitlab.fjmaimaimai.com/mmm-go/partnermg/pkg/port/consumer/handles" | ||
| 8 | +) | ||
| 9 | + | ||
| 10 | +//TopicHandle 处理kafka中得消息 | ||
| 11 | +type TopicHandle func(*sarama.ConsumerMessage) error | ||
| 12 | + | ||
| 13 | +//TopicHandleRouters 根据topic区分消息并进行处理 | ||
| 14 | +var TopicHandleRouters = map[string]TopicHandle{ | ||
| 15 | + // "topic_test": func(message *sarama.ConsumerMessage) error { | ||
| 16 | + // logs.Info("Done Message claimed: timestamp = %v, topic = %s offset = %v value = %v \n", | ||
| 17 | + // message.Timestamp, message.Topic, message.Offset, string(message.Value)) | ||
| 18 | + // return nil | ||
| 19 | + // }, | ||
| 20 | +} | ||
| 21 | + | ||
| 22 | +func init() { | ||
| 23 | + var runEnv string | ||
| 24 | + if os.Getenv("KAFKA_CONSUMER_ID") != "" { | ||
| 25 | + runEnv = os.Getenv("KAFKA_CONSUMER_ID") | ||
| 26 | + } | ||
| 27 | + if runEnv == "partnermg_test" { | ||
| 28 | + initHandleRoutersTest() | ||
| 29 | + } | ||
| 30 | + if runEnv == "partnermg_prd" { | ||
| 31 | + initHandleRoutersProd() | ||
| 32 | + } | ||
| 33 | +} | ||
| 34 | + | ||
| 35 | +func initHandleRoutersTest() { | ||
| 36 | + TopicHandleRouters["xiangmi_project_test"] = handles.DataFromXiangMi | ||
| 37 | +} | ||
| 38 | + | ||
| 39 | +func initHandleRoutersProd() { | ||
| 40 | + TopicHandleRouters["xiangmi_project"] = handles.DataFromXiangMi | ||
| 41 | +} |
vendor/github.com/DataDog/zstd/.travis.yml
0 → 100644
| 1 | +dist: xenial | ||
| 2 | +language: go | ||
| 3 | + | ||
| 4 | +go: | ||
| 5 | + - 1.10.x | ||
| 6 | + - 1.11.x | ||
| 7 | + - 1.12.x | ||
| 8 | + | ||
| 9 | +os: | ||
| 10 | + - linux | ||
| 11 | + - osx | ||
| 12 | + | ||
| 13 | +matrix: | ||
| 14 | + include: | ||
| 15 | + name: "Go 1.11.x CentOS 32bits" | ||
| 16 | + language: go | ||
| 17 | + go: 1.11.x | ||
| 18 | + os: linux | ||
| 19 | + services: | ||
| 20 | + - docker | ||
| 21 | + script: | ||
| 22 | + # Please update Go version in travis_test_32 as needed | ||
| 23 | + - "docker run -i -v \"${PWD}:/zstd\" toopher/centos-i386:centos6 /bin/bash -c \"linux32 --32bit i386 /zstd/travis_test_32.sh\"" | ||
| 24 | + | ||
| 25 | +install: | ||
| 26 | + - "wget https://github.com/DataDog/zstd/files/2246767/mr.zip" | ||
| 27 | + - "unzip mr.zip" | ||
| 28 | +script: | ||
| 29 | + - "go build" | ||
| 30 | + - "PAYLOAD=`pwd`/mr go test -v" | ||
| 31 | + - "PAYLOAD=`pwd`/mr go test -bench ." |
vendor/github.com/DataDog/zstd/LICENSE
0 → 100644
| 1 | +Simplified BSD License | ||
| 2 | + | ||
| 3 | +Copyright (c) 2016, Datadog <info@datadoghq.com> | ||
| 4 | +All rights reserved. | ||
| 5 | + | ||
| 6 | +Redistribution and use in source and binary forms, with or without | ||
| 7 | +modification, are permitted provided that the following conditions are met: | ||
| 8 | + | ||
| 9 | + * Redistributions of source code must retain the above copyright notice, | ||
| 10 | + this list of conditions and the following disclaimer. | ||
| 11 | + * Redistributions in binary form must reproduce the above copyright notice, | ||
| 12 | + this list of conditions and the following disclaimer in the documentation | ||
| 13 | + and/or other materials provided with the distribution. | ||
| 14 | + * Neither the name of the copyright holder nor the names of its contributors | ||
| 15 | + may be used to endorse or promote products derived from this software | ||
| 16 | + without specific prior written permission. | ||
| 17 | + | ||
| 18 | +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" | ||
| 19 | +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||
| 20 | +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
| 21 | +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE | ||
| 22 | +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
| 23 | +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR | ||
| 24 | +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER | ||
| 25 | +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | ||
| 26 | +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | ||
| 27 | +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
vendor/github.com/DataDog/zstd/README.md
0 → 100644
| 1 | +# Zstd Go Wrapper | ||
| 2 | + | ||
| 3 | +[C Zstd Homepage](https://github.com/Cyan4973/zstd) | ||
| 4 | + | ||
| 5 | +The current headers and C files are from *v1.3.8* (Commit | ||
| 6 | +[470344d](https://github.com/facebook/zstd/releases/tag/v1.3.8)). | ||
| 7 | + | ||
| 8 | +## Usage | ||
| 9 | + | ||
| 10 | +There are two main APIs: | ||
| 11 | + | ||
| 12 | +* simple Compress/Decompress | ||
| 13 | +* streaming API (io.Reader/io.Writer) | ||
| 14 | + | ||
| 15 | +The compress/decompress APIs mirror that of lz4, while the streaming API was | ||
| 16 | +designed to be a drop-in replacement for zlib. | ||
| 17 | + | ||
| 18 | +### Simple `Compress/Decompress` | ||
| 19 | + | ||
| 20 | + | ||
| 21 | +```go | ||
| 22 | +// Compress compresses the byte array given in src and writes it to dst. | ||
| 23 | +// If you already have a buffer allocated, you can pass it to prevent allocation | ||
| 24 | +// If not, you can pass nil as dst. | ||
| 25 | +// If the buffer is too small, it will be reallocated, resized, and returned bu the function | ||
| 26 | +// If dst is nil, this will allocate the worst case size (CompressBound(src)) | ||
| 27 | +Compress(dst, src []byte) ([]byte, error) | ||
| 28 | +``` | ||
| 29 | + | ||
| 30 | +```go | ||
| 31 | +// CompressLevel is the same as Compress but you can pass another compression level | ||
| 32 | +CompressLevel(dst, src []byte, level int) ([]byte, error) | ||
| 33 | +``` | ||
| 34 | + | ||
| 35 | +```go | ||
| 36 | +// Decompress will decompress your payload into dst. | ||
| 37 | +// If you already have a buffer allocated, you can pass it to prevent allocation | ||
| 38 | +// If not, you can pass nil as dst (allocates a 4*src size as default). | ||
| 39 | +// If the buffer is too small, it will retry 3 times by doubling the dst size | ||
| 40 | +// After max retries, it will switch to the slower stream API to be sure to be able | ||
| 41 | +// to decompress. Currently switches if compression ratio > 4*2**3=32. | ||
| 42 | +Decompress(dst, src []byte) ([]byte, error) | ||
| 43 | +``` | ||
| 44 | + | ||
| 45 | +### Stream API | ||
| 46 | + | ||
| 47 | +```go | ||
| 48 | +// NewWriter creates a new object that can optionally be initialized with | ||
| 49 | +// a precomputed dictionary. If dict is nil, compress without a dictionary. | ||
| 50 | +// The dictionary array should not be changed during the use of this object. | ||
| 51 | +// You MUST CALL Close() to write the last bytes of a zstd stream and free C objects. | ||
| 52 | +NewWriter(w io.Writer) *Writer | ||
| 53 | +NewWriterLevel(w io.Writer, level int) *Writer | ||
| 54 | +NewWriterLevelDict(w io.Writer, level int, dict []byte) *Writer | ||
| 55 | + | ||
| 56 | +// Write compresses the input data and write it to the underlying writer | ||
| 57 | +(w *Writer) Write(p []byte) (int, error) | ||
| 58 | + | ||
| 59 | +// Close flushes the buffer and frees C zstd objects | ||
| 60 | +(w *Writer) Close() error | ||
| 61 | +``` | ||
| 62 | + | ||
| 63 | +```go | ||
| 64 | +// NewReader returns a new io.ReadCloser that will decompress data from the | ||
| 65 | +// underlying reader. If a dictionary is provided to NewReaderDict, it must | ||
| 66 | +// not be modified until Close is called. It is the caller's responsibility | ||
| 67 | +// to call Close, which frees up C objects. | ||
| 68 | +NewReader(r io.Reader) io.ReadCloser | ||
| 69 | +NewReaderDict(r io.Reader, dict []byte) io.ReadCloser | ||
| 70 | +``` | ||
| 71 | + | ||
| 72 | +### Benchmarks (benchmarked with v0.5.0) | ||
| 73 | + | ||
| 74 | +The author of Zstd also wrote lz4. Zstd is intended to occupy a speed/ratio | ||
| 75 | +level similar to what zlib currently provides. In our tests, the can always | ||
| 76 | +be made to be better than zlib by chosing an appropriate level while still | ||
| 77 | +keeping compression and decompression time faster than zlib. | ||
| 78 | + | ||
| 79 | +You can run the benchmarks against your own payloads by using the Go benchmarks tool. | ||
| 80 | +Just export your payload filepath as the `PAYLOAD` environment variable and run the benchmarks: | ||
| 81 | + | ||
| 82 | +```go | ||
| 83 | +go test -bench . | ||
| 84 | +``` | ||
| 85 | + | ||
| 86 | +Compression of a 7Mb pdf zstd (this wrapper) vs [czlib](https://github.com/DataDog/czlib): | ||
| 87 | +``` | ||
| 88 | +BenchmarkCompression 5 221056624 ns/op 67.34 MB/s | ||
| 89 | +BenchmarkDecompression 100 18370416 ns/op 810.32 MB/s | ||
| 90 | + | ||
| 91 | +BenchmarkFzlibCompress 2 610156603 ns/op 24.40 MB/s | ||
| 92 | +BenchmarkFzlibDecompress 20 81195246 ns/op 183.33 MB/s | ||
| 93 | +``` | ||
| 94 | + | ||
| 95 | +Ratio is also better by a margin of ~20%. | ||
| 96 | +Compression speed is always better than zlib on all the payloads we tested; | ||
| 97 | +However, [czlib](https://github.com/DataDog/czlib) has optimisations that make it | ||
| 98 | +faster at decompressiong small payloads: | ||
| 99 | + | ||
| 100 | +``` | ||
| 101 | +Testing with size: 11... czlib: 8.97 MB/s, zstd: 3.26 MB/s | ||
| 102 | +Testing with size: 27... czlib: 23.3 MB/s, zstd: 8.22 MB/s | ||
| 103 | +Testing with size: 62... czlib: 31.6 MB/s, zstd: 19.49 MB/s | ||
| 104 | +Testing with size: 141... czlib: 74.54 MB/s, zstd: 42.55 MB/s | ||
| 105 | +Testing with size: 323... czlib: 155.14 MB/s, zstd: 99.39 MB/s | ||
| 106 | +Testing with size: 739... czlib: 235.9 MB/s, zstd: 216.45 MB/s | ||
| 107 | +Testing with size: 1689... czlib: 116.45 MB/s, zstd: 345.64 MB/s | ||
| 108 | +Testing with size: 3858... czlib: 176.39 MB/s, zstd: 617.56 MB/s | ||
| 109 | +Testing with size: 8811... czlib: 254.11 MB/s, zstd: 824.34 MB/s | ||
| 110 | +Testing with size: 20121... czlib: 197.43 MB/s, zstd: 1339.11 MB/s | ||
| 111 | +Testing with size: 45951... czlib: 201.62 MB/s, zstd: 1951.57 MB/s | ||
| 112 | +``` | ||
| 113 | + | ||
| 114 | +zstd starts to shine with payloads > 1KB | ||
| 115 | + | ||
| 116 | +### Stability - Current state: STABLE | ||
| 117 | + | ||
| 118 | +The C library seems to be pretty stable and according to the author has been tested and fuzzed. | ||
| 119 | + | ||
| 120 | +For the Go wrapper, the test cover most usual cases and we have succesfully tested it on all staging and prod data. |
vendor/github.com/DataDog/zstd/ZSTD_LICENSE
0 → 100644
| 1 | +BSD License | ||
| 2 | + | ||
| 3 | +For Zstandard software | ||
| 4 | + | ||
| 5 | +Copyright (c) 2016-present, Facebook, Inc. All rights reserved. | ||
| 6 | + | ||
| 7 | +Redistribution and use in source and binary forms, with or without modification, | ||
| 8 | +are permitted provided that the following conditions are met: | ||
| 9 | + | ||
| 10 | + * Redistributions of source code must retain the above copyright notice, this | ||
| 11 | + list of conditions and the following disclaimer. | ||
| 12 | + | ||
| 13 | + * Redistributions in binary form must reproduce the above copyright notice, | ||
| 14 | + this list of conditions and the following disclaimer in the documentation | ||
| 15 | + and/or other materials provided with the distribution. | ||
| 16 | + | ||
| 17 | + * Neither the name Facebook nor the names of its contributors may be used to | ||
| 18 | + endorse or promote products derived from this software without specific | ||
| 19 | + prior written permission. | ||
| 20 | + | ||
| 21 | +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND | ||
| 22 | +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
| 23 | +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
| 24 | +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR | ||
| 25 | +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
| 26 | +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
| 27 | +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON | ||
| 28 | +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
| 29 | +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
| 30 | +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
vendor/github.com/DataDog/zstd/bitstream.h
0 → 100644
| 1 | +/* ****************************************************************** | ||
| 2 | + bitstream | ||
| 3 | + Part of FSE library | ||
| 4 | + Copyright (C) 2013-present, Yann Collet. | ||
| 5 | + | ||
| 6 | + BSD 2-Clause License (http://www.opensource.org/licenses/bsd-license.php) | ||
| 7 | + | ||
| 8 | + Redistribution and use in source and binary forms, with or without | ||
| 9 | + modification, are permitted provided that the following conditions are | ||
| 10 | + met: | ||
| 11 | + | ||
| 12 | + * Redistributions of source code must retain the above copyright | ||
| 13 | + notice, this list of conditions and the following disclaimer. | ||
| 14 | + * Redistributions in binary form must reproduce the above | ||
| 15 | + copyright notice, this list of conditions and the following disclaimer | ||
| 16 | + in the documentation and/or other materials provided with the | ||
| 17 | + distribution. | ||
| 18 | + | ||
| 19 | + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | ||
| 20 | + "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | ||
| 21 | + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR | ||
| 22 | + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | ||
| 23 | + OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||
| 24 | + SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | ||
| 25 | + LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, | ||
| 26 | + DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY | ||
| 27 | + THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
| 28 | + (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | ||
| 29 | + OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
| 30 | + | ||
| 31 | + You can contact the author at : | ||
| 32 | + - Source repository : https://github.com/Cyan4973/FiniteStateEntropy | ||
| 33 | +****************************************************************** */ | ||
| 34 | +#ifndef BITSTREAM_H_MODULE | ||
| 35 | +#define BITSTREAM_H_MODULE | ||
| 36 | + | ||
| 37 | +#if defined (__cplusplus) | ||
| 38 | +extern "C" { | ||
| 39 | +#endif | ||
| 40 | + | ||
| 41 | +/* | ||
| 42 | +* This API consists of small unitary functions, which must be inlined for best performance. | ||
| 43 | +* Since link-time-optimization is not available for all compilers, | ||
| 44 | +* these functions are defined into a .h to be included. | ||
| 45 | +*/ | ||
| 46 | + | ||
| 47 | +/*-**************************************** | ||
| 48 | +* Dependencies | ||
| 49 | +******************************************/ | ||
| 50 | +#include "mem.h" /* unaligned access routines */ | ||
| 51 | +#include "debug.h" /* assert(), DEBUGLOG(), RAWLOG() */ | ||
| 52 | +#include "error_private.h" /* error codes and messages */ | ||
| 53 | + | ||
| 54 | + | ||
| 55 | +/*========================================= | ||
| 56 | +* Target specific | ||
| 57 | +=========================================*/ | ||
| 58 | +#if defined(__BMI__) && defined(__GNUC__) | ||
| 59 | +# include <immintrin.h> /* support for bextr (experimental) */ | ||
| 60 | +#endif | ||
| 61 | + | ||
| 62 | +#define STREAM_ACCUMULATOR_MIN_32 25 | ||
| 63 | +#define STREAM_ACCUMULATOR_MIN_64 57 | ||
| 64 | +#define STREAM_ACCUMULATOR_MIN ((U32)(MEM_32bits() ? STREAM_ACCUMULATOR_MIN_32 : STREAM_ACCUMULATOR_MIN_64)) | ||
| 65 | + | ||
| 66 | + | ||
| 67 | +/*-****************************************** | ||
| 68 | +* bitStream encoding API (write forward) | ||
| 69 | +********************************************/ | ||
| 70 | +/* bitStream can mix input from multiple sources. | ||
| 71 | + * A critical property of these streams is that they encode and decode in **reverse** direction. | ||
| 72 | + * So the first bit sequence you add will be the last to be read, like a LIFO stack. | ||
| 73 | + */ | ||
| 74 | +typedef struct { | ||
| 75 | + size_t bitContainer; | ||
| 76 | + unsigned bitPos; | ||
| 77 | + char* startPtr; | ||
| 78 | + char* ptr; | ||
| 79 | + char* endPtr; | ||
| 80 | +} BIT_CStream_t; | ||
| 81 | + | ||
| 82 | +MEM_STATIC size_t BIT_initCStream(BIT_CStream_t* bitC, void* dstBuffer, size_t dstCapacity); | ||
| 83 | +MEM_STATIC void BIT_addBits(BIT_CStream_t* bitC, size_t value, unsigned nbBits); | ||
| 84 | +MEM_STATIC void BIT_flushBits(BIT_CStream_t* bitC); | ||
| 85 | +MEM_STATIC size_t BIT_closeCStream(BIT_CStream_t* bitC); | ||
| 86 | + | ||
| 87 | +/* Start with initCStream, providing the size of buffer to write into. | ||
| 88 | +* bitStream will never write outside of this buffer. | ||
| 89 | +* `dstCapacity` must be >= sizeof(bitD->bitContainer), otherwise @return will be an error code. | ||
| 90 | +* | ||
| 91 | +* bits are first added to a local register. | ||
| 92 | +* Local register is size_t, hence 64-bits on 64-bits systems, or 32-bits on 32-bits systems. | ||
| 93 | +* Writing data into memory is an explicit operation, performed by the flushBits function. | ||
| 94 | +* Hence keep track how many bits are potentially stored into local register to avoid register overflow. | ||
| 95 | +* After a flushBits, a maximum of 7 bits might still be stored into local register. | ||
| 96 | +* | ||
| 97 | +* Avoid storing elements of more than 24 bits if you want compatibility with 32-bits bitstream readers. | ||
| 98 | +* | ||
| 99 | +* Last operation is to close the bitStream. | ||
| 100 | +* The function returns the final size of CStream in bytes. | ||
| 101 | +* If data couldn't fit into `dstBuffer`, it will return a 0 ( == not storable) | ||
| 102 | +*/ | ||
| 103 | + | ||
| 104 | + | ||
| 105 | +/*-******************************************** | ||
| 106 | +* bitStream decoding API (read backward) | ||
| 107 | +**********************************************/ | ||
| 108 | +typedef struct { | ||
| 109 | + size_t bitContainer; | ||
| 110 | + unsigned bitsConsumed; | ||
| 111 | + const char* ptr; | ||
| 112 | + const char* start; | ||
| 113 | + const char* limitPtr; | ||
| 114 | +} BIT_DStream_t; | ||
| 115 | + | ||
| 116 | +typedef enum { BIT_DStream_unfinished = 0, | ||
| 117 | + BIT_DStream_endOfBuffer = 1, | ||
| 118 | + BIT_DStream_completed = 2, | ||
| 119 | + BIT_DStream_overflow = 3 } BIT_DStream_status; /* result of BIT_reloadDStream() */ | ||
| 120 | + /* 1,2,4,8 would be better for bitmap combinations, but slows down performance a bit ... :( */ | ||
| 121 | + | ||
| 122 | +MEM_STATIC size_t BIT_initDStream(BIT_DStream_t* bitD, const void* srcBuffer, size_t srcSize); | ||
| 123 | +MEM_STATIC size_t BIT_readBits(BIT_DStream_t* bitD, unsigned nbBits); | ||
| 124 | +MEM_STATIC BIT_DStream_status BIT_reloadDStream(BIT_DStream_t* bitD); | ||
| 125 | +MEM_STATIC unsigned BIT_endOfDStream(const BIT_DStream_t* bitD); | ||
| 126 | + | ||
| 127 | + | ||
| 128 | +/* Start by invoking BIT_initDStream(). | ||
| 129 | +* A chunk of the bitStream is then stored into a local register. | ||
| 130 | +* Local register size is 64-bits on 64-bits systems, 32-bits on 32-bits systems (size_t). | ||
| 131 | +* You can then retrieve bitFields stored into the local register, **in reverse order**. | ||
| 132 | +* Local register is explicitly reloaded from memory by the BIT_reloadDStream() method. | ||
| 133 | +* A reload guarantee a minimum of ((8*sizeof(bitD->bitContainer))-7) bits when its result is BIT_DStream_unfinished. | ||
| 134 | +* Otherwise, it can be less than that, so proceed accordingly. | ||
| 135 | +* Checking if DStream has reached its end can be performed with BIT_endOfDStream(). | ||
| 136 | +*/ | ||
| 137 | + | ||
| 138 | + | ||
| 139 | +/*-**************************************** | ||
| 140 | +* unsafe API | ||
| 141 | +******************************************/ | ||
| 142 | +MEM_STATIC void BIT_addBitsFast(BIT_CStream_t* bitC, size_t value, unsigned nbBits); | ||
| 143 | +/* faster, but works only if value is "clean", meaning all high bits above nbBits are 0 */ | ||
| 144 | + | ||
| 145 | +MEM_STATIC void BIT_flushBitsFast(BIT_CStream_t* bitC); | ||
| 146 | +/* unsafe version; does not check buffer overflow */ | ||
| 147 | + | ||
| 148 | +MEM_STATIC size_t BIT_readBitsFast(BIT_DStream_t* bitD, unsigned nbBits); | ||
| 149 | +/* faster, but works only if nbBits >= 1 */ | ||
| 150 | + | ||
| 151 | + | ||
| 152 | + | ||
| 153 | +/*-************************************************************** | ||
| 154 | +* Internal functions | ||
| 155 | +****************************************************************/ | ||
| 156 | +MEM_STATIC unsigned BIT_highbit32 (U32 val) | ||
| 157 | +{ | ||
| 158 | + assert(val != 0); | ||
| 159 | + { | ||
| 160 | +# if defined(_MSC_VER) /* Visual */ | ||
| 161 | + unsigned long r=0; | ||
| 162 | + _BitScanReverse ( &r, val ); | ||
| 163 | + return (unsigned) r; | ||
| 164 | +# elif defined(__GNUC__) && (__GNUC__ >= 3) /* Use GCC Intrinsic */ | ||
| 165 | + return 31 - __builtin_clz (val); | ||
| 166 | +# else /* Software version */ | ||
| 167 | + static const unsigned DeBruijnClz[32] = { 0, 9, 1, 10, 13, 21, 2, 29, | ||
| 168 | + 11, 14, 16, 18, 22, 25, 3, 30, | ||
| 169 | + 8, 12, 20, 28, 15, 17, 24, 7, | ||
| 170 | + 19, 27, 23, 6, 26, 5, 4, 31 }; | ||
| 171 | + U32 v = val; | ||
| 172 | + v |= v >> 1; | ||
| 173 | + v |= v >> 2; | ||
| 174 | + v |= v >> 4; | ||
| 175 | + v |= v >> 8; | ||
| 176 | + v |= v >> 16; | ||
| 177 | + return DeBruijnClz[ (U32) (v * 0x07C4ACDDU) >> 27]; | ||
| 178 | +# endif | ||
| 179 | + } | ||
| 180 | +} | ||
| 181 | + | ||
| 182 | +/*===== Local Constants =====*/ | ||
| 183 | +static const unsigned BIT_mask[] = { | ||
| 184 | + 0, 1, 3, 7, 0xF, 0x1F, | ||
| 185 | + 0x3F, 0x7F, 0xFF, 0x1FF, 0x3FF, 0x7FF, | ||
| 186 | + 0xFFF, 0x1FFF, 0x3FFF, 0x7FFF, 0xFFFF, 0x1FFFF, | ||
| 187 | + 0x3FFFF, 0x7FFFF, 0xFFFFF, 0x1FFFFF, 0x3FFFFF, 0x7FFFFF, | ||
| 188 | + 0xFFFFFF, 0x1FFFFFF, 0x3FFFFFF, 0x7FFFFFF, 0xFFFFFFF, 0x1FFFFFFF, | ||
| 189 | + 0x3FFFFFFF, 0x7FFFFFFF}; /* up to 31 bits */ | ||
| 190 | +#define BIT_MASK_SIZE (sizeof(BIT_mask) / sizeof(BIT_mask[0])) | ||
| 191 | + | ||
| 192 | +/*-************************************************************** | ||
| 193 | +* bitStream encoding | ||
| 194 | +****************************************************************/ | ||
| 195 | +/*! BIT_initCStream() : | ||
| 196 | + * `dstCapacity` must be > sizeof(size_t) | ||
| 197 | + * @return : 0 if success, | ||
| 198 | + * otherwise an error code (can be tested using ERR_isError()) */ | ||
| 199 | +MEM_STATIC size_t BIT_initCStream(BIT_CStream_t* bitC, | ||
| 200 | + void* startPtr, size_t dstCapacity) | ||
| 201 | +{ | ||
| 202 | + bitC->bitContainer = 0; | ||
| 203 | + bitC->bitPos = 0; | ||
| 204 | + bitC->startPtr = (char*)startPtr; | ||
| 205 | + bitC->ptr = bitC->startPtr; | ||
| 206 | + bitC->endPtr = bitC->startPtr + dstCapacity - sizeof(bitC->bitContainer); | ||
| 207 | + if (dstCapacity <= sizeof(bitC->bitContainer)) return ERROR(dstSize_tooSmall); | ||
| 208 | + return 0; | ||
| 209 | +} | ||
| 210 | + | ||
| 211 | +/*! BIT_addBits() : | ||
| 212 | + * can add up to 31 bits into `bitC`. | ||
| 213 | + * Note : does not check for register overflow ! */ | ||
| 214 | +MEM_STATIC void BIT_addBits(BIT_CStream_t* bitC, | ||
| 215 | + size_t value, unsigned nbBits) | ||
| 216 | +{ | ||
| 217 | + MEM_STATIC_ASSERT(BIT_MASK_SIZE == 32); | ||
| 218 | + assert(nbBits < BIT_MASK_SIZE); | ||
| 219 | + assert(nbBits + bitC->bitPos < sizeof(bitC->bitContainer) * 8); | ||
| 220 | + bitC->bitContainer |= (value & BIT_mask[nbBits]) << bitC->bitPos; | ||
| 221 | + bitC->bitPos += nbBits; | ||
| 222 | +} | ||
| 223 | + | ||
| 224 | +/*! BIT_addBitsFast() : | ||
| 225 | + * works only if `value` is _clean_, | ||
| 226 | + * meaning all high bits above nbBits are 0 */ | ||
| 227 | +MEM_STATIC void BIT_addBitsFast(BIT_CStream_t* bitC, | ||
| 228 | + size_t value, unsigned nbBits) | ||
| 229 | +{ | ||
| 230 | + assert((value>>nbBits) == 0); | ||
| 231 | + assert(nbBits + bitC->bitPos < sizeof(bitC->bitContainer) * 8); | ||
| 232 | + bitC->bitContainer |= value << bitC->bitPos; | ||
| 233 | + bitC->bitPos += nbBits; | ||
| 234 | +} | ||
| 235 | + | ||
| 236 | +/*! BIT_flushBitsFast() : | ||
| 237 | + * assumption : bitContainer has not overflowed | ||
| 238 | + * unsafe version; does not check buffer overflow */ | ||
| 239 | +MEM_STATIC void BIT_flushBitsFast(BIT_CStream_t* bitC) | ||
| 240 | +{ | ||
| 241 | + size_t const nbBytes = bitC->bitPos >> 3; | ||
| 242 | + assert(bitC->bitPos < sizeof(bitC->bitContainer) * 8); | ||
| 243 | + MEM_writeLEST(bitC->ptr, bitC->bitContainer); | ||
| 244 | + bitC->ptr += nbBytes; | ||
| 245 | + assert(bitC->ptr <= bitC->endPtr); | ||
| 246 | + bitC->bitPos &= 7; | ||
| 247 | + bitC->bitContainer >>= nbBytes*8; | ||
| 248 | +} | ||
| 249 | + | ||
| 250 | +/*! BIT_flushBits() : | ||
| 251 | + * assumption : bitContainer has not overflowed | ||
| 252 | + * safe version; check for buffer overflow, and prevents it. | ||
| 253 | + * note : does not signal buffer overflow. | ||
| 254 | + * overflow will be revealed later on using BIT_closeCStream() */ | ||
| 255 | +MEM_STATIC void BIT_flushBits(BIT_CStream_t* bitC) | ||
| 256 | +{ | ||
| 257 | + size_t const nbBytes = bitC->bitPos >> 3; | ||
| 258 | + assert(bitC->bitPos < sizeof(bitC->bitContainer) * 8); | ||
| 259 | + MEM_writeLEST(bitC->ptr, bitC->bitContainer); | ||
| 260 | + bitC->ptr += nbBytes; | ||
| 261 | + if (bitC->ptr > bitC->endPtr) bitC->ptr = bitC->endPtr; | ||
| 262 | + bitC->bitPos &= 7; | ||
| 263 | + bitC->bitContainer >>= nbBytes*8; | ||
| 264 | +} | ||
| 265 | + | ||
| 266 | +/*! BIT_closeCStream() : | ||
| 267 | + * @return : size of CStream, in bytes, | ||
| 268 | + * or 0 if it could not fit into dstBuffer */ | ||
| 269 | +MEM_STATIC size_t BIT_closeCStream(BIT_CStream_t* bitC) | ||
| 270 | +{ | ||
| 271 | + BIT_addBitsFast(bitC, 1, 1); /* endMark */ | ||
| 272 | + BIT_flushBits(bitC); | ||
| 273 | + if (bitC->ptr >= bitC->endPtr) return 0; /* overflow detected */ | ||
| 274 | + return (bitC->ptr - bitC->startPtr) + (bitC->bitPos > 0); | ||
| 275 | +} | ||
| 276 | + | ||
| 277 | + | ||
| 278 | +/*-******************************************************** | ||
| 279 | +* bitStream decoding | ||
| 280 | +**********************************************************/ | ||
| 281 | +/*! BIT_initDStream() : | ||
| 282 | + * Initialize a BIT_DStream_t. | ||
| 283 | + * `bitD` : a pointer to an already allocated BIT_DStream_t structure. | ||
| 284 | + * `srcSize` must be the *exact* size of the bitStream, in bytes. | ||
| 285 | + * @return : size of stream (== srcSize), or an errorCode if a problem is detected | ||
| 286 | + */ | ||
| 287 | +MEM_STATIC size_t BIT_initDStream(BIT_DStream_t* bitD, const void* srcBuffer, size_t srcSize) | ||
| 288 | +{ | ||
| 289 | + if (srcSize < 1) { memset(bitD, 0, sizeof(*bitD)); return ERROR(srcSize_wrong); } | ||
| 290 | + | ||
| 291 | + bitD->start = (const char*)srcBuffer; | ||
| 292 | + bitD->limitPtr = bitD->start + sizeof(bitD->bitContainer); | ||
| 293 | + | ||
| 294 | + if (srcSize >= sizeof(bitD->bitContainer)) { /* normal case */ | ||
| 295 | + bitD->ptr = (const char*)srcBuffer + srcSize - sizeof(bitD->bitContainer); | ||
| 296 | + bitD->bitContainer = MEM_readLEST(bitD->ptr); | ||
| 297 | + { BYTE const lastByte = ((const BYTE*)srcBuffer)[srcSize-1]; | ||
| 298 | + bitD->bitsConsumed = lastByte ? 8 - BIT_highbit32(lastByte) : 0; /* ensures bitsConsumed is always set */ | ||
| 299 | + if (lastByte == 0) return ERROR(GENERIC); /* endMark not present */ } | ||
| 300 | + } else { | ||
| 301 | + bitD->ptr = bitD->start; | ||
| 302 | + bitD->bitContainer = *(const BYTE*)(bitD->start); | ||
| 303 | + switch(srcSize) | ||
| 304 | + { | ||
| 305 | + case 7: bitD->bitContainer += (size_t)(((const BYTE*)(srcBuffer))[6]) << (sizeof(bitD->bitContainer)*8 - 16); | ||
| 306 | + /* fall-through */ | ||
| 307 | + | ||
| 308 | + case 6: bitD->bitContainer += (size_t)(((const BYTE*)(srcBuffer))[5]) << (sizeof(bitD->bitContainer)*8 - 24); | ||
| 309 | + /* fall-through */ | ||
| 310 | + | ||
| 311 | + case 5: bitD->bitContainer += (size_t)(((const BYTE*)(srcBuffer))[4]) << (sizeof(bitD->bitContainer)*8 - 32); | ||
| 312 | + /* fall-through */ | ||
| 313 | + | ||
| 314 | + case 4: bitD->bitContainer += (size_t)(((const BYTE*)(srcBuffer))[3]) << 24; | ||
| 315 | + /* fall-through */ | ||
| 316 | + | ||
| 317 | + case 3: bitD->bitContainer += (size_t)(((const BYTE*)(srcBuffer))[2]) << 16; | ||
| 318 | + /* fall-through */ | ||
| 319 | + | ||
| 320 | + case 2: bitD->bitContainer += (size_t)(((const BYTE*)(srcBuffer))[1]) << 8; | ||
| 321 | + /* fall-through */ | ||
| 322 | + | ||
| 323 | + default: break; | ||
| 324 | + } | ||
| 325 | + { BYTE const lastByte = ((const BYTE*)srcBuffer)[srcSize-1]; | ||
| 326 | + bitD->bitsConsumed = lastByte ? 8 - BIT_highbit32(lastByte) : 0; | ||
| 327 | + if (lastByte == 0) return ERROR(corruption_detected); /* endMark not present */ | ||
| 328 | + } | ||
| 329 | + bitD->bitsConsumed += (U32)(sizeof(bitD->bitContainer) - srcSize)*8; | ||
| 330 | + } | ||
| 331 | + | ||
| 332 | + return srcSize; | ||
| 333 | +} | ||
| 334 | + | ||
| 335 | +MEM_STATIC size_t BIT_getUpperBits(size_t bitContainer, U32 const start) | ||
| 336 | +{ | ||
| 337 | + return bitContainer >> start; | ||
| 338 | +} | ||
| 339 | + | ||
| 340 | +MEM_STATIC size_t BIT_getMiddleBits(size_t bitContainer, U32 const start, U32 const nbBits) | ||
| 341 | +{ | ||
| 342 | + U32 const regMask = sizeof(bitContainer)*8 - 1; | ||
| 343 | + /* if start > regMask, bitstream is corrupted, and result is undefined */ | ||
| 344 | + assert(nbBits < BIT_MASK_SIZE); | ||
| 345 | + return (bitContainer >> (start & regMask)) & BIT_mask[nbBits]; | ||
| 346 | +} | ||
| 347 | + | ||
| 348 | +MEM_STATIC size_t BIT_getLowerBits(size_t bitContainer, U32 const nbBits) | ||
| 349 | +{ | ||
| 350 | + assert(nbBits < BIT_MASK_SIZE); | ||
| 351 | + return bitContainer & BIT_mask[nbBits]; | ||
| 352 | +} | ||
| 353 | + | ||
| 354 | +/*! BIT_lookBits() : | ||
| 355 | + * Provides next n bits from local register. | ||
| 356 | + * local register is not modified. | ||
| 357 | + * On 32-bits, maxNbBits==24. | ||
| 358 | + * On 64-bits, maxNbBits==56. | ||
| 359 | + * @return : value extracted */ | ||
| 360 | +MEM_STATIC size_t BIT_lookBits(const BIT_DStream_t* bitD, U32 nbBits) | ||
| 361 | +{ | ||
| 362 | + /* arbitrate between double-shift and shift+mask */ | ||
| 363 | +#if 1 | ||
| 364 | + /* if bitD->bitsConsumed + nbBits > sizeof(bitD->bitContainer)*8, | ||
| 365 | + * bitstream is likely corrupted, and result is undefined */ | ||
| 366 | + return BIT_getMiddleBits(bitD->bitContainer, (sizeof(bitD->bitContainer)*8) - bitD->bitsConsumed - nbBits, nbBits); | ||
| 367 | +#else | ||
| 368 | + /* this code path is slower on my os-x laptop */ | ||
| 369 | + U32 const regMask = sizeof(bitD->bitContainer)*8 - 1; | ||
| 370 | + return ((bitD->bitContainer << (bitD->bitsConsumed & regMask)) >> 1) >> ((regMask-nbBits) & regMask); | ||
| 371 | +#endif | ||
| 372 | +} | ||
| 373 | + | ||
| 374 | +/*! BIT_lookBitsFast() : | ||
| 375 | + * unsafe version; only works if nbBits >= 1 */ | ||
| 376 | +MEM_STATIC size_t BIT_lookBitsFast(const BIT_DStream_t* bitD, U32 nbBits) | ||
| 377 | +{ | ||
| 378 | + U32 const regMask = sizeof(bitD->bitContainer)*8 - 1; | ||
| 379 | + assert(nbBits >= 1); | ||
| 380 | + return (bitD->bitContainer << (bitD->bitsConsumed & regMask)) >> (((regMask+1)-nbBits) & regMask); | ||
| 381 | +} | ||
| 382 | + | ||
| 383 | +MEM_STATIC void BIT_skipBits(BIT_DStream_t* bitD, U32 nbBits) | ||
| 384 | +{ | ||
| 385 | + bitD->bitsConsumed += nbBits; | ||
| 386 | +} | ||
| 387 | + | ||
| 388 | +/*! BIT_readBits() : | ||
| 389 | + * Read (consume) next n bits from local register and update. | ||
| 390 | + * Pay attention to not read more than nbBits contained into local register. | ||
| 391 | + * @return : extracted value. */ | ||
| 392 | +MEM_STATIC size_t BIT_readBits(BIT_DStream_t* bitD, unsigned nbBits) | ||
| 393 | +{ | ||
| 394 | + size_t const value = BIT_lookBits(bitD, nbBits); | ||
| 395 | + BIT_skipBits(bitD, nbBits); | ||
| 396 | + return value; | ||
| 397 | +} | ||
| 398 | + | ||
| 399 | +/*! BIT_readBitsFast() : | ||
| 400 | + * unsafe version; only works only if nbBits >= 1 */ | ||
| 401 | +MEM_STATIC size_t BIT_readBitsFast(BIT_DStream_t* bitD, unsigned nbBits) | ||
| 402 | +{ | ||
| 403 | + size_t const value = BIT_lookBitsFast(bitD, nbBits); | ||
| 404 | + assert(nbBits >= 1); | ||
| 405 | + BIT_skipBits(bitD, nbBits); | ||
| 406 | + return value; | ||
| 407 | +} | ||
| 408 | + | ||
| 409 | +/*! BIT_reloadDStream() : | ||
| 410 | + * Refill `bitD` from buffer previously set in BIT_initDStream() . | ||
| 411 | + * This function is safe, it guarantees it will not read beyond src buffer. | ||
| 412 | + * @return : status of `BIT_DStream_t` internal register. | ||
| 413 | + * when status == BIT_DStream_unfinished, internal register is filled with at least 25 or 57 bits */ | ||
| 414 | +MEM_STATIC BIT_DStream_status BIT_reloadDStream(BIT_DStream_t* bitD) | ||
| 415 | +{ | ||
| 416 | + if (bitD->bitsConsumed > (sizeof(bitD->bitContainer)*8)) /* overflow detected, like end of stream */ | ||
| 417 | + return BIT_DStream_overflow; | ||
| 418 | + | ||
| 419 | + if (bitD->ptr >= bitD->limitPtr) { | ||
| 420 | + bitD->ptr -= bitD->bitsConsumed >> 3; | ||
| 421 | + bitD->bitsConsumed &= 7; | ||
| 422 | + bitD->bitContainer = MEM_readLEST(bitD->ptr); | ||
| 423 | + return BIT_DStream_unfinished; | ||
| 424 | + } | ||
| 425 | + if (bitD->ptr == bitD->start) { | ||
| 426 | + if (bitD->bitsConsumed < sizeof(bitD->bitContainer)*8) return BIT_DStream_endOfBuffer; | ||
| 427 | + return BIT_DStream_completed; | ||
| 428 | + } | ||
| 429 | + /* start < ptr < limitPtr */ | ||
| 430 | + { U32 nbBytes = bitD->bitsConsumed >> 3; | ||
| 431 | + BIT_DStream_status result = BIT_DStream_unfinished; | ||
| 432 | + if (bitD->ptr - nbBytes < bitD->start) { | ||
| 433 | + nbBytes = (U32)(bitD->ptr - bitD->start); /* ptr > start */ | ||
| 434 | + result = BIT_DStream_endOfBuffer; | ||
| 435 | + } | ||
| 436 | + bitD->ptr -= nbBytes; | ||
| 437 | + bitD->bitsConsumed -= nbBytes*8; | ||
| 438 | + bitD->bitContainer = MEM_readLEST(bitD->ptr); /* reminder : srcSize > sizeof(bitD->bitContainer), otherwise bitD->ptr == bitD->start */ | ||
| 439 | + return result; | ||
| 440 | + } | ||
| 441 | +} | ||
| 442 | + | ||
| 443 | +/*! BIT_endOfDStream() : | ||
| 444 | + * @return : 1 if DStream has _exactly_ reached its end (all bits consumed). | ||
| 445 | + */ | ||
| 446 | +MEM_STATIC unsigned BIT_endOfDStream(const BIT_DStream_t* DStream) | ||
| 447 | +{ | ||
| 448 | + return ((DStream->ptr == DStream->start) && (DStream->bitsConsumed == sizeof(DStream->bitContainer)*8)); | ||
| 449 | +} | ||
| 450 | + | ||
| 451 | +#if defined (__cplusplus) | ||
| 452 | +} | ||
| 453 | +#endif | ||
| 454 | + | ||
| 455 | +#endif /* BITSTREAM_H_MODULE */ |
vendor/github.com/DataDog/zstd/compiler.h
0 → 100644
| 1 | +/* | ||
| 2 | + * Copyright (c) 2016-present, Yann Collet, Facebook, Inc. | ||
| 3 | + * All rights reserved. | ||
| 4 | + * | ||
| 5 | + * This source code is licensed under both the BSD-style license (found in the | ||
| 6 | + * LICENSE file in the root directory of this source tree) and the GPLv2 (found | ||
| 7 | + * in the COPYING file in the root directory of this source tree). | ||
| 8 | + * You may select, at your option, one of the above-listed licenses. | ||
| 9 | + */ | ||
| 10 | + | ||
| 11 | +#ifndef ZSTD_COMPILER_H | ||
| 12 | +#define ZSTD_COMPILER_H | ||
| 13 | + | ||
| 14 | +/*-******************************************************* | ||
| 15 | +* Compiler specifics | ||
| 16 | +*********************************************************/ | ||
| 17 | +/* force inlining */ | ||
| 18 | + | ||
| 19 | +#if !defined(ZSTD_NO_INLINE) | ||
| 20 | +#if defined (__GNUC__) || defined(__cplusplus) || defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L /* C99 */ | ||
| 21 | +# define INLINE_KEYWORD inline | ||
| 22 | +#else | ||
| 23 | +# define INLINE_KEYWORD | ||
| 24 | +#endif | ||
| 25 | + | ||
| 26 | +#if defined(__GNUC__) | ||
| 27 | +# define FORCE_INLINE_ATTR __attribute__((always_inline)) | ||
| 28 | +#elif defined(_MSC_VER) | ||
| 29 | +# define FORCE_INLINE_ATTR __forceinline | ||
| 30 | +#else | ||
| 31 | +# define FORCE_INLINE_ATTR | ||
| 32 | +#endif | ||
| 33 | + | ||
| 34 | +#else | ||
| 35 | + | ||
| 36 | +#define INLINE_KEYWORD | ||
| 37 | +#define FORCE_INLINE_ATTR | ||
| 38 | + | ||
| 39 | +#endif | ||
| 40 | + | ||
| 41 | +/** | ||
| 42 | + * FORCE_INLINE_TEMPLATE is used to define C "templates", which take constant | ||
| 43 | + * parameters. They must be inlined for the compiler to elimininate the constant | ||
| 44 | + * branches. | ||
| 45 | + */ | ||
| 46 | +#define FORCE_INLINE_TEMPLATE static INLINE_KEYWORD FORCE_INLINE_ATTR | ||
| 47 | +/** | ||
| 48 | + * HINT_INLINE is used to help the compiler generate better code. It is *not* | ||
| 49 | + * used for "templates", so it can be tweaked based on the compilers | ||
| 50 | + * performance. | ||
| 51 | + * | ||
| 52 | + * gcc-4.8 and gcc-4.9 have been shown to benefit from leaving off the | ||
| 53 | + * always_inline attribute. | ||
| 54 | + * | ||
| 55 | + * clang up to 5.0.0 (trunk) benefit tremendously from the always_inline | ||
| 56 | + * attribute. | ||
| 57 | + */ | ||
| 58 | +#if !defined(__clang__) && defined(__GNUC__) && __GNUC__ >= 4 && __GNUC_MINOR__ >= 8 && __GNUC__ < 5 | ||
| 59 | +# define HINT_INLINE static INLINE_KEYWORD | ||
| 60 | +#else | ||
| 61 | +# define HINT_INLINE static INLINE_KEYWORD FORCE_INLINE_ATTR | ||
| 62 | +#endif | ||
| 63 | + | ||
| 64 | +/* force no inlining */ | ||
| 65 | +#ifdef _MSC_VER | ||
| 66 | +# define FORCE_NOINLINE static __declspec(noinline) | ||
| 67 | +#else | ||
| 68 | +# ifdef __GNUC__ | ||
| 69 | +# define FORCE_NOINLINE static __attribute__((__noinline__)) | ||
| 70 | +# else | ||
| 71 | +# define FORCE_NOINLINE static | ||
| 72 | +# endif | ||
| 73 | +#endif | ||
| 74 | + | ||
| 75 | +/* target attribute */ | ||
| 76 | +#ifndef __has_attribute | ||
| 77 | + #define __has_attribute(x) 0 /* Compatibility with non-clang compilers. */ | ||
| 78 | +#endif | ||
| 79 | +#if defined(__GNUC__) | ||
| 80 | +# define TARGET_ATTRIBUTE(target) __attribute__((__target__(target))) | ||
| 81 | +#else | ||
| 82 | +# define TARGET_ATTRIBUTE(target) | ||
| 83 | +#endif | ||
| 84 | + | ||
| 85 | +/* Enable runtime BMI2 dispatch based on the CPU. | ||
| 86 | + * Enabled for clang & gcc >=4.8 on x86 when BMI2 isn't enabled by default. | ||
| 87 | + */ | ||
| 88 | +#ifndef DYNAMIC_BMI2 | ||
| 89 | + #if ((defined(__clang__) && __has_attribute(__target__)) \ | ||
| 90 | + || (defined(__GNUC__) \ | ||
| 91 | + && (__GNUC__ >= 5 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)))) \ | ||
| 92 | + && (defined(__x86_64__) || defined(_M_X86)) \ | ||
| 93 | + && !defined(__BMI2__) | ||
| 94 | + # define DYNAMIC_BMI2 1 | ||
| 95 | + #else | ||
| 96 | + # define DYNAMIC_BMI2 0 | ||
| 97 | + #endif | ||
| 98 | +#endif | ||
| 99 | + | ||
| 100 | +/* prefetch | ||
| 101 | + * can be disabled, by declaring NO_PREFETCH build macro */ | ||
| 102 | +#if defined(NO_PREFETCH) | ||
| 103 | +# define PREFETCH_L1(ptr) (void)(ptr) /* disabled */ | ||
| 104 | +# define PREFETCH_L2(ptr) (void)(ptr) /* disabled */ | ||
| 105 | +#else | ||
| 106 | +# if defined(_MSC_VER) && (defined(_M_X64) || defined(_M_I86)) /* _mm_prefetch() is not defined outside of x86/x64 */ | ||
| 107 | +# include <mmintrin.h> /* https://msdn.microsoft.com/fr-fr/library/84szxsww(v=vs.90).aspx */ | ||
| 108 | +# define PREFETCH_L1(ptr) _mm_prefetch((const char*)(ptr), _MM_HINT_T0) | ||
| 109 | +# define PREFETCH_L2(ptr) _mm_prefetch((const char*)(ptr), _MM_HINT_T1) | ||
| 110 | +# elif defined(__GNUC__) && ( (__GNUC__ >= 4) || ( (__GNUC__ == 3) && (__GNUC_MINOR__ >= 1) ) ) | ||
| 111 | +# define PREFETCH_L1(ptr) __builtin_prefetch((ptr), 0 /* rw==read */, 3 /* locality */) | ||
| 112 | +# define PREFETCH_L2(ptr) __builtin_prefetch((ptr), 0 /* rw==read */, 2 /* locality */) | ||
| 113 | +# else | ||
| 114 | +# define PREFETCH_L1(ptr) (void)(ptr) /* disabled */ | ||
| 115 | +# define PREFETCH_L2(ptr) (void)(ptr) /* disabled */ | ||
| 116 | +# endif | ||
| 117 | +#endif /* NO_PREFETCH */ | ||
| 118 | + | ||
| 119 | +#define CACHELINE_SIZE 64 | ||
| 120 | + | ||
| 121 | +#define PREFETCH_AREA(p, s) { \ | ||
| 122 | + const char* const _ptr = (const char*)(p); \ | ||
| 123 | + size_t const _size = (size_t)(s); \ | ||
| 124 | + size_t _pos; \ | ||
| 125 | + for (_pos=0; _pos<_size; _pos+=CACHELINE_SIZE) { \ | ||
| 126 | + PREFETCH_L2(_ptr + _pos); \ | ||
| 127 | + } \ | ||
| 128 | +} | ||
| 129 | + | ||
| 130 | +/* disable warnings */ | ||
| 131 | +#ifdef _MSC_VER /* Visual Studio */ | ||
| 132 | +# include <intrin.h> /* For Visual 2005 */ | ||
| 133 | +# pragma warning(disable : 4100) /* disable: C4100: unreferenced formal parameter */ | ||
| 134 | +# pragma warning(disable : 4127) /* disable: C4127: conditional expression is constant */ | ||
| 135 | +# pragma warning(disable : 4204) /* disable: C4204: non-constant aggregate initializer */ | ||
| 136 | +# pragma warning(disable : 4214) /* disable: C4214: non-int bitfields */ | ||
| 137 | +# pragma warning(disable : 4324) /* disable: C4324: padded structure */ | ||
| 138 | +#endif | ||
| 139 | + | ||
| 140 | +#endif /* ZSTD_COMPILER_H */ |
-
请 注册 或 登录 后发表评论