|
@@ -0,0 +1,121 @@
|
|
|
+package com.qmth.boot.core.retrofit.core;
|
|
|
+
|
|
|
+import com.qmth.boot.core.retrofit.annotatioin.RetrofitClient;
|
|
|
+import com.qmth.boot.core.retrofit.config.RetrofitProperties;
|
|
|
+import com.qmth.boot.core.retrofit.interceptor.ErrorDecodeInterceptor;
|
|
|
+import com.qmth.boot.core.retrofit.interceptor.LoggingInterceptor;
|
|
|
+import com.qmth.boot.core.retrofit.interceptor.RetryInterceptor;
|
|
|
+import com.qmth.boot.core.retrofit.interceptor.SignatureInterceptor;
|
|
|
+import com.qmth.boot.core.retrofit.interfaces.CustomizeRetrofitConfiguration;
|
|
|
+import com.qmth.boot.core.retrofit.interfaces.SignatureProvider;
|
|
|
+import okhttp3.ConnectionPool;
|
|
|
+import okhttp3.OkHttpClient;
|
|
|
+import org.apache.commons.lang3.StringUtils;
|
|
|
+import org.springframework.beans.BeansException;
|
|
|
+import org.springframework.beans.factory.FactoryBean;
|
|
|
+import org.springframework.boot.logging.LogLevel;
|
|
|
+import org.springframework.context.ApplicationContext;
|
|
|
+import org.springframework.context.ApplicationContextAware;
|
|
|
+import retrofit2.Retrofit;
|
|
|
+import retrofit2.converter.jackson.JacksonConverterFactory;
|
|
|
+
|
|
|
+import java.lang.reflect.Proxy;
|
|
|
+
|
|
|
+public class RetrofitFactoryBean<T> implements FactoryBean<T>, ApplicationContextAware {
|
|
|
+
|
|
|
+ private ApplicationContext applicationContext;
|
|
|
+
|
|
|
+ private Class<T> retrofitInterface;
|
|
|
+
|
|
|
+ private RetrofitProperties retrofitProperties;
|
|
|
+
|
|
|
+ public RetrofitFactoryBean(Class<T> retrofitInterface) {
|
|
|
+ this.retrofitInterface = retrofitInterface;
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public T getObject() {
|
|
|
+ Retrofit retrofit = getRetrofit(retrofitInterface);
|
|
|
+ // source
|
|
|
+ T source = retrofit.create(retrofitInterface);
|
|
|
+ // proxy
|
|
|
+ return (T) Proxy.newProxyInstance(retrofitInterface.getClassLoader(), new Class<?>[] { retrofitInterface },
|
|
|
+ new RetrofitInvocationHandler(source, retrofitProperties));
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public Class<T> getObjectType() {
|
|
|
+ return this.retrofitInterface;
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public boolean isSingleton() {
|
|
|
+ return true;
|
|
|
+ }
|
|
|
+
|
|
|
+ private synchronized Retrofit getRetrofit(Class<?> retrofitClientInterfaceClass) {
|
|
|
+ RetrofitClient retrofitClient = retrofitClientInterfaceClass.getAnnotation(RetrofitClient.class);
|
|
|
+ CustomizeRetrofitConfiguration customize = applicationContext.getBean(retrofitClient.configuration());
|
|
|
+
|
|
|
+ OkHttpClient client = getOkHttpClient(retrofitClient, customize);
|
|
|
+ Retrofit.Builder retrofitBuilder = new Retrofit.Builder().baseUrl(getBaseUrl(retrofitClient, customize))
|
|
|
+ .addConverterFactory(JacksonConverterFactory.create()).validateEagerly(true).client(client);
|
|
|
+ if (retrofitClient.directReturn()) {
|
|
|
+ retrofitBuilder.addCallAdapterFactory(new DirectCallAdapterFactory());
|
|
|
+ }
|
|
|
+ return retrofitBuilder.build();
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * Get OkHttpClient instance, one interface corresponds to one OkHttpClient
|
|
|
+ *
|
|
|
+ * @param retrofitClient @RetrofitClient
|
|
|
+ * @return OkHttpClient instance
|
|
|
+ */
|
|
|
+ private OkHttpClient getOkHttpClient(RetrofitClient retrofitClient, CustomizeRetrofitConfiguration customize) {
|
|
|
+ OkHttpClient.Builder okHttpClientBuilder = new OkHttpClient.Builder().connectionPool(new ConnectionPool());
|
|
|
+
|
|
|
+ // add signature interceptor
|
|
|
+ SignatureProvider provider = customize.getSignature();
|
|
|
+ if (provider != null) {
|
|
|
+ okHttpClientBuilder.addInterceptor(new SignatureInterceptor(provider));
|
|
|
+ }
|
|
|
+
|
|
|
+ // add ErrorDecodeInterceptor
|
|
|
+ okHttpClientBuilder.addInterceptor(new ErrorDecodeInterceptor());
|
|
|
+
|
|
|
+ // add retry interceptor
|
|
|
+ okHttpClientBuilder.addInterceptor(new RetryInterceptor(retrofitProperties.getRetry()));
|
|
|
+
|
|
|
+ // add logging interceptor
|
|
|
+ LogLevel logLevel = getLogLevel(retrofitClient);
|
|
|
+ if (!logLevel.equals(LogLevel.OFF)) {
|
|
|
+ okHttpClientBuilder.addNetworkInterceptor(new LoggingInterceptor(logLevel));
|
|
|
+ }
|
|
|
+
|
|
|
+ return okHttpClientBuilder.build();
|
|
|
+ }
|
|
|
+
|
|
|
+ private String getBaseUrl(RetrofitClient retrofitClient, CustomizeRetrofitConfiguration customize) {
|
|
|
+ String url = customize.getBaseUrl();
|
|
|
+ if (StringUtils.isBlank(url)) {
|
|
|
+ url = retrofitClient.baseUrl();
|
|
|
+ }
|
|
|
+ return url;
|
|
|
+ }
|
|
|
+
|
|
|
+ private LogLevel getLogLevel(RetrofitClient retrofitClient) {
|
|
|
+ LogLevel level = retrofitClient.logLevel();
|
|
|
+ if (level.equals(LogLevel.OFF)) {
|
|
|
+ level = retrofitProperties.getLogLevel();
|
|
|
+ }
|
|
|
+ return level;
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
|
|
|
+ this.applicationContext = applicationContext;
|
|
|
+ this.retrofitProperties = applicationContext.getBean(RetrofitProperties.class);
|
|
|
+ }
|
|
|
+
|
|
|
+}
|