github.com/chanxuehong/wechat@v0.0.0-20230222024006-36f0325263cd/mp/shakearound/device/search.go (about) 1 package device 2 3 import ( 4 "errors" 5 6 "github.com/chanxuehong/wechat/internal/util" 7 "github.com/chanxuehong/wechat/mp/core" 8 ) 9 10 type SearchQuery struct { 11 Type int `json:"type"` // 查询类型。1:查询设备id列表中的设备;2:分页查询所有设备信息;3:分页查询某次申请的所有设备信息 12 DeviceIdentifiers []*DeviceIdentifier `json:"device_identifiers,omitempty"` // 指定的设备 ; 当type为1时,此项为必填 13 ApplyId *int64 `json:"apply_id,omitempty"` // 批次ID,申请设备ID时所返回的批次ID;当type为3时,此项为必填 14 Begin *int `json:"begin,omitempty"` // 设备列表的起始索引值 15 Count *int `json:"count,omitempty"` // 待查询的设备数量,不能超过50个 16 } 17 18 func NewSearchQuery1(deviceIdentifiers []*DeviceIdentifier) *SearchQuery { 19 return &SearchQuery{ 20 Type: 1, 21 DeviceIdentifiers: deviceIdentifiers, 22 } 23 } 24 25 func NewSearchQuery2(begin, count int) *SearchQuery { 26 return &SearchQuery{ 27 Type: 2, 28 Begin: util.Int(begin), 29 Count: util.Int(count), 30 } 31 } 32 33 func NewSearchQuery3(applyId int64, begin, count int) *SearchQuery { 34 return &SearchQuery{ 35 Type: 3, 36 ApplyId: util.Int64(applyId), 37 Begin: util.Int(begin), 38 Count: util.Int(count), 39 } 40 } 41 42 type SearchResult struct { 43 TotalCount int `json:"total_count"` // 商户名下的设备总量 44 ItemCount int `json:"item_count"` // 查询的设备数量 45 Devices []Device `json:"devices"` // 查询的设备信息列表 46 } 47 48 type DeviceBase struct { 49 DeviceId int64 `json:"device_id"` 50 UUID string `json:"uuid"` 51 Major int `json:"major"` 52 Minor int `json:"minor"` 53 } 54 55 type Device struct { 56 DeviceBase 57 Comment string `json:"comment"` // 设备的备注信息 58 PageIds string `json:"page_ids"` // 与此设备关联的页面ID列表,用逗号隔开 59 Status int `json:"status"` // 激活状态,0:未激活,1:已激活(但不活跃),2:活跃 60 PoiId int64 `json:"poi_id"` // 设备关联的门店ID,关联门店后,在门店1KM的范围内有优先摇出信息的机会。门店相关信息具体可查看门店相关的接口文档 61 } 62 63 // 查询设备列表. 64 func Search(clt *core.Client, query *SearchQuery) (rslt *SearchResult, err error) { 65 var result struct { 66 core.Error 67 SearchResult `json:"data"` 68 } 69 70 incompleteURL := "https://api.weixin.qq.com/shakearound/device/search?access_token=" 71 if err = clt.PostJSON(incompleteURL, query, &result); err != nil { 72 return 73 } 74 75 if result.ErrCode != core.ErrCodeOK { 76 err = &result.Error 77 return 78 } 79 80 result.SearchResult.ItemCount = len(result.SearchResult.Devices) 81 rslt = &result.SearchResult 82 return 83 } 84 85 // DeviceIterator 86 // 87 // iter, err := NewDeviceIterator(*core.Client, *SearchQuery) 88 // if err != nil { 89 // // TODO: 增加你的代码 90 // } 91 // 92 // for iter.HasNext() { 93 // items, err := iter.NextPage() 94 // if err != nil { 95 // // TODO: 增加你的代码 96 // } 97 // // TODO: 增加你的代码 98 // } 99 type DeviceIterator struct { 100 clt *core.Client 101 102 nextQuery *SearchQuery // 下一次查询参数 103 104 lastSearchResult *SearchResult // 最近一次获取的数据 105 nextPageCalled bool // NextPage() 是否调用过 106 } 107 108 func (iter *DeviceIterator) TotalCount() int { 109 return iter.lastSearchResult.TotalCount 110 } 111 112 func (iter *DeviceIterator) HasNext() bool { 113 if !iter.nextPageCalled { // 第一次调用需要特殊对待 114 return iter.lastSearchResult.ItemCount > 0 || 115 *iter.nextQuery.Begin < iter.lastSearchResult.TotalCount 116 } 117 118 return *iter.nextQuery.Begin < iter.lastSearchResult.TotalCount 119 } 120 121 func (iter *DeviceIterator) NextPage() (devices []Device, err error) { 122 if !iter.nextPageCalled { // 第一次调用需要特殊对待 123 iter.nextPageCalled = true 124 125 devices = iter.lastSearchResult.Devices 126 return 127 } 128 129 rslt, err := Search(iter.clt, iter.nextQuery) 130 if err != nil { 131 return 132 } 133 134 *iter.nextQuery.Begin += rslt.ItemCount 135 iter.lastSearchResult = rslt 136 137 devices = rslt.Devices 138 return 139 } 140 141 func NewDeviceIterator(clt *core.Client, query *SearchQuery) (iter *DeviceIterator, err error) { 142 if query.Type != 2 { 143 err = errors.New("Unsupported SearchQuery.Type") 144 return 145 } 146 147 // 逻辑上相当于第一次调用 DeviceIterator.NextPage, 因为第一次调用 DeviceIterator.HasNext 需要数据支撑, 所以提前获取了数据 148 149 rslt, err := Search(clt, query) 150 if err != nil { 151 return 152 } 153 154 *query.Begin += rslt.ItemCount 155 156 iter = &DeviceIterator{ 157 clt: clt, 158 159 nextQuery: query, 160 161 lastSearchResult: rslt, 162 nextPageCalled: false, 163 } 164 return 165 }