WeixinDevice - TuPengXiong/TuPengXiong.github.io GitHub Wiki

微信设备相关代码

package xyz.kingsilk.qh.service.service

import grails.converters.JSON
import grails.transaction.Transactional
import org.springframework.http.*
import org.springframework.web.client.RestTemplate
import org.springframework.web.util.UriComponentsBuilder

@Transactional
class WeiXinDeviceService {

    /** API URL : 设备的二维码 */
    public static final String DEVICE_TICKETS = "https://api.weixin.qq.com/device/create_qrcode"
    /** API URL : 第三方获取deviceid和设备二维码 */
    public static final String DEVICE_GET_QRCODE = "https://api.weixin.qq.com/device/getqrcode"
    /** API URL : 设备绑定 */
    public static final String DEVICE_BIND = "https://api.weixin.qq.com/device/bind"
    /** API URL : 设备强制绑定 */
    public static final String DEVICE_COMPEL_BIND = "https://api.weixin.qq.com/device/compel_bind"
    /** API URL : 设备解绑 */
    public static final String DEVICE_UNBIND = "https://api.weixin.qq.com/device/unbind"
    /** API URL : 设备强制解绑 */
    public static final String DEVICE_COMPEL_UNBIND = "https://api.weixin.qq.com/device/compel_unbind"
    /** API URL : 设备获取状态 */
    public static final String DEVICE_GET_STATE = "https://api.weixin.qq.com/device/get_stat"
    /** API URL : 设备验证二维码 */
    public static final String DEVICE_VERIFY_QRCODE = "https://api.weixin.qq.com/device/verify_qrcode"
    /** API URL : 获取设备绑定openID */
    public static final String DEVICE_GET_QPENID = "https://api.weixin.qq.com/device/get_openid"
    /** API URL : 通过openid获取用户绑定的deviceid */
    public static final String DEVICE_GET_BIND = " https://api.weixin.qq.com/device/get_bind_device"
    /** API URL : 设备授权*/
    public static final String DEVICE_AUTHORIZE = "https://api.weixin.qq.com/device/authorize_device"
    /** API URL : 主动发送消息给设备*/
    public static final String DEVICE_TRANSMSG = "https://api.weixin.qq.com/device/transmsg"
    /**
     * 微信硬件应⽤端数据接口
     * 微信硬件云端和应⽤端消息交互,分成三种消息类型:
     1. 应⽤端查询设备状态:当应⽤端需要查询设备信息的时候,应⽤端可以调
     ⽤查询设备API,微信硬件云端收到请求后,⽴即返回成功收到请求。待
     查询到设备状态成功,将查询结果POST到接⼊者的注册URL上。
     2. 应⽤端设置设备状态:当应⽤端需要设置设备信息的时候,应⽤端可以调
     ⽤设置设备状态API,微信硬件云端收到请求后,⽴即返回成功收到请
     求。待设备状态设置成功后,将查询结果POST到接⼊者的注册URL上。
     3. 设备状态变化通知消息:当设备状态有变化或者有消息需要通知应⽤端的
     时候,微信硬件云POST消息给接⼊者的注册URL上。微信硬件云端⽴即返
     回成功收到请求。
     */
    /** API URL : . 设备查询*/

    public static
    final String MY_DEVICE_GET_STATUS = "https://api.weixin.qq.com/hardware/mydevice/platform/get_device_status"
    public static final String MY_DEVICE_CTRL = "https://api.weixin.qq.com/hardware/mydevice/platform/ctrl_device"

    RestTemplate wxRestTemplate

    /**
     * 获取设备的二维码
     * @param device_id_list
     * @param accessToken
     * @return
     * 成功:json方式返回二维码的生成ticket
     *{
     * "errcode":0,
     * "errmsg":"succ",
     * "device_num":1,
     * "code_list":[{"device_id":"id1","ticket":"t1"}]
     *}* 错误的Json返回示例:
     *{
     *      "errcode":-1,"errmsg":""
     *}
     */
    public String getDeviceTickets(List<String> device_id_list, String accessToken) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_TICKETS)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                device_num    : device_id_list.size(),
                device_id_list: device_id_list
        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 主动发送消息给设备
     * 第三方发送消息给设备主人的微信终端,并最终送达设备
     * @param accessToken 调用接口凭证
     * @param device_id 设备id
     * @param device_type 设备类型,目前为“公众账号原始ID”
     * @param content 消息内容,BASE64编码
     * @param openid 用户对应的openid
     * @return
     * 成功的Json返回结果:
     *{base_resp:{"errcode": 0,"errmsg":"ok"}}* 失败的Json返回示例:
     *{base_resp:{"errcode": -1,"errmsg":"system error"}}
     */
    public String transmsg(String accessToken, String device_id, String openid, String device_type, String content) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_TRANSMSG)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "device_id"  : device_id,
                "openid"     : openid,
                "device_type": device_type,
                "content"    : content

        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 设备强制绑定
     * 第三方后台绑定操作处理成功,通知公众平台。
     * @param accessToken 调用接口凭证
     * @param device_id 设备id
     * @param openid 用户对应的openid
     * @return
     * 成功的Json返回结果:
     *{base_resp:{"errcode": 0,"errmsg":"ok"}}* 失败的Json返回示例:
     *{base_resp:{"errcode": -1,"errmsg":"system error"}}
     */
    public String compel_bind(String accessToken, String device_id, String openid) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_COMPEL_BIND)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "device_id": device_id,
                "openid"   : openid

        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 设备绑定
     * 第三方后台绑定操作处理成功,通知公众平台。
     * @param accessToken 调用接口凭证
     * @param ticket 绑定操作合法性的凭证(由微信后台生成,第三方H5通过客户端jsapi获得)
     * @param device_id 设备id
     * @param openid 用户对应的openid
     * @return
     * 成功的Json返回结果:
     *{base_resp:{"errcode": 0,"errmsg":"ok"}}* 失败的Json返回示例:
     *{base_resp:{"errcode": -1,"errmsg":"system error"}}
     */
    public String bind(String accessToken, String ticket, String device_id, String openid) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_BIND)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "ticket"   : ticket,
                "device_id": device_id,
                "openid"   : openid

        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 设备解绑
     * 第三方后台绑定操作处理成功,通知公众平台。
     * @param accessToken 调用接口凭证
     * @param ticket 绑定操作合法性的凭证(由微信后台生成,第三方H5通过客户端jsapi获得)
     * @param device_id 设备id
     * @param openid 用户对应的openid
     * @return
     * 成功的Json返回结果:
     *{base_resp:{"errcode": 0,"errmsg":"ok"}}* 失败的Json返回示例:
     *{base_resp:{"errcode": -1,"errmsg":"system error"}}
     */
    public String unbind(String accessToken, String ticket, String device_id, String openid) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_UNBIND)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "ticket"   : ticket,
                "device_id": device_id,
                "openid"   : openid

        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 设备强制解绑
     * 第三方后台绑定操作处理成功,通知公众平台。
     * @param accessToken 调用接口凭证
     * @param device_id 设备id
     * @param openid 用户对应的openid
     * @return
     * 成功的Json返回结果:
     *{base_resp:{"errcode": 0,"errmsg":"ok"}}* 失败的Json返回示例:
     *{base_resp:{"errcode": -1,"errmsg":"system error"}}
     */
    public String compel_unbind(String accessToken, String device_id, String openid) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_COMPEL_UNBIND)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "device_id": device_id,
                "openid"   : openid

        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 利用deviceid更新设备属性
     * 第三方公众账号将device id及其属性信息提交公众平台进行授权。
     * http://iot.weixin.qq.com/wiki/new/index.html?page=3-4-6
     * @param accessToken 调用接口凭证
     * @param device_num 设备id的个数
     * @param device_list 设备id的列表,json的array格式,其size必须等于device_num
     * @param op_type 请求操作的类型,限定取值为: 1:设备更新(更新已授权设备的各属性值)
     * @return
     * 成功的Json返回结果:{"resp":[{
     "base_info":{
     "device_type":"your_devcie_type",
     "device_id":"id"
     },
     "errcode":0,
     "errmsg":"ok"
     }]}* 失败的Json返回示例:
     *{"errcode":42001,"errmsg":""}
     */
    public String authorize(String accessToken, String device_num, String device_list, op_type) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_AUTHORIZE)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "device_num" : device_num,
                "device_list": device_list,
                "op_type"    : op_type

        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 设备获取状态
     * 第三方公众账号通过设备id查询该id的状态(三种状态:未授权、已授权、已绑定)。
     * http://iot.weixin.qq.com/wiki/document-2_7.html
     * @param accessToken 调用接口凭证
     * @param product_id ;
     * 设备的产品编号(由微信硬件平台分配)。可在公众号设备功能管理页面查询。
     当product_id 为‘1’时,不要填写product_id 字段(会引起不必要错误);
     当product_id 不为‘1’时,必须填写 product_id 字段;
     * @return
     * 成功的Json返回结果:{resp_msg:{"ret_code":0," error_info":"ok"},"deviceid":"XXX","qrticket":"XXX"}* 失败的Json返回示例:{resp_msg:{"ret_code":-1," error_info":"system error"}}
     */
    public String get_qrcode(String accessToken, String product_id) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_GET_QRCODE)
                .queryParam("access_token", accessToken)
                .queryParam("product_id", product_id)
                .build()
                .encode("UTF-8")
                .toUri()
        ResponseEntity respEntity = wxRestTemplate.getForEntity(uri, String)
        return respEntity?.body
    }

    /**
     * 设备获取状态
     * 第三方公众账号通过设备id查询该id的状态(三种状态:未授权、已授权、已绑定)。
     * http://iot.weixin.qq.com/wiki/document-2_7.html
     * @param accessToken 调用接口凭证
     * @param device_id 设备id
     * @return
     * 成功的Json返回结果:
     *
     * 设备状态,目前取值如下: 0:未授权
     * 1:已经授权(尚未被用户绑定) 2:已经被用户绑定 3:属性未设置
     *{
     * "errcode":0,
     * "errmsg":"ok",
     * "status":2,
     * "status_info":"bind"
     *}*  失败的Json返回示例:
     *{"errcode":42001,"errmsg":""}
     */
    public String get_stat(String accessToken, String device_id) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_GET_STATE)
                .queryParam("access_token", accessToken)
                .queryParam("device_id", device_id)
                .build()
                .encode("UTF-8")
                .toUri()
        ResponseEntity respEntity = wxRestTemplate.getForEntity(uri, String)
        return respEntity?.body
    }

    /**
     * 验证二维码
     * 第三方后台绑定操作处理成功,通知公众平台。
     * @param accessToken 调用接口凭证
     * @param ticket 设备二维码的ticket
     * @return
     * 成功的Json返回结果:
     *{
     * "errcode":0,
     * "errmsg":"ok",
     * "device_type":"gh_xxxxxx",
     * "device_id":"DEVICE_ID",
     * "mac":"MAC"
     *}* 失败的Json返回示例:
     *{"errcode":42001,"errmsg":""}
     */
    public String verify_qrcode(String accessToken, String ticket) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_VERIFY_QRCODE)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "ticket": ticket,
        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 获取设备绑定openID
     * 通过device type和device id获取设备主人的openid。
     * http://iot.weixin.qq.com/wiki/document-2_4.html
     * @param device_type 设备类型,目前为“公众账号原始ID”
     * @param accessToken 调用接口凭证
     * @param device_id 设备id
     * @return
     * 成功的Json返回结果:
     *{
     * "open_id":["omN7ljrpaxQgK4NW4H5cRzFRtfa8","omN7ljtqrTZuvYLkjPEX_t_Pmmlg",],
     * "resp_msg":{"ret_code":0,"error_info":"get open id list OK!"}*}* 失败的Json返回示例:
     *{"errcode":42001,"errmsg":""}
     */
    public String get_openid(String accessToken, String device_id, String device_type) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_GET_QPENID)
                .queryParam("access_token", accessToken)
                .queryParam("device_id", device_id)
                .queryParam("device_type", device_type)
                .build()
                .encode("UTF-8")
                .toUri()
        ResponseEntity respEntity = wxRestTemplate.getForEntity(uri, String)
        return respEntity?.body
    }

    /**
     * 获取设备绑定openID
     * 通过device type和device id获取设备主人的openid。
     * http://iot.weixin.qq.com/wiki/document-2_4.html
     * @param device_type 设备类型,目前为“公众账号原始ID”
     * @param accessToken 调用接口凭证
     * @param device_id 设备id
     * @return
     * 成功的Json返回结果:
     *{
     * "resp_msg": {
     * "ret_code": 0,
     * "error_info": "ok"
     *},
     * "openid": "OPENID",
     * "device_list": [
     *{
     * "device_type": "dt1",
     * "device_id": "di1"
     *}* ]
     *}* 失败的Json返回示例:
     *{
     * "resp_msg": {
     * "ret_code": -1,
     * "error_info": "ERR_MSG"
     *},
     * "openid": "OPENID"
     *}
     */
    public String get_bind(String accessToken, String openid) {
        URI uri = UriComponentsBuilder.fromHttpUrl(DEVICE_GET_BIND)
                .queryParam("access_token", accessToken)
                .queryParam("openid", openid)
                .build()
                .encode("UTF-8")
                .toUri()
        ResponseEntity respEntity = wxRestTemplate.getForEntity(uri, String)
        return respEntity?.body
    }

    /**
     * 获取设备的运⾏状态
     * http://iot.weixin.qq.com/wiki/doc/hardwarecloud/openapi.pdf
     * @param accessToken 公众号调⽤接⼜的凭证
     * @param device_type 设备所属的公众号的原始ID
     * @param device_id 设备ID
     * @param services 欲查询的能⼒项及属性
     * @param user ⽤户的openid
     * @param data 可以⾃⾏填写任意内容,微信 平台将进⾏透传
     * @return
     回包格式:{
     "error_code": 0, //0代表成功
     "error_msg": "ok",
     "msg_id" : "xxx"
     }
     */
    public String get_status(String accessToken, String device_type, String device_id, String services, String user, String data) {
        URI uri = UriComponentsBuilder.fromHttpUrl(MY_DEVICE_GET_STATUS)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "device_type": device_type,
                "services"   : services,
                "user"       : user,
                "data"       : data,
                "device_id"  : device_id
        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }

    /**
     * 设备控制
     * 应⽤端POST设置消息到微信云,微信云⽴即回复收到。当设备设置成功后,微信云发送响应消息通知应⽤端成功处理。
     * http://iot.weixin.qq.com/wiki/doc/hardwarecloud/openapi.pdf
     * @param accessToken 公众号调⽤接⼜的凭证
     * @param device_type 设备所属的公众号的原始ID
     * @param device_id 设备ID
     * @param services 欲查询的能⼒项及属性
     * @param user ⽤户的openid
     * @param data 可以⾃⾏填写任意内容,微信 平台将进⾏透传
     * @return
     *
     回包格式:{
     "error_code": 0,//0代表成功
     "error_msg": "ok",
     "msg_id" : "xxx"
     }
     */
    public String ctrl(String accessToken, String device_type, String device_id, String services, String user, String data) {
        URI uri = UriComponentsBuilder.fromHttpUrl(MY_DEVICE_CTRL)
                .queryParam("access_token", accessToken)
                .build()
                .encode("UTF-8")
                .toUri()
        HttpHeaders headers = new HttpHeaders()
        headers.setContentType(MediaType.APPLICATION_JSON)
        def json = ([
                "device_type": device_type,
                "services"   : services,
                "user"       : user,
                "data"       : data,
                "device_id"  : device_id
        ] as JSON)
        HttpEntity<String> reqEntity = new HttpEntity<String>(json.toString(), headers)
        ResponseEntity respEntity = wxRestTemplate.exchange(uri, HttpMethod.POST, reqEntity, String.class)
        return respEntity?.body
    }


}

⚠️ **GitHub.com Fallback** ⚠️