gorm의 Transaction에 대해 얘기를 나눠보도록 하겠습니다.

2660 단어 golang

순서


본고는 주로gorm의 Transaction을 연구하고자 한다

Transaction


gorm.io/[email protected]/finisher_api.go
// Transaction start a transaction as a block, return error will rollback, otherwise to commit.
func (db *DB) Transaction(fc func(tx *DB) error, opts ...*sql.TxOptions) (err error) {
    panicked := true

    if committer, ok := db.Statement.ConnPool.(TxCommitter); ok && committer != nil {
        // nested transaction
        if !db.DisableNestedTransaction {
            err = db.SavePoint(fmt.Sprintf("sp%p", fc)).Error
            defer func() {
                // Make sure to rollback when panic, Block error or Commit error
                if panicked || err != nil {
                    db.RollbackTo(fmt.Sprintf("sp%p", fc))
                }
            }()
        }

        if err == nil {
            err = fc(db.Session(&Session{}))
        }
    } else {
        tx := db.Begin(opts...)

        defer func() {
            // Make sure to rollback when panic, Block error or Commit error
            if panicked || err != nil {
                tx.Rollback()
            }
        }()

        if err = tx.Error; err == nil {
            err = fc(tx)
        }

        if err == nil {
            err = tx.Commit().Error
        }
    }

    panicked = false
    return
}

DB의 Transaction 방법은 비TxCommitter 유형의db를 대상으로 합니다.Statement.ConnPool 실행db.Begin, 이후에 defer를 등록하여 panicked 또는 err에 대한 실행 tx.Rollback (), fc를 실행한 후 err를 nil로 판단한 경우 tx.Commit (), Error를 err로 지정합니다

인스턴스

func TestInsertInTx(t *testing.T) {
    err := db.Transaction(func(tx *gorm.DB) error {
        classes := []model.Class{
            {
                Name: "abc2",
            },
            {
                Name: "abc2",
            },
        }
        err := db.Create(&classes).Error
        if err != nil {
            return err
        }

        uc := []model.UserClass{
            {
                UserId: 1,
                ClassId: classes[0].ID,
            },
            {
                UserId: 1,
                ClassId: classes[1].ID,
            },
        }
        err2 := db.Create(&uc).Error
        if err2 != nil {
            return err2
        }

        return nil
    })

    if err != nil {
        t.Error(err)
    }
}

작은 매듭


gorm의 DB는 트랜잭션 방법을 제공합니다. 하나의 사무 템플릿, 자동commit 또는rollback에 해당합니다.func(tx*gorm.DB) error 파라미터를 제공하여 사용자 정의 사무 내의 데이터베이스 작업에 사용합니다.

doc

  • gorm
  • 좋은 웹페이지 즐겨찾기