add transaction pictures api

This commit is contained in:
MaysWind
2024-08-31 01:09:55 +08:00
parent 636ac974b8
commit 772a22a182
12 changed files with 466 additions and 71 deletions
+94 -20
View File
@@ -71,6 +71,67 @@ func (s *TransactionPictureService) GetPictureInfoByPictureId(c core.Context, ui
return pictureInfo, nil
}
// GetNewPictureInfosByPictureIds returns new transaction picture info models according to transaction picture ids
func (s *TransactionPictureService) GetNewPictureInfosByPictureIds(c core.Context, uid int64, pictureIds []int64) ([]*models.TransactionPictureInfo, error) {
if uid <= 0 {
return nil, errs.ErrUserIdInvalid
}
if pictureIds == nil {
return nil, errs.ErrTransactionPictureIdInvalid
}
var pictureInfos []*models.TransactionPictureInfo
err := s.UserDataDB(uid).NewSession(c).Where("uid=? AND deleted=? AND transaction_id=?", uid, false, models.TransactionPictureNewPictureTransactionId).In("picture_id", pictureIds).OrderBy("picture_id asc").Find(&pictureInfos)
if err != nil {
return nil, err
}
return pictureInfos, nil
}
// GetPictureInfosByTransactionId returns transaction picture info models according to transaction id
func (s *TransactionPictureService) GetPictureInfosByTransactionId(c core.Context, uid int64, transactionId int64) ([]*models.TransactionPictureInfo, error) {
if uid <= 0 {
return nil, errs.ErrUserIdInvalid
}
if transactionId <= 0 {
return nil, errs.ErrTransactionIdInvalid
}
var pictureInfos []*models.TransactionPictureInfo
err := s.UserDataDB(uid).NewSession(c).Where("uid=? AND deleted=? AND transaction_id=?", uid, false, transactionId).OrderBy("picture_id asc").Find(&pictureInfos)
if err != nil {
return nil, err
}
return pictureInfos, nil
}
// GetPictureInfosByTransactionIds returns transaction picture info models according to transaction ids
func (s *TransactionPictureService) GetPictureInfosByTransactionIds(c core.Context, uid int64, transactionIds []int64) (map[int64][]*models.TransactionPictureInfo, error) {
if uid <= 0 {
return nil, errs.ErrUserIdInvalid
}
if transactionIds == nil {
return nil, errs.ErrTransactionIdInvalid
}
var pictureInfos []*models.TransactionPictureInfo
err := s.UserDataDB(uid).NewSession(c).Where("uid=? AND deleted=?", uid, false).In("transaction_id", transactionIds).OrderBy("picture_id asc").Find(&pictureInfos)
if err != nil {
return nil, err
}
pictureInfoMap := s.GetPictureInfoListMapByList(pictureInfos)
return pictureInfoMap, err
}
// GetPictureByPictureId returns the transaction picture data according to transaction picture id
func (s *TransactionPictureService) GetPictureByPictureId(c core.Context, uid int64, pictureId int64, fileExtension string) ([]byte, error) {
if uid <= 0 {
@@ -150,26 +211,39 @@ func (s *TransactionPictureService) UploadPicture(c core.Context, pictureInfo *m
})
}
// DeleteAllPictures deletes all existed transaction pictures from database
func (s *TransactionPictureService) DeleteAllPictures(c core.Context, uid int64) error {
if uid <= 0 {
return errs.ErrUserIdInvalid
// GetPictureInfoMapByList returns a transaction picture info list map by a list
func (s *TransactionPictureService) GetPictureInfoMapByList(pictureInfos []*models.TransactionPictureInfo) map[int64]*models.TransactionPictureInfo {
pictureInfoMap := make(map[int64]*models.TransactionPictureInfo)
for i := 0; i < len(pictureInfos); i++ {
pictureInfo := pictureInfos[i]
pictureInfoMap[pictureInfo.PictureId] = pictureInfo
}
now := time.Now().Unix()
updateModel := &models.TransactionPictureInfo{
Deleted: true,
DeletedUnixTime: now,
}
return s.UserDataDB(uid).DoTransaction(c, func(sess *xorm.Session) error {
_, err := sess.Cols("deleted", "deleted_unix_time").Where("uid=? AND deleted=?", uid, false).Update(updateModel)
if err != nil {
return err
}
return nil
})
return pictureInfoMap
}
// GetPictureInfoListMapByList returns a transaction picture info list map by a list
func (s *TransactionPictureService) GetPictureInfoListMapByList(pictureInfos []*models.TransactionPictureInfo) map[int64][]*models.TransactionPictureInfo {
pictureInfoMap := make(map[int64][]*models.TransactionPictureInfo)
for i := 0; i < len(pictureInfos); i++ {
pictureInfo := pictureInfos[i]
pictureInfos, _ := pictureInfoMap[pictureInfo.TransactionId]
pictureInfoMap[pictureInfo.TransactionId] = append(pictureInfos, pictureInfo)
}
return pictureInfoMap
}
// GetTransactionPictureIds returns transaction picture ids list
func (s *TransactionPictureService) GetTransactionPictureIds(pictureInfos []*models.TransactionPictureInfo) []int64 {
pictureIds := make([]int64, len(pictureInfos))
for i := 0; i < len(pictureInfos); i++ {
pictureIds[i] = pictureInfos[i].PictureId
}
return pictureIds
}
+124 -3
View File
@@ -203,7 +203,7 @@ func (s *TransactionService) GetTransactionCount(c core.Context, uid int64, maxT
}
// CreateTransaction saves a new transaction to database
func (s *TransactionService) CreateTransaction(c core.Context, transaction *models.Transaction, tagIds []int64) error {
func (s *TransactionService) CreateTransaction(c core.Context, transaction *models.Transaction, tagIds []int64, pictureIds []int64) error {
if transaction.Uid <= 0 {
return errs.ErrUserIdInvalid
}
@@ -261,6 +261,11 @@ func (s *TransactionService) CreateTransaction(c core.Context, transaction *mode
}
}
pictureUpdateModel := &models.TransactionPictureInfo{
TransactionId: transaction.TransactionId,
UpdatedUnixTime: now,
}
return s.UserDataDB(transaction.Uid).DoTransaction(c, func(sess *xorm.Session) error {
// Get and verify source and destination account
sourceAccount, destinationAccount, err := s.getAccountModels(sess, transaction)
@@ -296,6 +301,13 @@ func (s *TransactionService) CreateTransaction(c core.Context, transaction *mode
return err
}
// Get and verify pictures
err = s.isPicturesValid(sess, transaction, pictureIds)
if err != nil {
return err
}
// Verify balance modification transaction and calculate real amount
if transaction.Type == models.TRANSACTION_DB_TYPE_MODIFY_BALANCE {
otherTransactionExists, err := sess.Cols("uid", "deleted", "account_id").Where("uid=? AND deleted=? AND account_id=?", transaction.Uid, false, sourceAccount.AccountId).Limit(1).Exist(&models.Transaction{})
@@ -376,6 +388,15 @@ func (s *TransactionService) CreateTransaction(c core.Context, transaction *mode
}
}
// Update transaction picture
if len(pictureIds) > 0 {
_, err = sess.Cols("transaction_id", "updated_unix_time").Where("uid=? AND deleted=? AND transaction_id=?", transaction.Uid, false, models.TransactionPictureNewPictureTransactionId).In("picture_id", pictureIds).Update(pictureUpdateModel)
if err != nil {
return err
}
}
// Update account table
if transaction.Type == models.TRANSACTION_DB_TYPE_MODIFY_BALANCE {
sourceAccount.UpdatedUnixTime = time.Now().Unix()
@@ -543,7 +564,7 @@ func (s *TransactionService) CreateScheduledTransactions(c core.Context, current
}
tagIds := template.GetTagIds()
err = s.CreateTransaction(c, transaction, tagIds)
err = s.CreateTransaction(c, transaction, tagIds, nil)
if err == nil {
successCount++
@@ -560,7 +581,7 @@ func (s *TransactionService) CreateScheduledTransactions(c core.Context, current
}
// ModifyTransaction saves an existed transaction to database
func (s *TransactionService) ModifyTransaction(c core.Context, transaction *models.Transaction, currentTagIdsCount int, addTagIds []int64, removeTagIds []int64) error {
func (s *TransactionService) ModifyTransaction(c core.Context, transaction *models.Transaction, currentTagIdsCount int, addTagIds []int64, removeTagIds []int64, addPictureIds []int64, removePictureIds []int64) error {
if transaction.Uid <= 0 {
return errs.ErrUserIdInvalid
}
@@ -736,6 +757,13 @@ func (s *TransactionService) ModifyTransaction(c core.Context, transaction *mode
return err
}
// Get and verify pictures
err = s.isPicturesValid(sess, transaction, addPictureIds)
if err != nil {
return err
}
// Update transaction row
updatedRows, err := sess.ID(transaction.TransactionId).Cols(updateCols...).Where("uid=? AND deleted=?", transaction.Uid, false).Update(transaction)
@@ -801,6 +829,35 @@ func (s *TransactionService) ModifyTransaction(c core.Context, transaction *mode
}
}
// Update transaction picture
if len(removePictureIds) > 0 {
pictureUpdateModel := &models.TransactionPictureInfo{
Deleted: true,
DeletedUnixTime: now,
}
deletedRows, err := sess.Cols("deleted", "deleted_unix_time").Where("uid=? AND deleted=? AND transaction_id=?", transaction.Uid, false, transaction.TransactionId).In("picture_id", removePictureIds).Update(pictureUpdateModel)
if err != nil {
return err
} else if deletedRows < 1 {
return errs.ErrTransactionPictureNotFound
}
}
if len(addPictureIds) > 0 {
pictureUpdateModel := &models.TransactionPictureInfo{
TransactionId: transaction.TransactionId,
UpdatedUnixTime: now,
}
_, err = sess.Cols("transaction_id", "updated_unix_time").Where("uid=? AND deleted=? AND transaction_id=?", transaction.Uid, false, models.TransactionPictureNewPictureTransactionId).In("picture_id", addPictureIds).Update(pictureUpdateModel)
if err != nil {
return err
}
}
// Update account table
if oldTransaction.Type == models.TRANSACTION_DB_TYPE_MODIFY_BALANCE {
if transaction.AccountId != oldTransaction.AccountId {
@@ -973,6 +1030,11 @@ func (s *TransactionService) DeleteTransaction(c core.Context, uid int64, transa
DeletedUnixTime: now,
}
pictureUpdateModel := &models.TransactionPictureInfo{
Deleted: true,
DeletedUnixTime: now,
}
return s.UserDataDB(uid).DoTransaction(c, func(sess *xorm.Session) error {
// Get and verify current transaction
oldTransaction := &models.Transaction{}
@@ -1025,6 +1087,13 @@ func (s *TransactionService) DeleteTransaction(c core.Context, uid int64, transa
return err
}
// Update transaction picture
_, err = sess.Cols("deleted", "deleted_unix_time").Where("uid=? AND deleted=? AND transaction_id=?", uid, false, oldTransaction.TransactionId).Update(pictureUpdateModel)
if err != nil {
return err
}
// Update account table
if oldTransaction.Type == models.TRANSACTION_DB_TYPE_MODIFY_BALANCE {
sourceAccount.UpdatedUnixTime = time.Now().Unix()
@@ -1097,6 +1166,11 @@ func (s *TransactionService) DeleteAllTransactions(c core.Context, uid int64) er
DeletedUnixTime: now,
}
pictureUpdateModel := &models.TransactionPictureInfo{
Deleted: true,
DeletedUnixTime: now,
}
accountUpdateModel := &models.Account{
Balance: 0,
Deleted: true,
@@ -1118,6 +1192,13 @@ func (s *TransactionService) DeleteAllTransactions(c core.Context, uid int64) er
return err
}
// Update all transaction picture to deleted
_, err = sess.Cols("deleted", "deleted_unix_time").Where("uid=? AND deleted=?", uid, false).Update(pictureUpdateModel)
if err != nil {
return err
}
// Update all account table to deleted
_, err = sess.Cols("balance", "deleted", "deleted_unix_time").Where("uid=? AND deleted=?", uid, false).Update(accountUpdateModel)
@@ -1495,6 +1576,17 @@ func (s *TransactionService) GetTransactionMapByList(transactions []*models.Tran
return transactionMap
}
// GetTransactionIds returns transaction ids list
func (s *TransactionService) GetTransactionIds(transactions []*models.Transaction) []int64 {
transactionIds := make([]int64, len(transactions))
for i := 0; i < len(transactions); i++ {
transactionIds[i] = transactions[i].TransactionId
}
return transactionIds
}
func (s *TransactionService) getTransactionQueryCondition(uid int64, maxTransactionTime int64, minTransactionTime int64, transactionType models.TransactionDbType, categoryIds []int64, accountIds []int64, tagIds []int64, amountFilter string, keyword string, noDuplicated bool) (string, []any) {
condition := "uid=? AND deleted=?"
conditionParams := make([]any, 0, 16)
@@ -1924,3 +2016,32 @@ func (s *TransactionService) isTagsValid(sess *xorm.Session, transaction *models
return nil
}
func (s *TransactionService) isPicturesValid(sess *xorm.Session, transaction *models.Transaction, pictureIds []int64) error {
if len(pictureIds) > 0 {
var pictureInfos []*models.TransactionPictureInfo
err := sess.Where("uid=? AND deleted=?", transaction.Uid, false).In("picture_id", pictureIds).Find(&pictureInfos)
if err != nil {
return err
}
pictureInfoMap := make(map[int64]*models.TransactionPictureInfo)
for i := 0; i < len(pictureInfos); i++ {
if pictureInfos[i].TransactionId != models.TransactionPictureNewPictureTransactionId && pictureInfos[i].TransactionId != transaction.TransactionId {
return errs.ErrTransactionPictureIdInvalid
}
pictureInfoMap[pictureInfos[i].PictureId] = pictureInfos[i]
}
for i := 0; i < len(pictureIds); i++ {
if _, exists := pictureInfoMap[pictureIds[i]]; !exists {
return errs.ErrTransactionPictureNotFound
}
}
}
return nil
}