github.com/stripe/stripe-go/v76@v76.25.0/search_iter_test.go (about) 1 package stripe 2 3 import ( 4 "fmt" 5 "net/http" 6 "net/http/httptest" 7 "testing" 8 9 assert "github.com/stretchr/testify/require" 10 "github.com/stripe/stripe-go/v76/form" 11 ) 12 13 var nextPageTestToken = "next_page_test_token" 14 15 func TestSearchIterEmpty(t *testing.T) { 16 tq := testSearchQuery{{nil, &SearchMeta{}, nil}} 17 g, gerr := collect(GetSearchIter(nil, tq.query)) 18 assert.Equal(t, 0, len(tq)) 19 assert.Equal(t, 0, len(g)) 20 assert.NoError(t, gerr) 21 } 22 23 func TestSearchIterEmptyErr(t *testing.T) { 24 tq := testSearchQuery{{nil, &SearchMeta{}, errTest}} 25 g, gerr := collect(GetSearchIter(nil, tq.query)) 26 assert.Equal(t, 0, len(tq)) 27 assert.Equal(t, 0, len(g)) 28 assert.Equal(t, errTest, gerr) 29 } 30 31 func TestSearchIterOne(t *testing.T) { 32 tq := testSearchQuery{{[]interface{}{1}, &SearchMeta{}, nil}} 33 want := []interface{}{1} 34 g, gerr := collect(GetSearchIter(nil, tq.query)) 35 assert.Equal(t, 0, len(tq)) 36 assert.Equal(t, want, g) 37 assert.NoError(t, gerr) 38 } 39 40 func TestSearchIterOneErr(t *testing.T) { 41 tq := testSearchQuery{{[]interface{}{1}, &SearchMeta{}, errTest}} 42 want := []interface{}{1} 43 g, gerr := collect(GetSearchIter(nil, tq.query)) 44 assert.Equal(t, 0, len(tq)) 45 assert.Equal(t, want, g) 46 assert.Equal(t, errTest, gerr) 47 } 48 49 func TestSearchIterPage2Empty(t *testing.T) { 50 tq := testSearchQuery{ 51 {[]interface{}{&item{"x"}}, &SearchMeta{HasMore: true, URL: "", NextPage: &nextPageTestToken}, nil}, 52 {nil, &SearchMeta{}, nil}, 53 } 54 want := []interface{}{&item{"x"}} 55 g, gerr := collect(GetSearchIter(nil, tq.query)) 56 assert.Equal(t, 0, len(tq)) 57 assert.Equal(t, want, g) 58 assert.NoError(t, gerr) 59 } 60 61 func TestSearchIterPage2EmptyErr(t *testing.T) { 62 tq := testSearchQuery{ 63 {[]interface{}{&item{"x"}}, &SearchMeta{HasMore: true, URL: "", NextPage: &nextPageTestToken}, nil}, 64 {nil, &SearchMeta{}, errTest}, 65 } 66 want := []interface{}{&item{"x"}} 67 g, gerr := collect(GetSearchIter(nil, tq.query)) 68 assert.Equal(t, 0, len(tq)) 69 assert.Equal(t, want, g) 70 assert.Equal(t, errTest, gerr) 71 } 72 73 func TestSearchIterTwoPages(t *testing.T) { 74 tq := testSearchQuery{ 75 {[]interface{}{&item{"x"}}, &SearchMeta{HasMore: true, URL: "", NextPage: &nextPageTestToken}, nil}, 76 {[]interface{}{2}, &SearchMeta{HasMore: false, URL: ""}, nil}, 77 } 78 want := []interface{}{&item{"x"}, 2} 79 g, gerr := collect(GetSearchIter(nil, tq.query)) 80 assert.Equal(t, 0, len(tq)) 81 assert.Equal(t, want, g) 82 assert.NoError(t, gerr) 83 } 84 85 func TestSearchIterTwoPagesErr(t *testing.T) { 86 tq := testSearchQuery{ 87 {[]interface{}{&item{"x"}}, &SearchMeta{HasMore: true, URL: "", NextPage: &nextPageTestToken}, nil}, 88 {[]interface{}{2}, &SearchMeta{HasMore: false, URL: ""}, errTest}, 89 } 90 want := []interface{}{&item{"x"}, 2} 91 g, gerr := collect(GetSearchIter(nil, tq.query)) 92 assert.Equal(t, 0, len(tq)) 93 assert.Equal(t, want, g) 94 assert.Equal(t, errTest, gerr) 95 } 96 97 func TestSearchIterListAndMeta(t *testing.T) { 98 type listType struct { 99 SearchMeta 100 } 101 listMeta := &SearchMeta{HasMore: true, URL: "", NextPage: &nextPageTestToken} 102 list := &listType{SearchMeta: *listMeta} 103 104 tq := testSearchQuery{{nil, list, nil}} 105 it := GetSearchIter(nil, tq.query) 106 assert.Equal(t, list, it.SearchResult()) 107 assert.Equal(t, listMeta, it.Meta()) 108 } 109 110 func TestSearchIterMultiplePages(t *testing.T) { 111 // Create an ephemeral test server so that we can inspect request attributes. 112 ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { 113 if r.URL.RawQuery == "query=my+query" { 114 w.Write([]byte(`{"data":[{"id": "1"}, {"id":"2"}], "has_more":true, "next_page":"page2", "total_count": 4 }`)) 115 return 116 } else if r.URL.RawQuery == "query=my+query&page=page2" { 117 w.Write([]byte(`{"data":[{"id": "3"}, {"id":"4"}], "has_more":false, "next_page":null }`)) 118 return 119 } 120 assert.Fail(t, "shouldn't be hit") 121 })) 122 defer ts.Close() 123 124 // Configure the stripe client to use the ephemeral backend. 125 backend := GetBackendWithConfig(APIBackend, &BackendConfig{ 126 URL: String(ts.URL), 127 }) 128 client := Client{B: backend, Key: Key} 129 130 iter := client.Search(&SearchParams{ 131 Query: "my query", 132 }) 133 assert.Equal(t, *iter.Meta().TotalCount, uint32(4)) 134 cnt := 0 135 for iter.Next() { 136 e := iter.Current().(*TestEntity) 137 cnt += 1 138 assert.Equal(t, fmt.Sprint(cnt), e.ID) 139 } 140 141 assert.Equal(t, 4, cnt) 142 } 143 144 type testSearchQuery []struct { 145 v []interface{} 146 m SearchContainer 147 e error 148 } 149 150 func (tq *testSearchQuery) query(*Params, *form.Values) ([]interface{}, SearchContainer, error) { 151 x := (*tq)[0] 152 *tq = (*tq)[1:] 153 return x.v, x.m, x.e 154 } 155 156 // Client is used to invoke /charges APIs. 157 type Client struct { 158 B Backend 159 Key string 160 } 161 162 // SearchIter is an iterator for charges. 163 type TestSearchIter struct { 164 *SearchIter 165 } 166 167 // Search returns a search result containing charges. 168 func (c Client) Search(params *SearchParams) *TestSearchIter { 169 return &TestSearchIter{ 170 SearchIter: GetSearchIter(params, func(p *Params, b *form.Values) ([]interface{}, SearchContainer, error) { 171 list := &TestSearchResult{} 172 err := c.B.CallRaw(http.MethodGet, "/v1/something/search", c.Key, b, p, list) 173 174 ret := make([]interface{}, len(list.Data)) 175 for i, v := range list.Data { 176 ret[i] = v 177 } 178 179 return ret, list, err 180 }), 181 } 182 } 183 184 type TestEntity struct { 185 APIResource 186 // Amount intended to be collected by this payment. A positive integer representing how much to charge in the [smallest currency unit](https://stripe.com/docs/currencies#zero-decimal) (e.g., 100 cents to charge $1.00 or 100 to charge ¥100, a zero-decimal currency). The minimum amount is $0.50 US or [equivalent in charge currency](https://stripe.com/docs/currencies#minimum-and-maximum-charge-amounts). The amount value supports up to eight digits (e.g., a value of 99999999 for a USD charge of $999,999.99). 187 ID string `json:"id"` 188 } 189 190 type TestSearchResult struct { 191 APIResource 192 SearchMeta 193 Data []*TestEntity `json:"data"` 194 }