SQLMock 和 Gorm:模拟 Postgres 插入
SQLMock and Gorm: Mocking Postgres Insert
当我尝试使用 SQLMock 和 Gorm.io 模拟 Postgres 插入时,我收到一条错误消息,指出查询不是预期的。我尝试使用 regexp.QuoteMeta()
来包装和转义我的字符串,但它不起作用。我添加和删除了参数和结果,但错误继续出现
如何通过 SQLMock 设置预期的查询?
我给你原始的 PostgresQuery 和 UserModel
//RAW QUERY
INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}]
//Gorm model
type User struct {
ID string `gorm:"primaryKey"`
Name *string
Surname *string
Birthdate *time.Time
Company *string
CustomClaims *json.RawMessage
Deleted gorm.DeletedAt
}
func (repository Repository) CreateUser(user users.User) (*users.User, error) {
newUser := toRepositoryModel(user)
err := repository.db.Create(newUser).Error //db -> *gorm.DB
//....
}
//TEST
const expectedQuery = `INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}]`
suite.mock.ExpectQuery(regexp.QuoteMeta(experctedQuery)) //HOW SHOULD BE MODIFIED?
user, err2 := postgres.CreateUser(users.User{
ID: ID,
})
//ERROR
"call to ExecQuery 'INSERT INTO \"users\" (\"id\",\"name\",\"surname\",\"birthdate\",\"company\",\"custom_claims\",\"deleted\") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}], was not expected, next expectation is: ExpectedQuery => expecting Query, QueryContext or QueryRow which:\n - matches sql: 'INSERT INTO \"users\" \(\"id\",\"name\",\"surname\",\"birthdate\",\"company\",\"custom_claims\",\"deleted\"\) VALUES \(\,\,\,\,\,\,\\)' with args \[\{Name: Ordinal:1 Value:my_user_id\} \{Name: Ordinal:2 Value:<nil>\} \{Name: Ordinal:3 Value:<nil>\} \{Name: Ordinal:4 Value:<nil>\} \{Name: Ordinal:5 Value:<nil>\} \{Name: Ordinal:6 Value:<nil>\} \{Name: Ordinal:7 Value:<nil>\}\]'\n - is without arguments",
}
call to ExecQuery 'INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}], was not expected, next expectation is: ExpectedQuery => expecting Query, QueryContext or QueryRow which:
- matches sql: 'INSERT INTO "users" \("id","name","surname","birthdate","company","custom_claims","deleted"\) VALUES \($1,$2,$3,$4,$5,$6,$7\)' with args \[\{Name: Ordinal:1 Value:my_user_id\} \{Name: Ordinal:2 Value:<nil>\} \{Name: Ordinal:3 Value:<nil>\} \{Name: Ordinal:4 Value:<nil>\} \{Name: Ordinal:5 Value:<nil>\} \{Name: Ordinal:6 Value:<nil>\} \{Name: Ordinal:7 Value:<nil>\}\]'
- is without arguments
occurred
我成功了。
suite.mock.ExpectExec(regexp.QuoteMeta(`INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)`)).WithArgs(ID, nil, nil, nil, nil, nil, nil).WillReturnResult(sqlmock.NewResult(0, 1))
更新
Postgres SELECT :
//Simulate returned row(s)
userMockRows := sqlmock.NewRows([]string{"id", "name", "surname", "birthdate", "company", "custom_claims", "deleted"}).AddRow(ID, nil, nil, nil, nil, nil, nil)
//Expect SELECT
suite.mock.ExpectQuery(regexp.QuoteMeta(`SELECT * FROM "users" WHERE id = `)).WithArgs(ID).WillReturnRows(userMockRows)
Postgres 更新:
suite.mock.ExpectExec(regexp.QuoteMeta(`UPDATE "users" SET "name"=,"surname"=,"birthdate"=,"company"=,"custom_claims"=,"deleted"= WHERE "id" = `)).WithArgs(newName, nil, nil, nil, nil, nil, ID).WillReturnResult(sqlmock.NewResult(0, 1))
当我尝试使用 SQLMock 和 Gorm.io 模拟 Postgres 插入时,我收到一条错误消息,指出查询不是预期的。我尝试使用 regexp.QuoteMeta()
来包装和转义我的字符串,但它不起作用。我添加和删除了参数和结果,但错误继续出现
如何通过 SQLMock 设置预期的查询?
我给你原始的 PostgresQuery 和 UserModel
//RAW QUERY
INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}]
//Gorm model
type User struct {
ID string `gorm:"primaryKey"`
Name *string
Surname *string
Birthdate *time.Time
Company *string
CustomClaims *json.RawMessage
Deleted gorm.DeletedAt
}
func (repository Repository) CreateUser(user users.User) (*users.User, error) {
newUser := toRepositoryModel(user)
err := repository.db.Create(newUser).Error //db -> *gorm.DB
//....
}
//TEST
const expectedQuery = `INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}]`
suite.mock.ExpectQuery(regexp.QuoteMeta(experctedQuery)) //HOW SHOULD BE MODIFIED?
user, err2 := postgres.CreateUser(users.User{
ID: ID,
})
//ERROR
"call to ExecQuery 'INSERT INTO \"users\" (\"id\",\"name\",\"surname\",\"birthdate\",\"company\",\"custom_claims\",\"deleted\") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}], was not expected, next expectation is: ExpectedQuery => expecting Query, QueryContext or QueryRow which:\n - matches sql: 'INSERT INTO \"users\" \(\"id\",\"name\",\"surname\",\"birthdate\",\"company\",\"custom_claims\",\"deleted\"\) VALUES \(\,\,\,\,\,\,\\)' with args \[\{Name: Ordinal:1 Value:my_user_id\} \{Name: Ordinal:2 Value:<nil>\} \{Name: Ordinal:3 Value:<nil>\} \{Name: Ordinal:4 Value:<nil>\} \{Name: Ordinal:5 Value:<nil>\} \{Name: Ordinal:6 Value:<nil>\} \{Name: Ordinal:7 Value:<nil>\}\]'\n - is without arguments",
}
call to ExecQuery 'INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)' with args [{Name: Ordinal:1 Value:my_user_id} {Name: Ordinal:2 Value:<nil>} {Name: Ordinal:3 Value:<nil>} {Name: Ordinal:4 Value:<nil>} {Name: Ordinal:5 Value:<nil>} {Name: Ordinal:6 Value:<nil>} {Name: Ordinal:7 Value:<nil>}], was not expected, next expectation is: ExpectedQuery => expecting Query, QueryContext or QueryRow which:
- matches sql: 'INSERT INTO "users" \("id","name","surname","birthdate","company","custom_claims","deleted"\) VALUES \($1,$2,$3,$4,$5,$6,$7\)' with args \[\{Name: Ordinal:1 Value:my_user_id\} \{Name: Ordinal:2 Value:<nil>\} \{Name: Ordinal:3 Value:<nil>\} \{Name: Ordinal:4 Value:<nil>\} \{Name: Ordinal:5 Value:<nil>\} \{Name: Ordinal:6 Value:<nil>\} \{Name: Ordinal:7 Value:<nil>\}\]'
- is without arguments
occurred
我成功了。
suite.mock.ExpectExec(regexp.QuoteMeta(`INSERT INTO "users" ("id","name","surname","birthdate","company","custom_claims","deleted") VALUES (,,,,,,)`)).WithArgs(ID, nil, nil, nil, nil, nil, nil).WillReturnResult(sqlmock.NewResult(0, 1))
更新
Postgres SELECT :
//Simulate returned row(s)
userMockRows := sqlmock.NewRows([]string{"id", "name", "surname", "birthdate", "company", "custom_claims", "deleted"}).AddRow(ID, nil, nil, nil, nil, nil, nil)
//Expect SELECT
suite.mock.ExpectQuery(regexp.QuoteMeta(`SELECT * FROM "users" WHERE id = `)).WithArgs(ID).WillReturnRows(userMockRows)
Postgres 更新:
suite.mock.ExpectExec(regexp.QuoteMeta(`UPDATE "users" SET "name"=,"surname"=,"birthdate"=,"company"=,"custom_claims"=,"deleted"= WHERE "id" = `)).WithArgs(newName, nil, nil, nil, nil, nil, ID).WillReturnResult(sqlmock.NewResult(0, 1))