Java tutorial
/* * The MIT License (MIT) * * Copyright (c) 2016 Shengjie Sim Sun * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */ package com.tencent.tinker.app; import android.content.Context; import android.os.Looper; import android.os.MessageQueue; import com.tencent.tinker.app.callback.TinkerServerPatchRequestCallback; import com.tencent.tinker.lib.service.PatchResult; import com.tencent.tinker.lib.tinker.Tinker; import com.tencent.tinker.lib.util.TinkerLog; import com.tencent.tinker.loader.shareutil.ShareConstants; import com.tencent.tinker.loader.shareutil.SharePatchFileUtil; import com.tencent.tinker.server.TinkerServerClient; import com.tencent.tinker.server.client.ConfigRequestCallback; import com.tencent.tinker.server.client.DefaultPatchRequestCallback; import com.tencent.tinker.server.client.PatchRequestCallback; import com.tencent.tinker.server.utils.Debugger; import org.json.JSONException; import org.json.JSONObject; import java.io.File; import java.util.HashMap; import java.util.Iterator; public class TinkerServerManager { private static final String TAG = "Tinker.ServerManager"; private static final String CONDITION_CHANNEL = "channel"; static TinkerServerClient sTinkerServerClient; static String channel; /** * ? TinkerServer * @param context context * @param tinker {@link Tinker} * @param hours ?, ???, >= 0 * @param appKey TinkerpatchappKey * @param appVersion TinkerpatchappVersion * @param channel ????GooglePlay???channel?google?? */ public static void installTinkerServer(Context context, Tinker tinker, int hours, String appKey, String appVersion, String channel) { installTinkerServer(context, tinker, hours, appKey, appVersion, channel, new TinkerServerPatchRequestCallback()); } /** * ? TinkerServer * @param context context * @param tinker {@link Tinker} * @param hours ?, ???, >= 0 * @param appKey TinkerpatchappKey * @param appVersion TinkerpatchappVersion * @param channel ????GooglePlay???channel?google?? * @param patchRequestCallback {@link PatchRequestCallback} patchcallback */ public static void installTinkerServer(Context context, Tinker tinker, int hours, String appKey, String appVersion, String channel, PatchRequestCallback patchRequestCallback) { final boolean debug = Debugger.getInstance(context).isDebug(); TinkerLog.i(TAG, String.format("installTinkerServer, debug value: %s appVersion: %s, channel: %s", String.valueOf(debug), appVersion, channel)); sTinkerServerClient = TinkerServerClient.init(context, tinker, appKey, appVersion, debug, patchRequestCallback); // add channel condition sTinkerServerClient.updateTinkerCondition(CONDITION_CHANNEL, channel); sTinkerServerClient.setCheckIntervalByHours(hours); TinkerServerManager.channel = channel; } /** * ??? * @param immediately ?,? */ public static void checkTinkerUpdate(final boolean immediately) { if (sTinkerServerClient == null) { TinkerLog.e(TAG, "checkTinkerUpdate, sTinkerServerClient == null"); return; } Tinker tinker = sTinkerServerClient.getTinker(); //only check at the main process if (tinker.isMainProcess()) { Looper.getMainLooper().myQueue().addIdleHandler(new MessageQueue.IdleHandler() { @Override public boolean queueIdle() { sTinkerServerClient.checkTinkerUpdate(immediately); return false; } }); } } /** * ???? * @param configRequestCallback * @param immediately ?,? */ public static void getDynamicConfig(final ConfigRequestCallback configRequestCallback, final boolean immediately) { if (sTinkerServerClient == null) { TinkerLog.e(TAG, "checkTinkerUpdate, sTinkerServerClient == null"); return; } Tinker tinker = sTinkerServerClient.getTinker(); //only check at the main process if (tinker.isMainProcess()) { Looper.getMainLooper().myQueue().addIdleHandler(new MessageQueue.IdleHandler() { @Override public boolean queueIdle() { sTinkerServerClient.getDynamicConfig(configRequestCallback, immediately); return false; } }); } } /** * ? * @param hours 0 */ public static void setGetConfigIntervalByHours(int hours) { if (sTinkerServerClient == null) { TinkerLog.e(TAG, "setGetConfigIntervalByHours, sTinkerServerClient == null"); return; } sTinkerServerClient.setGetConfigIntervalByHours(hours); } /** * ? json Hashmap * @param jsonString * @return * @throws JSONException */ public static HashMap<String, String> jsonToMap(String jsonString) throws JSONException { HashMap<String, String> map = new HashMap<>(); JSONObject jObject = new JSONObject(jsonString); Iterator<String> keys = jObject.keys(); while (keys.hasNext()) { String key = keys.next(); String value = jObject.getString(key); map.put(key, value); } return map; } /** * ?? * @param key * @param value */ public void updateTinkerCondition(String key, String value) { if (sTinkerServerClient == null) { TinkerLog.e(TAG, "updateTinkerCondition, sTinkerServerClient == null"); return; } sTinkerServerClient.updateTinkerCondition(key, value); } /** * ??? * @param patchResult */ public static void reportTinkerPatchFail(PatchResult patchResult) { if (sTinkerServerClient == null) { TinkerLog.e(TAG, "reportTinkerPatchFail, sTinkerServerClient == null"); return; } if (patchResult == null) { TinkerLog.e(TAG, "reportTinkerPatchFail, patchResult == null"); return; } if (patchResult.isSuccess) { TinkerLog.i(TAG, "reportTinkerPatchFail, patch success, just return"); return; } String patchMd5 = (patchResult.patchVersion != null) ? patchResult.patchVersion : SharePatchFileUtil.getMD5(new File(patchResult.rawPatchFilePath)); if (!patchMd5.equals(sTinkerServerClient.getCurrentPatchMd5())) { TinkerLog.e(TAG, "reportTinkerPatchFail, md5 not equal, patchMd5:%s, currentPatchMd5:%s", patchMd5, sTinkerServerClient.getCurrentPatchMd5()); return; } sTinkerServerClient.reportPatchFail(sTinkerServerClient.getCurrentPatchVersion(), DefaultPatchRequestCallback.ERROR_PATCH_FAIL); } /** * ??? * @param patchMd5 */ public static void reportTinkerPatchListenerFail(int returnCode, String patchMd5) { if (sTinkerServerClient == null) { TinkerLog.e(TAG, "reportTinkerPatchListenerFail, sTinkerServerClient == null"); return; } if (returnCode == ShareConstants.ERROR_PATCH_OK) { return; } if (patchMd5 == null) { TinkerLog.e(TAG, "reportTinkerPatchListenerFail, patchMd5 == null"); return; } if (!patchMd5.equals(sTinkerServerClient.getCurrentPatchMd5())) { TinkerLog.e(TAG, "reportTinkerPatchListenerFail, md5 not equal, patchMd5:%s, currentPatchMd5:%s", patchMd5, sTinkerServerClient.getCurrentPatchMd5()); return; } sTinkerServerClient.reportPatchFail(sTinkerServerClient.getCurrentPatchVersion(), DefaultPatchRequestCallback.ERROR_LISTENER_CHECK_FAIL); } /** * ? */ public static void reportTinkerLoadFail() { if (sTinkerServerClient == null) { TinkerLog.e(TAG, "reportTinkerPatchFail, sTinkerServerClient == null"); return; } sTinkerServerClient.reportPatchFail(sTinkerServerClient.getCurrentPatchVersion(), DefaultPatchRequestCallback.ERROR_LOAD_FAIL); } public static boolean isGooglePlayChannel() { return channel.contains("google"); } }