Dans cet article, l'éditeur php Xiaoxin vous présentera une erreur courante qui se produit lors de l'écriture de tests unitaires en langage Go, à savoir les erreurs d'assertion. Lorsque nous écrivons des tests unitaires, nous rencontrons parfois des situations dans lesquelles la valeur de retour ne peut pas être déterminée, ce qui peut entraîner des erreurs d'appel de méthode inattendues. Dans cet article, nous aborderons les causes et les solutions à ce problème pour vous aider à mieux gérer les erreurs d'assertion et garantir l'exactitude et la fiabilité de vos tests unitaires.
J'écris des tests unitaires pour mes méthodes de service en utilisant testify
et toutes les méthodes fonctionnent correctement sauf la méthode de mise à jour car dans la méthode de mise à jour j'appelle une autre méthode du même service dans la méthode de mise à jour (" getbyid") .
Méthode de mise à jour dans mon service :
func (ts *teamservice) update(team *team.team) apperror { t, err := ts.teamrepo.getbyid(team.id) if err != nil { return err } if t.teamownerid != team.teamownerid { return newforbiddenerror(forbiddenerr) } return ts.teamrepo.update(team) }
Méthode de mise à jour du mockrepo :
func (t *teamrepomock) update(team *team.team) apperror { args := t.called(team) if args.error(0) != nil { return newnotfounderror(args.error(0)) } return nil }
Mise en place des tests :
func testupdate(t *testing.t) { _, teamidgen, playeridgen := setupconfig() t.run("update a team", func(t *testing.t) { teamrepo, _, ts := setupteamservice(teamidgen, playeridgen) teamrepo.on("update", testteam1).return(nil) result := ts.update(testteam1) assert.nil(t, result) }) t.run("update a team fails", func(t *testing.t) { teamrepo, _, ts := setupteamservice(teamidgen, playeridgen) expected := oopserr teamrepo.on("update", testteam1).return(expected) result := ts.update(testteam1) assert.equalvalues(t, expected.error(), result.error()) }) }
Maintenant, lorsque j'exécute le test, j'obtiens l'erreur suivante :
--- FAIL: TestUpdate (0.01s) --- FAIL: TestUpdate/Update_a_team (0.01s) panic: assert: mock: I don't know what to return because the method call was unexpected. Either do Mock.On("GetByID").Return(...) first, or remove the GetByID() call. This method was unexpected: GetByID(string) 0: "" at: [/home/waleem/Desktop/project/eazykhel_server/services/teamservice/team_service_init_test.go:18 /home/waleem/Desktop/project/eazykhel_server/services/teamservice/team_service.go:146 /home/waleem/Desktop/project/eazykhel_server/services/teamservice/team_service_test.go:277] [recovered] panic:
J'ai essayé d'appeler .on("update")
avant et après avoir appelé mock.on("getbyid")
dans l'implémentation de la fonction de test mais cela ne fonctionne pas et j'ai a également modifié la fonction de mise à jour du mockrepo mais cela n'a pas fonctionné. .on("update")
之前和之后调用 mock.on("getbyid")
,但它不起作用,而且我还修改了mockrepo update函数,但它没用。
让我尝试帮助您解决问题。我通过一些简化复制了该存储库,只是为了发布相关代码。如果我在您的解决方案中没有错,有一个服务(teamservice
)调用底层包(teamrepo
)提供的一些方法。您想测试 teamservice
结构的 update
repo/repo.go
Laissez-moi essayer de vous aider à résoudre votre problème. J'ai copié le référentiel avec quelques simplifications juste pour publier le code correspondant. Si je ne me trompe pas dans votre solution, il existe un service (teamservice
) qui appelle certaines méthodes fournies par le package sous-jacent (teamrepo
). Vous souhaitez tester la méthode update
de la structure teamservice
. Après examen, laissez-moi d'abord montrer le code, puis j'essaierai d'expliquer chaque fichier : getbyid
和 update
package repo type team struct { id int teamownerid int name string } type teamrepo struct{} func (t *teamrepo) getbyid(id int) (team, error) { return team{id: id, teamownerid: id, name: "myteam"}, nil } func (t *teamrepo) update(team team) error { return nil }
services/service.go
. Évidemment, ce n’est pas votre code réel, mais cela n’a pas d’importance pour le moment. sut
)。通过依赖注入,我们将利用通过接口 teamrepointerface
注入的 repo
package services import ( "errors" "testifymock/repo" ) type teamservice struct { tr teamrepointerface } func newteamservice(repo teamrepointerface) *teamservice { return &teamservice{ tr: repo, } } type teamrepointerface interface { getbyid(id int) (repo.team, error) update(team repo.team) error } func (ts *teamservice) update(team *repo.team) error { t, err := ts.tr.getbyid(team.id) if err != nil { return err } if t.teamownerid != team.teamownerid { return errors.new("forbidden") } return ts.tr.update(*team) }
services/service_test.go
fonctions fournies par le package) qui deviendront notre système en cours de test
package services import ( "errors" "testing" "testifymock/repo" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/mock" ) // 1. declare the mock struct type teamRepoMock struct { mock.Mock } // 2. implement the interface func (m *teamRepoMock) GetByID(id int) (repo.Team, error) { args := m.Called(id) return args.Get(0).(repo.Team), args.Error(1) } func (m *teamRepoMock) Update(team repo.Team) error { args := m.Called(team) return args.Error(0) } func TestUpdate(t *testing.T) { t.Run("GoodUpdate", func(t *testing.T) { // 3. instantiate/setup mock repoMock := new(teamRepoMock) repoMock.On("GetByID", 1).Return(repo.Team{ID: 1, TeamOwnerID: 1, Name: "test"}, nil).Times(1) repoMock.On("Update", repo.Team{ID: 1, TeamOwnerID: 1, Name: "test"}).Return(nil).Times(1) sut := NewTeamService(repoMock) err := sut.Update(&repo.Team{ID: 1, TeamOwnerID: 1, Name: "test"}) // 4. check that all expectations were met on the mock assert.Nil(t, err) assert.True(t, repoMock.AssertExpectations(t)) }) t.Run("BadUpdate", func(t *testing.T) { // 3. instantiate/setup mock repoMock := new(teamRepoMock) repoMock.On("GetByID", 1).Return(repo.Team{ID: 1, TeamOwnerID: 1, Name: "test"}, nil).Times(1) repoMock.On("Update", repo.Team{ID: 1, TeamOwnerID: 1, Name: "test"}).Return(errors.New("some error while updating")).Times(1) sut := NewTeamService(repoMock) err := sut.Update(&repo.Team{ID: 1, TeamOwnerID: 1, Name: "test"}) // 4. check that all expectations were met on the mock assert.Equal(t, "some error while updating", err.Error()) assert.True(t, repoMock.AssertExpectations(t)) }) }
repomock.on("getbyid", 1).return(repo.team{id: 1, teamownerid: 1, 姓名: "test"}, nil).times(1)
Dans le code vous pouvez trouver quelques commentaires pour mieux détailler ce qui se passe. Comme vous pouvez le deviner, le problème est que cet appel manque dans le code :
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!