Error: suite.go:61: test panicked: reflect: Call with too few input arguments
Asked Answered
K

4

18

I'm setting unit test in golang.
But now I'm facing error when running go test -v.
I want to resolve this error and make test success.

article
  ├ client
  ├ api
  │  ├ main.go
  │  ├ contoroller
  │  │    ├ contoroller.go
  │  │    └ contoroller_test.go
  │  ├ service
  │  │    ├ service.go
  │  │    └ service_test.go
  │  ├ dao
  │  │    ├ dao.go
  │  │    └ dao_test.go
  │  ├ s3
  │  │    ├ s3.go
  │  │    └ s3_test.go
  │  ├ go.mod 
  │  ├ go.sum
  │  └ Dockerfile
  ├ nginx
  └ docker-compose.yml

Now I'm setting service_test.go for service.go.

service_test.go

package service

// import

type MockDaoInterface struct {
}

func (_m *MockDaoInterface) GetArticleDao() *sql.Rows {
    db, mock, _ := sqlmock.New()
    mockRows := mock.NewRows([]string{"id", "uuid", "title", "content"}).
        AddRow(1, "bea1b24d-0627-4ea0-aa2b-8af4c6c2a41c", "test", "test").
        AddRow(2, "844bc620-7336-41a3-9cb4-552a0024ff1c", "test2", "test2")
    mock.ExpectQuery("select").WillReturnRows(mockRows)
    rows, _ := db.Query("select")
    return rows
}


type ServiceSuite struct {
    suite.Suite
    service *Service
    dao     dao.DaoInterface
}

func (s *ServiceSuite) SetupTest() {
    s.service = NewService(s.dao)
    s.service.dao = &MockDaoInterface{}
}

func (s *ServiceSuite) TestGetArticleService(t *testing.T) {

    articles := s.service.GetArticleService()

    var expectedArticles []util.Article

    expectedArticle1 := util.Article{
        ID:      1,
        UUID:    "bea1b24d-0627-4ea0-aa2b-8af4c6c2a41c",
        TITLE:   "test",
        CONTENT: "test",
    }
    expectedArticles = append(expectedArticles, expectedArticle1)

    expectedArticle2 := util.Article{
        ID:      2,
        UUID:    "844bc620-7336-41a3-9cb4-552a0024ff1c",
        TITLE:   "test2",
        CONTENT: "test2",
    }
    expectedArticles = append(expectedArticles, expectedArticle2)

    assert.Equal(s.T(), expectedArticles, articles)
}

func TestServiceSuite(t *testing.T) {
    suite.Run(t, new(ServiceSuite))
}

service.go

package service

// import 

type Service struct {
    dao dao.DaoInterface
}

func NewService(dao dao.DaoInterface) *Service {
    return &Service{dao: dao}
}

func (s Service) GetArticleService() []util.Article {
    var articles []util.Article

    results := s.dao.GetArticleDao()

    article := util.Article{}
    for results.Next() {
        err := results.Scan(&article.ID, &article.UUID, &article.TITLE, &article.CONTENT)
        if err != nil {
            panic(err.Error())
        } else {
            articles = append(articles, article)
        }
    }
    return articles
}

dao.go

package dao

// import

type Dao struct {
    database *sql.DB
    s3       s3.S3Interface
}

func NewDao(database *sql.DB, s3 s3.S3Interface) *Dao {
    objs := &Dao{database: database, s3: s3}
    return objs
}

type DaoInterface interface {
    GetArticleDao() *sql.Rows
}

Here is the full source code(branch: go-test-service)
https://github.com/jpskgc/article/tree/go-test-service

I expect service_test.go to success test.
But the actual is it fails with error.
I want to resolve this error and to success test.

$ go test -v
=== RUN   TestServiceSuite
=== RUN   TestServiceSuite/TestGetArticleService
--- FAIL: TestServiceSuite (0.00s)
    --- FAIL: TestServiceSuite/TestGetArticleService (0.00s)
        suite.go:61: test panicked: reflect: Call with too few input arguments
FAIL
exit status 1
FAIL    article/api/service     0.045s
Kopeisk answered 9/9, 2019 at 5:37 Comment(1)
Before you fix this error, you need to seriously start closing the returned *sql.Rows object. Please see database/sql documentation on how to properly use that type of result. If you don't do it, your program will keep crashing because of too-many-connections open.Accidence
K
55

It's resolved by removing t *testing.T from aurgument.

func (s *ServiceSuite) TestGetArticleService() {
// some code
}
Kopeisk answered 9/9, 2019 at 6:14 Comment(4)
@TehSphinX, its correct to remove t *testing.T from argument. The user is using package "suite" in which, we do not need to send the "t *testing.T" parameter asgo test doesn't run this test function TestGetArticleService directly, but "suite" will. To get the testing context, one needs to use suite.T() within the function.Twelvetone
you must use T() from suiteMoxie
@Twelvetone is correct in that you need to use suite.T(), thanks!Carrel
Hm, but I still have this error...Victor
C
5

This method should not have any parameter

func (s *ServiceSuite) TestGetArticleService(t *testing.T) {

change it to

func (s *ServiceSuite) TestGetArticleService() {
Cherie answered 10/11, 2022 at 9:29 Comment(0)
K
0

I had the same problem

type AnswerApplicationSvcTestSuite struct {
    mock.Mock
    suite.Suite
    svc                   *answerApplicationService
}

My problem is hesitating to nest both mock.Mock and suete.Suite

I tried to delete mock.Mock

Then it's back to normal

Kapp answered 15/9, 2021 at 10:7 Comment(0)
V
0

My solution was

go generate ./...

because of mocks expected inputs.

Victor answered 16/5, 2023 at 18:57 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.