假如說,有多個業(yè)務(wù),功能模式相同的公眾號/小程序,如果只是小程序開發(fā),那是不是需要復(fù)制多套代碼,改appid信息,在微信公眾號后臺,配置域名服務(wù)器以及密鑰等繁瑣的信息,每改一個提交發(fā)布一次,進(jìn)行重復(fù)的步驟。隨著要維護(hù)的公眾號/小程序數(shù)量逐步增加,需要投入的資源以及成本也隨之增加。
讓客戶滿意是我們工作的目標(biāo),不斷超越客戶的期望值來自于我們對這個行業(yè)的熱愛。我們立志把好的技術(shù)通過有效、簡單的方式提供給客戶,將通過不懈努力成為客戶在信息化領(lǐng)域值得信任、有價值的長期合作伙伴,公司提供的服務(wù)項目有:域名注冊、網(wǎng)絡(luò)空間、營銷軟件、網(wǎng)站建設(shè)、饒河網(wǎng)站維護(hù)、網(wǎng)站推廣。有沒有想過,只需要開發(fā)一套公眾號/小程序代碼,以之為模板,再來一套后臺管理系統(tǒng),把在微信公眾號后臺做的那些事都搬到我們自己的系統(tǒng)中。來一個業(yè)務(wù)相同的小程序,只需要管理員授權(quán)后,只要在我們的系統(tǒng)中點點幾個按鈕,就可以把小程序發(fā)布上線,一次開發(fā)供 N 個公眾號使用,提供標(biāo)準(zhǔn)化的接口服務(wù)來滿足業(yè)務(wù)的基礎(chǔ)需求。通過掃描二維碼授權(quán)給平臺,幫助 N 多個公眾號代實現(xiàn)業(yè)務(wù),不再需要理解繁瑣參數(shù)設(shè)置,并且密碼不提供給開發(fā)者,保證安全,真正做到解放運營同學(xué)和開發(fā)的雙手,有更多的時間去談女朋友,那該多好。沒錯,微信第三方平臺開發(fā)就是來幫你節(jié)省更多時間去把妹的神器。
相關(guān)學(xué)習(xí)推薦:微信公眾號開發(fā)教程
概述
微信公眾平臺-第三方平臺(簡稱第三方平臺)開放給所有通過開發(fā)者資質(zhì)認(rèn)證后的開發(fā)者使用。在得到公眾號或小程序運營者(簡稱運營者)授權(quán)后,第三方平臺開發(fā)者可以通過調(diào)用微信開放平臺的接口能力,為公眾號或小程序的運營者提供賬號申請、小程序創(chuàng)建、技術(shù)開發(fā)、行業(yè)方案、活動營銷、插件能力等全方位服務(wù)。同一個賬號的運營者可以選擇多家適合自己的第三方為其提供產(chǎn)品能力或委托運營。
從業(yè)務(wù)特征上來說,第三方平臺必須如圖所示:
從具體的業(yè)務(wù)場景上說,第三方平臺包括以下場景:
提供行業(yè)解決方案,如針對電商行業(yè)的解決方案,或針對旅游行業(yè)的解決方案等;
行業(yè):(橫向)提供更加專業(yè)的運營能力,精細(xì)化運營用戶公眾號或小程序;
功能:(縱向)對公眾平臺功能的優(yōu)化,如專門優(yōu)化圖文消息視覺樣式和排版的工具,或?qū)iT定制的 CRM 用戶管理功能,或功能強大的小程序插件等。
接入第三方開發(fā)的前提是要有微信開放平臺應(yīng)用,詳細(xì)創(chuàng)建步驟請參考
developers.weixin.qq.com/doc/oplatfo…
1、獲取驗證票據(jù)
驗證票據(jù)(component_verify_ticket),在第三方平臺創(chuàng)建審核通過后,微信服務(wù)器會向其 ”授權(quán)事件接收URL” 每隔 10 分鐘以 POST 的方式推送 component_verify_ticket
接收 POST 請求后,只需直接返回字符串 success。為了加強安全性,postdata 中的 xml 將使用服務(wù)申請時的加解密 key 來進(jìn)行加密,在收到推送后需進(jìn)行解密。
public void saveTicket(HttpServletRequest request, HttpServletResponse response) throws IOException { String msgSignature = request.getParameter("msg_signature");// 微信加密簽名 String timeStamp = request.getParameter("timestamp");// 時間戳 String nonce = request.getParameter("nonce"); // 隨機數(shù) BufferedReader br = new BufferedReader(new InputStreamReader(request.getInputStream(),"UTF-8")); StringBuffer sb = new StringBuffer(); String line = null; while ((line = br.readLine()) != null) { sb = sb.append(line); } String postData = sb.toString(); try { AuthorizedUtils.saveComponentVerifyTicket(msgSignature, timeStamp, nonce, postData); } catch (Exception e) { logger.error("系統(tǒng)異常", e); } finally { // 響應(yīng)消息 PrintWriter out = response.getWriter(); out.print("success"); } }復(fù)制代碼
2、獲取令牌
令牌(component_access_token)是第三方平臺接口的調(diào)用憑據(jù)。令牌的獲取是有限制的,每個令牌的有效期為 2 小時,請自行做好令牌的管理,在令牌快過期時(比如1小時50分),重新調(diào)用接口獲取。
public static ComponentToken getComponentToken(String ticket) { RedisServiceredisService = RedisService.load(); ComponentToken componentToken = redisService.load(ComponentToken.COMPONENTTOKEN_ID, ComponentToken.class); if (componentToken == null) { String encryptAppId = ThirdPlat.PLAT_APPID; String appId = EnDecryptUtil.d3esDecode(encryptAppId); String encryptSecret = ThirdPlat.PLAT_SECRET; String secret = EnDecryptUtil.d3esDecode(encryptSecret); String requestUrl = AuthAccessUrl.COMPONENT_ACCESS_URL; Map map = new HashMap<>(); map.put("component_appid", appId); //第三方平臺appid map.put("component_appsecret", secret); //第三方平臺appsecret map.put("component_verify_ticket", ticket); String outputStr = JSONObject.toJSONString(map); logger.warn("請求數(shù)據(jù)"+outputStr); JSONObject jsonObject = HttpRequestUtils.httpRequest(requestUrl, "POST", outputStr); if (null != jsonObject) { long expires = System.currentTimeMillis() + 7200; try{ expires = System.currentTimeMillis() + jsonObject.getIntValue("expires_in"); }catch (Exception e) { } try { componentToken = new ComponentToken(); componentToken.setComponentAccessToken(jsonObject.getString("component_access_token")); componentToken.setExpiresIn(expires); redisService.save(componentToken, ComponentToken.class); } catch (Exception e) { componentToken = null; logger.error("系統(tǒng)異常", e); } } } else { long sysTime = System.currentTimeMillis(); if (sysTime >= componentToken.getExpiresIn()) { redisService.delete(ComponentToken.COMPONENTTOKEN_ID, ComponentToken.class); componentToken = getComponentToken(ticket); }else{ } } return componentToken; }復(fù)制代碼
3、快速創(chuàng)建小程序
快速創(chuàng)建小程序接口優(yōu)化了小程序注冊認(rèn)證的流程,能幫助第三方平臺迅速拓展線下商戶,拓展商戶的服務(wù)范圍,占領(lǐng)小程序線下商業(yè)先機。采用法人人臉識別方式替代小額打款等認(rèn)證流程,極大的減輕了小程序主體、類目資質(zhì)信息收集的人力成本。第三方平臺只需收集法人姓名、法人微信、企業(yè)名稱、企業(yè)代碼信息這四個信息,便可以向企業(yè)法人下發(fā)一條模板消息來采集法人人臉信息,完成全部注冊、認(rèn)證流程。以及法人收到創(chuàng)建成功后的小程序APPID時,同時下發(fā)模板消息給法人,提示法人進(jìn)行郵箱和密碼的設(shè)置,便于后續(xù)法人登陸小程序控制臺進(jìn)行管理。
通過該接口創(chuàng)建小程序默認(rèn)為“已認(rèn)證”。為降低接入小程序的成本門檻,通過該接口創(chuàng)建的小程序無需交 300 元認(rèn)證費。
public AjaxResult fastRegister(String merchantId) { Merchant merchant = merchantService.getById(merchantId); if (merchant == null) { logger.warn("快速創(chuàng)建小程序---->失敗,merchant為null"); return AjaxResult.error("快速創(chuàng)建小程序失敗,merchant為null",null); } else { RedisServiceredisService = RedisService.load(); ComponentVerifyTicket componentVerifyTicket = redisService.load(ComponentVerifyTicket.COMPONENT_VERIFY_TICKET_ID, ComponentVerifyTicket.class); if (componentVerifyTicket == null) { logger.warn("快速創(chuàng)建小程序---->失敗,component_verify_ticket為null"); return AjaxResult.error("快速創(chuàng)建小程序失敗,component_verify_ticket為null",null); } else { ComponentToken componentToken = AuthorizedUtils.getComponentToken(componentVerifyTicket.getComponentVerifyTicket()); RegisterWeappOut out = new RegisterWeappOut(); out.setName(merchant.getName()) .setCode(merchant.getCode()) .setCode_type(merchant.getCodeType()) .setLegal_persona_wechat(merchant.getLegalPersonaWechat()) .setLegal_persona_name(merchant.getLegalPersonaName()) .setComponent_phone(merchant.getComponentPhone()); JSONObject obj = BaseUtils.createRegisterWeapp(componentToken,out); if (obj.getInteger("errcode") == 0 && "ok".equalsIgnoreCase(obj.getString("errmsg"))) { return AjaxResult.success(); } else { return AjaxResult.error(obj.getInteger("errcode"),obj.getString("errmsg")); } } } } 復(fù)制代碼
4、獲取預(yù)授權(quán)碼
預(yù)授權(quán)碼(pre_auth_code)是第三方平臺方實現(xiàn)授權(quán)托管的必備信息,每個預(yù)授權(quán)碼有效期為 10 分鐘。需要先獲取令牌才能調(diào)用。
public static String getPreAuthCode(String ticket) { ComponentToken componentToken = getComponentToken(ticket); String encryptAppId = ThirdPlat.PLAT_APPID; String appId = EnDecryptUtil.d3esDecode(encryptAppId); String url = AuthAccessUrl.PRE_AUTH_CODE_URL + componentToken.getComponentAccessToken(); Mapmap = new HashMap (); map.put("component_appid", appId); JSONObject jsonObject = HttpRequestUtils.httpRequest(url, "POST", JSONObject.toJSONString(map)); return jsonObject.getString("pre_auth_code"); }復(fù)制代碼
5、引導(dǎo)商戶授權(quán)獲取授權(quán)信息
第三方服務(wù)商構(gòu)建授權(quán)鏈接放置自己的網(wǎng)站,用戶點擊后,彈出授權(quán)頁面。
public AjaxResult getMchWebAuthUrl(@PathVariable("id") String id) { RedisServiceredisService = RedisService.load(); ComponentVerifyTicket componentVerifyTicket = redisService.load(ComponentVerifyTicket.COMPONENT_VERIFY_TICKET_ID, ComponentVerifyTicket.class); if(componentVerifyTicket == null){ return AjaxResult.error("引入用戶進(jìn)入授權(quán)頁失敗,component_verify_ticket為null",null); }else{ String preAuthCode = AuthorizedUtils.getPreAuthCode(componentVerifyTicket.getComponentVerifyTicket()); String encryptAppId = ThirdPlat.PLAT_APPID; String appId = EnDecryptUtil.d3esDecode(encryptAppId); String auth_type = ThirdPlat.AUTH_TYPE; String requestUrl = AuthAccessUrl.WEB_AUTH_URL; try { requestUrl = requestUrl.replace("COMPONENT_APPID", appId).replace("PRE_AUTH_CODE", preAuthCode) .replace("REDIRECT_URI", URLEncoder.encode(ThirdPlat.REDIRECT_URI.replace("MERCHANTID", id),"UTF-8")).replace("AUTH_TYPE", auth_type); } catch (UnsupportedEncodingException e) { e.printStackTrace(); } logger.warn("步驟2:引入用戶進(jìn)入授權(quán)頁---->成功,url為:" + requestUrl); return AjaxResult.success("操作成功",requestUrl); } }復(fù)制代碼
6、設(shè)置小程序基本信息
設(shè)置小程序名稱,當(dāng)名稱沒有命中關(guān)鍵詞,則直接設(shè)置成功;當(dāng)名稱命中關(guān)鍵詞,需提交證明材料,并需要審核。修改小程序的頭像。修改功能介紹。修改小程序隱私設(shè)置,即修改是否可被搜索。
public AjaxResult setBasicInfo(BasicInfo basicInfo) throws IOException { Merchant merchant = merchantService.getById(basicInfo.getMerchantId()); if (merchant == null) { logger.warn("設(shè)置基本信息---->失敗,merchant為null"); return AjaxResult.error("設(shè)置基本信息失敗,merchant為null",null); } else { AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); //修改頭像 if (StringUtils.isNotEmpty(basicInfo.getHeadImage())) { UploadIn uli = new UploadIn(); uli.setType("image").setUrlPath(basicInfo.getHeadImage()); JSONObject uploadJson = BaseUtils.upload(info,uli); String mediaId = uploadJson.getString("media_id"); ModifyHeadImageIn mhi = new ModifyHeadImageIn(); mhi.setHead_img_media_id(mediaId).setX1("0").setY1("0").setX2("1").setY2("1"); JSONObject obj = BaseUtils.modifyHeadImage(info,mhi); if (!obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) || !ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG))) { return AjaxResult.error(obj.getInteger(ResStatus.ERRCODE),obj.getString(ResStatus.ERRMSG)); } else { merchant.setAppletsHeadImg(basicInfo.getHeadImage()); } } //修改名稱 if (StringUtils.isNotEmpty(basicInfo.getNickname())) { UploadIn uli = new UploadIn(); uli.setType("image").setUrlPath(merchant.getBusinessLicense()); JSONObject uploadJson = BaseUtils.upload(info,uli); String mediaId = uploadJson.getString("media_id"); SetNicknameIn sni = new SetNicknameIn(); sni.setNick_name(basicInfo.getNickname()); sni.setLicense(mediaId); JSONObject obj = BaseUtils.setNickname(info,sni); if (!obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) || !ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG))) { return AjaxResult.error(obj.getInteger(ResStatus.ERRCODE),obj.getString(ResStatus.ERRMSG)); } else { merchant.setAppletsName(basicInfo.getNickname()); if (obj.containsKey("audit_id") && StringUtils.isNotEmpty(obj.getString("audit_id"))) { merchant.setAuditId(obj.getString("audit_id")); } } } //修改功能介紹 if (StringUtils.isNotEmpty(basicInfo.getSignature())) { ModifySignatureIn msi = new ModifySignatureIn(); msi.setSignature(basicInfo.getSignature()); JSONObject obj = BaseUtils.modifySignature(info, msi); if (!obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) || !ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG))) { return AjaxResult.error(obj.getInteger(ResStatus.ERRCODE),obj.getString(ResStatus.ERRMSG)); } else { merchant.setAppletsSignature(basicInfo.getSignature()); } } //修改隱私設(shè)置,即修改是否可被搜索 if (StringUtils.isNotEmpty(basicInfo.getStatus())) { SearchStatusIn ssi = new SearchStatusIn(); ssi.setStatus(basicInfo.getStatus()); JSONObject obj = BaseUtils.changeWxaSearchStatus(info, ssi); if (!obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) || !ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG))) { return AjaxResult.error(obj.getInteger(ResStatus.ERRCODE),obj.getString(ResStatus.ERRMSG)); } else { merchant.setSearchStatus(basicInfo.getStatus()); } } merchantService.updateById(merchant); return AjaxResult.success(); } }復(fù)制代碼
7、支付授權(quán)
即填寫商戶號和商戶號密鑰,以及上傳p12證書
8、設(shè)置服務(wù)器域名
授權(quán)給第三方的小程序,其服務(wù)器域名只可以為第三方平臺的服務(wù)器,當(dāng)小程序通過第三方平臺發(fā)布代碼上線后,小程序原先自己配置的服務(wù)器域名將被刪除,只保留第三方平臺的域名,所以第三方平臺在代替小程序發(fā)布代碼之前,需要調(diào)用接口為小程序添加第三方平臺自身的域名。
注意:
需要先將域名登記到第三方平臺的小程序服務(wù)器域名中,才可以調(diào)用接口進(jìn)行配置。
最多可以添加1000個合法服務(wù)器域名;其中,Request域名、Socket域名、Uploadfile域名、Download域名、Udp域名的設(shè)置數(shù)量均支持200個。
每月可提交修改申請50次。
public AjaxResult modifyDomain(ModifyDomain modifyDomain) { Merchant merchant = merchantService.getById(modifyDomain.getMerchantId()); if (merchant == null) { logger.warn("設(shè)置服務(wù)器域名---->失敗,merchant為null"); return AjaxResult.error("設(shè)置服務(wù)器域名失敗,merchant為null",null); } else { AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); ModifyDomainOut out = new ModifyDomainOut(); out.setAction(modifyDomain.getAction()); String[] requests = modifyDomain.getRequestdomain().split(","); ListrequestList = Arrays.asList(requests); out.setRequestdomain(requestList); String[] wsrequests = modifyDomain.getWsrequestdomain().split(","); List wsrequestList = Arrays.asList(wsrequests); out.setWsrequestdomain(wsrequestList); String[] uploads = modifyDomain.getUploaddomain().split(","); List uploadList = Arrays.asList(uploads); out.setUploaddomain(uploadList); String[] downloads = modifyDomain.getDownloaddomain().split(","); List downloadsList = Arrays.asList(downloads); out.setDownloaddomain(downloadsList); JSONObject obj = BaseUtils.modifyDomain(info, out); if("0".equals(obj.getString("errcode")) && "ok".equalsIgnoreCase(obj.getString("errmsg"))){ return AjaxResult.success(); } else { return AjaxResult.error(obj.getInteger("errcode"),obj.getString("errmsg")); } } }復(fù)制代碼
9、設(shè)置業(yè)務(wù)域名
授權(quán)給第三方的小程序,其業(yè)務(wù)域名只可以為第三方平臺的服務(wù)器,當(dāng)小程序通過第三方發(fā)布代碼上線后,小程序原先自己配置的業(yè)務(wù)域名將被刪除,只保留第三方平臺的域名,所以第三方平臺在代替小程序發(fā)布代碼之前,需要調(diào)用接口為小程序添加業(yè)務(wù)域名。
注意:
需要先將業(yè)務(wù)域名登記到第三方平臺的小程序業(yè)務(wù)域名中,才可以調(diào)用接口進(jìn)行配置。
為授權(quán)的小程序配置域名時支持配置子域名,例如第三方登記的業(yè)務(wù)域名如為 qq.com,則可以直接將 qq.com 及其子域名(如 xxx.qq.com)也配置到授權(quán)的小程序中。
最多可以添加100個業(yè)
public AjaxResult webviewDomain(WebviewDomain webviewDomain) { Merchant merchant = merchantService.getById(webviewDomain.getMerchantId()); if (merchant == null) { logger.warn("設(shè)置業(yè)務(wù)域名---->失敗,merchant為null"); return AjaxResult.error("設(shè)置業(yè)務(wù)域名失敗,merchant為null",null); } else { AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); SetWebViewDomainOut out = new SetWebViewDomainOut(); out.setAction(webviewDomain.getAction()); String[] webviews = webviewDomain.getWebviewdomain().split(","); ListwebviewList = Arrays.asList(webviews); out.setWebviewdomain(webviewList); JSONObject obj = BaseUtils.setWebViewDomain(info, out); if("0".equals(obj.getString("errcode")) && "ok".equalsIgnoreCase(obj.getString("errmsg"))){ return AjaxResult.success(); } else { return AjaxResult.error(obj.getInteger("errcode"),obj.getString("errmsg")); } } }復(fù)制代碼
10、上傳小程序代碼
第三方平臺需要先將草稿添加到代碼模板庫,或者從代碼模板庫中選取某個代碼模板,得到對應(yīng)的模板 id(template_id);然后調(diào)用本接口可以為已授權(quán)的小程序上傳代碼。
public AjaxResult commit(CommitModel model) { Merchant merchant = merchantService.selectMerchantById(model.getMerchantId()); if (merchant == null) { logger.warn("上傳代碼---->失敗,merchant為null"); return AjaxResult.error("上傳代碼,merchant為null",null); } AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); CommitIn commitIn = new CommitIn(); String value = model.getValue(); String[] items = value.split("_"); String version = items[2]; commitIn.setTemplate_id(items[0]) .setUser_desc(items[1]) .setUser_version(version); //第三方自定義的配置 JSONObject obj = new JSONObject(); obj.put("extAppid", merchant.getAppid()); Mapmap = new HashMap<>(); map.put("merchantId", model.getMerchantId()); map.put("userVersion", commitIn.getUser_version()); obj.put("ext", map); map = new HashMap<>(); Map maps = new HashMap<>(); maps.put("pages/index/index", map); obj.put("extPages", maps); commitIn.setExt_json(JSONObject.toJSONString(obj)); //接受微信返回的數(shù)據(jù) obj = CodeUtils.commit(info, commitIn); if("0".equals(obj.getString("errcode")) && "ok".equalsIgnoreCase(obj.getString("errmsg"))){ AppletsRelease ar = appletsReleaseService.getOne(new LambdaQueryWrapper () .eq(AppletsRelease::getMerchantId,merchant.getId())); if(ar == null){ ar = new AppletsRelease(); ar.setMerchantId(model.getMerchantId()).setHistoryversion(version); } else{ ar.setHistoryversion(version); } appletsReleaseService.saveOrUpdate(ar); return AjaxResult.success(); } else { return AjaxResult.error(obj.getInteger("errcode"),obj.getString("errmsg")); } }復(fù)制代碼
11、成員管理
第三方平臺在幫助旗下授權(quán)的小程序提交代碼審核之前,可先讓小程序運營者體驗,體驗之前需要將運營者的個人微信號添加到該小程序的體驗者名單中。
注意: 如果運營者同時也是該小程序的管理員,則無需綁定,管理員默認(rèn)有體驗權(quán)限。
/** * 綁定體驗者 * @parambindTester * @return */ @Override public AjaxResult bindTester(BindTester bindTester) { Merchant merchant = merchantService.getById(bindTester.getMerchantId()); if (merchant == null) { logger.warn("綁定體驗者---->失敗,merchant為null"); return AjaxResult.error("綁定體驗者失敗,merchant為null",null); } else { AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); JSONObject obj = MemberUtils.bindTester(info, bindTester.getWechatId()); if("0".equals(obj.getString("errcode")) && "ok".equalsIgnoreCase(obj.getString("errmsg"))){ AppletsTester at = new AppletsTester(); at.setMerchantId(bindTester.getMerchantId()).setWechatId(bindTester.getWechatId()).setUserStr(obj.getString("userstr")); appletsTesterService.insertAppletsTester(at); return AjaxResult.success(); } else { return AjaxResult.error(obj.getInteger("errcode"),obj.getString("errmsg")); } } } /** * 解除體驗者 * @paramtesterIds * @return */ @Override public AjaxResult unbindTester(Long[] testerIds) { for (Long id : testerIds) { AppletsTester tester = appletsTesterService.getById(id); if (tester == null) { logger.warn("解除體驗者---->失敗,tester為null"); return AjaxResult.error("解除體驗者,tester為null",null); } Merchant merchant = merchantService.getById(tester.getMerchantId()); if (merchant == null) { logger.warn("解除體驗者---->失敗,merchant為null"); return AjaxResult.error("解除體驗者,merchant為null",null); } AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); JSONObject obj = MemberUtils.unbindTester(info, tester.getWechatId()); if("0".equals(obj.getString("errcode")) && "ok".equalsIgnoreCase(obj.getString("errmsg"))){ appletsTesterService.removeById(id); } else { return AjaxResult.error(obj.getInteger("errcode"),obj.getString("errmsg")); } } return AjaxResult.success(); }復(fù)制代碼
12、獲取體驗版二維碼
public AjaxResult getQrcode(String merchantId) { Merchant merchant = merchantService.getById(merchantId); if (merchant == null) { logger.warn("獲取體驗二維碼---->失敗,merchant為null"); return AjaxResult.error("獲取體驗二維碼,merchant為null",null); } AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); String qrcodeUrl = CodeUtils.getQrcode(info, "pages/index/index"); return AjaxResult.success("操作成功",qrcodeUrl); }復(fù)制代碼
13、提交審核
public AjaxResult submitAudit(SubmitAudit submit) { Merchant merchant = merchantService.getById(submit.getMerchantId()); if (merchant == null) { logger.warn("獲取體驗二維碼---->失敗,merchant為null"); return AjaxResult.error("獲取體驗二維碼,merchant為null", null); } AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); Listcategorys = submit.getCategory(); submit.setFirst_id(categorys.get(0).split("-")[0]) .setFirst_class(categorys.get(0).split("-")[1]) .setSecond_id(categorys.get(1).split("-")[0]) .setSecond_class(categorys.get(1).split("-")[1]) .setTag(submit.getTag().replace(",", " ")); List submits = new ArrayList<>(); submits.add(submit); JSONObject sa = CodeUtils.submitAudit(info, submits); if (sa.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) && ResStatus.MSG.equalsIgnoreCase(sa.getString(ResStatus.ERRMSG))) { JSONObject obj = CodeUtils.getAuditStatus(info, sa.getString("auditid")); if (obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) && ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG))) { AppletsRelease ar = appletsReleaseService.getOne(new LambdaQueryWrapper () .eq(AppletsRelease::getMerchantId,merchant.getId())); if (ar == null) { return AjaxResult.error("請先上傳代碼"); } ar.setMerchantId(submit.getMerchantId()) .setAuditId(sa.getString("auditid")) .setStatus(obj.getString("status")) .setRemark(obj.getString("screenshot")); if (AppletsRelease.STATUS_0.equals(ar.getStatus())) { ar.setRemark(AppletsRelease.MSG_0); } else if (AppletsRelease.STATUS_1.equals(ar.getStatus())) { ar.setReason(obj.getString("reason")) .setScreenshot(obj.getString("screenshot")) .setRemark(AppletsRelease.MSG_1); } else if (AppletsRelease.STATUS_2.equals(ar.getStatus())) { ar.setRemark(AppletsRelease.MSG_2); } else if (AppletsRelease.STATUS_3.equals(ar.getStatus())) { ar.setRemark(AppletsRelease.MSG_3); } else if (AppletsRelease.STATUS_4.equals(ar.getStatus())) { ar.setRemark(AppletsRelease.MSG_4); } appletsReleaseService.updateById(ar); return AjaxResult.success(); } else { return AjaxResult.error(obj.getInteger(ResStatus.ERRCODE), obj.getString(ResStatus.ERRMSG)); } } else { return AjaxResult.error(sa.getInteger(ResStatus.ERRCODE), sa.getString(ResStatus.ERRMSG)); } }復(fù)制代碼
14、審核撤回
注意: 單個帳號每天審核撤回次數(shù)最多不超過 1 次,一個月不超過 10 次。
public AjaxResult undoCodeAudit(String[] ids) { StringBuilder sb = new StringBuilder(); for (String id : ids) { Merchant merchant = merchantService.getById(id); AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); JSONObject obj = CodeUtils.undoCodeAudit(info); if (obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) && ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG))) { AppletsRelease ar = appletsReleaseService.getOne(new LambdaQueryWrapper() .eq(AppletsRelease::getMerchantId,merchant.getId())); ar.setStatus(AppletsRelease.MSG_3); appletsReleaseService.updateById(ar); } else{ sb.append(merchant.getName()+","); } } if (sb.length() == 0) { return AjaxResult.success(); } else { String name = sb.substring(0, sb.length()-1); return AjaxResult.error(name+"審核撤回失敗"); } }復(fù)制代碼
15、發(fā)布已通過審核的小程序
public AjaxResult releaseApplets(String[] ids) { StringBuilder sb = new StringBuilder(); for (String id : ids) { Merchant merchant = merchantService.getById(id); AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); JSONObject obj = CodeUtils.release(info); if (obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) && ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG))) { AppletsRelease ar = appletsReleaseService.getOne(new LambdaQueryWrapper() .eq(AppletsRelease::getMerchantId,merchant.getId())); ar.setStatus(AppletsRelease.STATUS_5); appletsReleaseService.updateById(ar); } else{ sb.append(merchant.getName()+","); } } if (sb.length() == 0) { return AjaxResult.success(); } else { String name = sb.substring(0, sb.length()-1); return AjaxResult.error(name+"發(fā)布失敗"); } }復(fù)制代碼
16、小程序版本回退
如果沒有上一個線上版本,將無法回退
只能向上回退一個版本,即當(dāng)前版本回退后,不能再調(diào)用版本回退接口。
public AjaxResult revertCodeRelease(String[] ids) { StringBuilder sb = new StringBuilder(); for (String id : ids) { Merchant merchant = merchantService.getById(id); AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); JSONObject obj = CodeUtils.revertCodeRelease(info); if (!(obj.getInteger(ResStatus.ERRCODE).equals(ResStatus.CODE) && ResStatus.MSG.equalsIgnoreCase(obj.getString(ResStatus.ERRMSG)))) { sb.append(merchant.getName()+","); } } if (sb.length() == 0) { return AjaxResult.success(); } else { String name = sb.substring(0, sb.length()-1); return AjaxResult.error(null,name+"審核撤回失敗"); } }復(fù)制代碼
17、獲取小程序碼
public AjaxResult getMiniQrcode(@PathVariable("merchantId") String merchantId) { Merchant merchant = merchantService.getById(merchantId); if (merchant == null) { logger.warn("獲取小程序碼---->失敗,merchant為null"); return AjaxResult.error("獲取小程序碼,merchant為null",null); } String qrcode; if (StringUtils.isNotEmpty(merchant.getAppletImage())) { qrcode = merchant.getAppletImage(); } else { AuthorizationInfo info = AuthorizedUtils.getAuthorizationInfo(merchant.getAppid()); qrcode = WxUtils.getMiniQrcode(merchantId, "pages/index/index", "merchant", "miniQrcode", info.getAuthorizer_access_token()); merchant.setAppletImage(qrcode); merchantService.updateById(merchant); } return AjaxResult.success("操作成功",qrcode); }復(fù)制代碼
相關(guān)學(xué)習(xí)推薦:微信小程序教程