package com.ectrip.checkincar.plate; import android.text.TextUtils; import com.ectrip.checkincar.core.prefs.AppPrefs; import org.json.JSONObject; import java.io.IOException; import java.util.concurrent.TimeUnit; import okhttp3.FormBody; import okhttp3.OkHttpClient; import okhttp3.Request; import okhttp3.RequestBody; import okhttp3.Response; /** * 百度智能云 access_token 获取与缓存(AK/SK → token,有效期约 30 天)。 * 全部方法须在后台线程调用。 */ public final class BaiduCloudToken { private static final String TOKEN_URL = "https://aip.baidubce.com/oauth/2.0/token"; private static final OkHttpClient CLIENT = new OkHttpClient.Builder() .connectTimeout(5, TimeUnit.SECONDS) .readTimeout(10, TimeUnit.SECONDS) .build(); private BaiduCloudToken() { } /** 缓存 token 仍有效(剩余 >24h)则直接用,否则重新获取。失败抛 IOException(中文 message)。 */ public static String getToken() throws IOException { if (AppPrefs.isCloudTokenValid()) { return AppPrefs.getCloudToken(); } return refreshToken(); } /** 强制用当前 AK/SK 重新鉴权。 */ public static String refreshToken() throws IOException { String ak = AppPrefs.getCloudAk(); String sk = AppPrefs.getCloudSk(); if (TextUtils.isEmpty(ak) || TextUtils.isEmpty(sk)) { throw new IOException("未配置 API Key / Secret Key"); } RequestBody body = new FormBody.Builder() .add("grant_type", "client_credentials") .add("client_id", ak) .add("client_secret", sk) .build(); Request request = new Request.Builder() .url(TOKEN_URL) .post(body) .addHeader("Content-Type", "application/x-www-form-urlencoded") .build(); try (Response response = CLIENT.newCall(request).execute()) { String rs = response.body() != null ? response.body().string() : ""; JSONObject json = new JSONObject(rs); String token = json.optString("access_token", null); if (TextUtils.isEmpty(token)) { AppPrefs.clearCloudToken(); String err = json.optString("error_description", json.optString("error", "鉴权失败")); throw new IOException("API Key/Secret 校验失败:" + err); } long expiresIn = json.optLong("expires_in", 2592000L); AppPrefs.setCloudToken(token, expiresIn); return token; } catch (IOException e) { AppPrefs.clearCloudToken(); throw new IOException("无法连接百度云,请检查外网/WiFi(" + e.getMessage() + ")"); } catch (Exception e) { AppPrefs.clearCloudToken(); throw new IOException("鉴权响应解析失败:" + e.getMessage()); } } }