作者 linmadan

添加素币兑换接口,修复错误提示bug

... ... @@ -61,3 +61,11 @@ func CreateAcceptanceTaskService(options map[string]interface{}) (service.Accept
}
return domainService.NewAcceptanceTaskService(transactionContext)
}
func CreateExchangeSuMoneyService(options map[string]interface{}) (service.ExchangeSuMoneyService, error) {
var transactionContext *pgTransaction.TransactionContext
if value, ok := options["transactionContext"]; ok {
transactionContext = value.(*pgTransaction.TransactionContext)
}
return domainService.NewExchangeSuMoneyService(transactionContext)
}
... ...
... ... @@ -11,7 +11,7 @@ type ExchangeSuMoneyCommand struct {
Uid int64 `json:"uid" valid:"Required"`
// 素币值
SuMoney float64 `json:"suMoney" valid:"Required"`
// 操作人UID(默认为系统操作)
// 操作人UID
Operator int64 `json:"operator,omitempty"`
// 兑换描述
ExchangeDescription string `json:"exchangeDescription" valid:"Required"`
... ...
... ... @@ -11,6 +11,8 @@ type SearchSuMoneyTransactionRecordCommand struct {
Uid int64 `json:"uid" valid:"Required"`
// 记录类型(1兑换,2任务奖励)
RecordType int `json:"recordType" valid:"Required"`
// 操作人UID
Operator int64 `json:"operator,omitempty"`
// 查询偏离量
Offset int `json:"offset,omitempty"`
// 查询限制
... ...
... ... @@ -2,8 +2,11 @@ package service
import (
"github.com/linmadan/egglib-go/core/application"
"github.com/linmadan/egglib-go/utils/tool_funs"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/application/factory"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/application/suMoney/command"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/domain"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/domain/service"
)
// 素币服务
... ... @@ -25,10 +28,22 @@ func (suMoneyService *SuMoneyService) ExchangeSuMoney(exchangeSuMoneyCommand *co
defer func() {
transactionContext.RollbackTransaction()
}()
if err := transactionContext.CommitTransaction(); err != nil {
return nil, application.ThrowError(application.TRANSACTION_ERROR, err.Error())
var exchangeSuMoneyService service.ExchangeSuMoneyService
if value, err := factory.CreateExchangeSuMoneyService(map[string]interface{}{
"transactionContext": transactionContext,
}); err != nil {
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, err.Error())
} else {
exchangeSuMoneyService = value
}
if task, err := exchangeSuMoneyService.Exchange(exchangeSuMoneyCommand.Uid, exchangeSuMoneyCommand.Operator, exchangeSuMoneyCommand.SuMoney, exchangeSuMoneyCommand.ExchangeDescription); err != nil {
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, err.Error())
} else {
if err := transactionContext.CommitTransaction(); err != nil {
return nil, application.ThrowError(application.TRANSACTION_ERROR, err.Error())
}
return task, nil
}
return nil, nil
}
// 搜索素币事务记录
... ... @@ -46,10 +61,25 @@ func (suMoneyService *SuMoneyService) SearchSuMoneyTransactionRecord(searchSuMon
defer func() {
transactionContext.RollbackTransaction()
}()
if err := transactionContext.CommitTransaction(); err != nil {
return nil, application.ThrowError(application.TRANSACTION_ERROR, err.Error())
var suMoneyTransactionRecordRepository domain.SuMoneyTransactionRecordRepository
if value, err := factory.CreateSuMoneyTransactionRecordRepository(map[string]interface{}{
"transactionContext": transactionContext,
}); err != nil {
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, err.Error())
} else {
suMoneyTransactionRecordRepository = value
}
if count, suMoneyTransactionRecords, err := suMoneyTransactionRecordRepository.Find(tool_funs.SimpleStructToMap(searchSuMoneyTransactionRecordCommand)); err != nil {
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, err.Error())
} else {
if err := transactionContext.CommitTransaction(); err != nil {
return nil, application.ThrowError(application.TRANSACTION_ERROR, err.Error())
}
return map[string]interface{}{
"count": count,
"suMoneyTransactionRecords": suMoneyTransactionRecords,
}, nil
}
return nil, nil
}
func NewSuMoneyService(options map[string]interface{}) *SuMoneyService {
... ...
... ... @@ -338,7 +338,7 @@ func (taskService *TaskService) CreateTask(createTaskCommand *command.CreateTask
if value, err := factory.CreateTaskDao(map[string]interface{}{
"transactionContext": transactionContext,
}); err != nil {
return nil, err
return nil, application.ThrowError(application.TRANSACTION_ERROR, err.Error())
} else {
taskDao = value
}
... ... @@ -346,7 +346,7 @@ func (taskService *TaskService) CreateTask(createTaskCommand *command.CreateTask
if value, err := factory.CreateEmployeeRepository(map[string]interface{}{
"transactionContext": transactionContext,
}); err != nil {
return nil, err
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, err.Error())
} else {
employeeRepository = value
}
... ... @@ -354,10 +354,10 @@ func (taskService *TaskService) CreateTask(createTaskCommand *command.CreateTask
"uid": createTaskCommand.Sponsor,
})
if err != nil {
return nil, err
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, err.Error())
}
if sponsor == nil {
return nil, fmt.Errorf("无效的发布者")
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, "无效的发布者")
}
newTask := &domain.Task{
TaskStatus: domain.TASK_STATUS_UNRELEASED,
... ... @@ -390,7 +390,7 @@ func (taskService *TaskService) CreateTask(createTaskCommand *command.CreateTask
} else {
if createTaskCommand.TaskType == domain.TASK_TYPE_BID {
if err := taskDao.AddBidInfo(task.TaskId, createTaskCommand.BidStartTime, createTaskCommand.BidEndTime); err != nil {
return nil, err
return nil, application.ThrowError(application.INTERNAL_SERVER_ERROR, err.Error())
}
}
if err := transactionContext.CommitTransaction(); err != nil {
... ...
package service
import "gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/domain"
type ExchangeSuMoneyService interface {
Exchange(uid int64, operatorUid int64, suMoney float64, recordDescription string) (*domain.SuMoneyTransactionRecord, error)
}
... ...
package domain_service
import (
"fmt"
coreDomain "github.com/linmadan/egglib-go/core/domain"
pgTransaction "github.com/linmadan/egglib-go/transaction/pg"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/domain"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/infrastructure/dao"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/infrastructure/repository"
"time"
)
type ExchangeSuMoneyService struct {
coreDomain.BaseEventPublisher
transactionContext *pgTransaction.TransactionContext
}
func (service *ExchangeSuMoneyService) Exchange(uid int64, operatorUid int64, suMoney float64, recordDescription string) (*domain.SuMoneyTransactionRecord, error) {
var employeeRepository domain.EmployeeRepository
var suMoneyTransactionRecordRepository domain.SuMoneyTransactionRecordRepository
var employeeDao *dao.EmployeeDao
if repository, err := repository.NewEmployeeRepository(service.transactionContext); err != nil {
return nil, err
} else {
employeeRepository = repository
}
if repository, err := repository.NewSuMoneyTransactionRecordRepository(service.transactionContext); err != nil {
return nil, err
} else {
suMoneyTransactionRecordRepository = repository
}
if dao, err := dao.NewEmployeeDao(service.transactionContext); err != nil {
return nil, err
} else {
employeeDao = dao
}
employee, err := employeeRepository.FindOne(map[string]interface{}{
"uid": uid,
})
if err != nil {
return nil, err
}
if employee == nil {
return nil, fmt.Errorf("无效的兑换者")
}
operator, err := employeeRepository.FindOne(map[string]interface{}{
"uid": operatorUid,
})
if err != nil {
return nil, err
}
if operator == nil {
return nil, fmt.Errorf("无效的操作者")
}
if employee.SuMoney < suMoney {
return nil, fmt.Errorf("当前素币不足")
}
suMoneyTransactionRecord := &domain.SuMoneyTransactionRecord{
RecordType: domain.SU_MONEY_TRANSACTION_RECORD_TYPE_EXCHANGE,
Employee: employee.EmployeeInfo,
SuMoney: suMoney,
Operator: operator.EmployeeInfo,
RecordDescription: recordDescription,
CreateTime: time.Now(),
}
if err := employeeDao.TransferSuMoney(employee.EmployeeInfo.Uid, suMoney); err != nil {
return nil, err
}
if suMoneyTransactionRecord, err := suMoneyTransactionRecordRepository.Save(suMoneyTransactionRecord); err != nil {
return nil, err
} else {
return suMoneyTransactionRecord, nil
}
}
func NewExchangeSuMoneyService(transactionContext *pgTransaction.TransactionContext) (*ExchangeSuMoneyService, error) {
if transactionContext == nil {
return nil, fmt.Errorf("transactionContext参数不能为nil")
} else {
return &ExchangeSuMoneyService{
transactionContext: transactionContext,
}, nil
}
}
... ...
... ... @@ -66,8 +66,14 @@ func (repository *SuMoneyTransactionRecordRepository) Find(queryOptions map[stri
var suMoneyTransactionRecordModels []*models.SuMoneyTransactionRecord
suMoneyTransactionRecords := make([]*domain.SuMoneyTransactionRecord, 0)
query := tx.Model(&suMoneyTransactionRecordModels)
if employeeUid, ok := queryOptions["employeeUid"]; ok && (employeeUid != int64(0)) {
query = query.Where(`task.employee @> '{"uid":?}'`, employeeUid)
if uid, ok := queryOptions["uid"]; ok && (uid != int64(0)) {
query = query.Where(`su_money_transaction_record.employee @> '{"uid":?}'`, uid)
}
if recordType, ok := queryOptions["recordType"]; ok && (recordType != 0) {
query = query.Where(`su_money_transaction_record.record_type = ?`, recordType)
}
if operator, ok := queryOptions["operator"]; ok && (operator != int64(0)) {
query = query.Where(`su_money_transaction_record.operator @> '{"uid":?}'`, operator)
}
if offset, ok := queryOptions["offset"]; ok {
offset := offset.(int)
... ...
package controllers
import (
"encoding/json"
"github.com/astaxie/beego"
"github.com/linmadan/egglib-go/web/beego/utils"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/application/suMoney/command"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/application/suMoney/service"
)
type SuMoneyController struct {
beego.Controller
}
func (controller *SuMoneyController) ExchangeSuMoney() {
suMoneyService := service.NewSuMoneyService(nil)
exchangeSuMoneyCommand := &command.ExchangeSuMoneyCommand{}
json.Unmarshal(controller.Ctx.Input.GetData("requestBody").([]byte), exchangeSuMoneyCommand)
data, err := suMoneyService.ExchangeSuMoney(exchangeSuMoneyCommand)
var response utils.JsonResponse
if err != nil {
response = utils.ResponseError(controller.Ctx, err)
} else {
response = utils.ResponseData(controller.Ctx, data)
}
controller.Data["json"] = response
controller.ServeJSON()
}
func (controller *SuMoneyController) SearchSuMoneyTransactionRecord() {
suMoneyService := service.NewSuMoneyService(nil)
searchSuMoneyTransactionRecordCommand := &command.SearchSuMoneyTransactionRecordCommand{}
json.Unmarshal(controller.Ctx.Input.GetData("requestBody").([]byte), searchSuMoneyTransactionRecordCommand)
data, err := suMoneyService.SearchSuMoneyTransactionRecord(searchSuMoneyTransactionRecordCommand)
var response utils.JsonResponse
if err != nil {
response = utils.ResponseError(controller.Ctx, err)
} else {
response = utils.ResponseData(controller.Ctx, data)
}
controller.Data["json"] = response
controller.ServeJSON()
}
... ...
... ... @@ -2,6 +2,7 @@ package controllers
import (
"encoding/json"
"fmt"
"github.com/astaxie/beego"
"github.com/linmadan/egglib-go/web/beego/utils"
... ... @@ -156,6 +157,7 @@ func (controller *TaskController) CreateTask() {
data, err := taskService.CreateTask(createTaskCommand)
var response utils.JsonResponse
if err != nil {
fmt.Println(err.Error())
response = utils.ResponseError(controller.Ctx, err)
} else {
response = utils.ResponseData(controller.Ctx, data)
... ...
package routers
import (
"github.com/astaxie/beego"
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/port/beego/controllers"
)
func init() {
beego.Router("/su-money/exchange", &controllers.SuMoneyController{}, "Post:ExchangeSuMoney")
beego.Router("/su-money/search-su-money-transaction-record", &controllers.SuMoneyController{}, "Post:SearchSuMoneyTransactionRecord")
}
... ...
package su_money
import (
"net/http"
"github.com/gavv/httpexpect"
"github.com/go-pg/pg"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
pG "gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/infrastructure/pg"
)
var _ = Describe("素币兑换", func() {
var suMoneyTransactionRecordId int64
BeforeEach(func() {
_, err := pG.DB.QueryOne(
pg.Scan(&suMoneyTransactionRecordId),
"INSERT INTO su_money_transaction_records (su_money_transaction_record_id, record_type, employee, su_money, operator, record_description, create_time) VALUES (?, ?, ?, ?, ?, ?, ?) RETURNING id",
"testSuMoneyTransactionRecordId", "testRecordType", "testEmployee", "testSuMoney", "testOperator", "testRecordDescription", "testCreateTime")
Expect(err).NotTo(HaveOccurred())
})
Describe("素币兑换", func() {
Context("", func() {
It("", func() {
httpExpect := httpexpect.New(GinkgoT(), server.URL)
body := map[string]interface{}{
"uid": "int64",
"suMoney": "float64",
"operator": "int64",
"exchangeDescription": "string",
}
httpExpect.POST("/su-money/exchange").
WithJSON(body).
Expect().
Status(http.StatusOK).
JSON().
Object().
ContainsKey("code").ValueEqual("code", 0).
ContainsKey("msg").ValueEqual("msg", "ok").
ContainsKey("data").Value("data").Object()
})
})
})
AfterEach(func() {
_, err := pG.DB.Exec("DELETE FROM su_money_transaction_records WHERE true")
Expect(err).NotTo(HaveOccurred())
})
})
... ...
package su_money
import (
"gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/domain"
"net/http"
"time"
"github.com/gavv/httpexpect"
"github.com/go-pg/pg"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
pG "gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/infrastructure/pg"
)
var _ = Describe("搜索素币事务记录", func() {
var suMoneyTransactionRecordId int64
BeforeEach(func() {
_, err := pG.DB.QueryOne(
pg.Scan(&suMoneyTransactionRecordId),
"INSERT INTO su_money_transaction_records (id, record_type, employee, su_money, operator, record_description, create_time) VALUES (?, ?, ?, ?, ?, ?, ?) RETURNING id",
1, 1, &domain.EmployeeInfo{
Uid: 2499036607974745088,
}, 100.00, &domain.EmployeeInfo{
Uid: 2499036607974745099,
}, "testRecordDescription", time.Now())
Expect(err).NotTo(HaveOccurred())
})
Describe("搜索素币事务记录", func() {
Context("指定搜索条件", func() {
It("返回搜索结果", func() {
httpExpect := httpexpect.New(GinkgoT(), server.URL)
body := map[string]interface{}{
"uid": 2499036607974745088,
"recordType": 1,
"operator": 2499036607974745099,
"offset": 0,
"limit": 20,
}
httpExpect.POST("/su-money/search-su-money-transaction-record").
WithJSON(body).
Expect().
Status(http.StatusOK).
JSON().
Object().
ContainsKey("code").ValueEqual("code", 0).
ContainsKey("msg").ValueEqual("msg", "ok").
ContainsKey("data").Value("data").Object()
})
})
})
AfterEach(func() {
_, err := pG.DB.Exec("DELETE FROM su_money_transaction_records WHERE true")
Expect(err).NotTo(HaveOccurred())
})
})
... ...
package su_money
import (
"net/http"
"net/http/httptest"
"testing"
"github.com/astaxie/beego"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
_ "gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/infrastructure/pg"
_ "gitlab.fjmaimaimai.com/linmadan/mmm-worth/pkg/port/beego"
)
func TestSuMoney(t *testing.T) {
RegisterFailHandler(Fail)
RunSpecs(t, "Beego Port SuMoney Correlations Test Case Suite")
}
var handler http.Handler
var server *httptest.Server
var _ = BeforeSuite(func() {
handler = beego.BeeApp.Handlers
server = httptest.NewServer(handler)
})
var _ = AfterSuite(func() {
server.Close()
})
... ...