1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135
| import android.util.Base64 import com.testapp.BuildConfig import com.testapp.MyAppcation import com.testapp.utils.HMACSHA1 import com.testapp.utils.Utils import okhttp3.Interceptor import okhttp3.OkHttpClient import okhttp3.Response import okhttp3.logging.HttpLoggingInterceptor import org.json.JSONObject import retrofit2.Retrofit import retrofit2.converter.gson.GsonConverterFactory import java.nio.charset.Charset import java.util.concurrent.TimeUnit
object NetService { const val TokenErrorCode = 401
val service by lazy { getService(ApiInterface::class.java) }
private val tokenInterceptor by lazy { object : Interceptor { override fun intercept(chain: Interceptor.Chain): Response { val request = chain.request() val response = chain.proceed(request)
val responseBody = response.body val source = responseBody?.source() source?.request(Long.MAX_VALUE) val buffer = source?.buffer val contentType = responseBody?.contentType() var charset: Charset = java.nio.charset.StandardCharsets.UTF_8 if (contentType != null) { charset = contentType.charset(java.nio.charset.StandardCharsets.UTF_8) ?: java.nio.charset.StandardCharsets.UTF_8 }
val bodyString = buffer?.clone()?.readString(charset)
var code = 0 try { code = JSONObject(bodyString).getInt("code") } catch (e: Exception) {
}
if (code == TokenErrorCode) { val time = Utils.getNetTimestamp(System.currentTimeMillis()) val appId = MyAppcation.instance.appId val data = "appId${appId}timestamp$time" val appKey = MyAppcation.instance.appKey val sign = Base64.encodeToString( HMACSHA1.calculateRFC2104HMAC(data, appKey), Base64.NO_WRAP )
val token = service.getToken( appId = appId, appKey = appKey, timestamp = time, sign = sign ).execute().body()?.data?.token?.value ?: ""
if (token.isEmpty()) { throw java.lang.Exception("refresh token fail") } MyAppcation.instance.token = token val retryRequest = chain.request() .newBuilder() .removeHeader("token") .addHeader("token", token) .build() return chain.proceed(retryRequest) }
return response } } }
private val loggingInterceptor by lazy { HttpLoggingInterceptor() }
private fun <S> getService(serviceClass: Class<S>): S { return Retrofit.Builder() .baseUrl("http://dev.cloud.zhibankeji.com/") .addConverterFactory(GsonConverterFactory.create()) .client(createHttpClient()) .build() .create(serviceClass) }
private fun createHttpClient(): OkHttpClient { if (BuildConfig.DEBUG) { loggingInterceptor.level = HttpLoggingInterceptor.Level.BODY } else { loggingInterceptor.level = HttpLoggingInterceptor.Level.NONE }
return OkHttpClient.Builder() .addInterceptor(object : Interceptor { override fun intercept(chain: Interceptor.Chain): Response { val request = chain.request().newBuilder() .addHeader("token", MyAppcation.instance.token) .addHeader("appId", MyAppcation.instance.appId) .addHeader("deviceType", MyAppcation.instance.deviceType) .addHeader("deviceId", MyAppcation.instance.deviceId) .addHeader("deviceDetail", MyAppcation.instance.deviceDetail) .build() return chain.proceed(request) } }) .readTimeout(30, TimeUnit.SECONDS) .connectTimeout(30, TimeUnit.SECONDS) .writeTimeout(30, TimeUnit.SECONDS) .addInterceptor(loggingInterceptor) .addInterceptor(tokenInterceptor) .build() } }
|