diff --git a/app/build.gradle b/app/build.gradle
index 9fbfb0a..667fb79 100644
--- a/app/build.gradle
+++ b/app/build.gradle
@@ -1,17 +1,19 @@
plugins {
id 'com.android.application'
+ id 'kotlin-android'
+ id 'kotlin-android-extensions'
+ id 'kotlin-kapt'
}
android {
- compileSdkVersion 30
- buildToolsVersion "30.0.3"
+ compileSdkVersion rootProject.ext.android.compileSdkVersion
+ buildToolsVersion rootProject.ext.android.buildToolsVersion
defaultConfig {
- applicationId "com.yinuo.commonlibtest"
- minSdkVersion 23
- targetSdkVersion 30
- versionCode 1
- versionName "1.0"
+ minSdkVersion rootProject.ext.android.minSdkVersion
+ targetSdkVersion rootProject.ext.android.targetSdkVersion
+ versionCode rootProject.ext.android.versionCode
+ versionName rootProject.ext.android.versionName
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
@@ -26,6 +28,14 @@ android {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
+
+ dataBinding {
+ enabled = true
+ }
+
+ viewBinding {
+ enabled = true
+ }
}
dependencies {
@@ -34,7 +44,4 @@ dependencies {
implementation 'com.google.android.material:material:1.2.1'
implementation 'androidx.constraintlayout:constraintlayout:2.0.1'
implementation project(path: ':commonLib')
- testImplementation 'junit:junit:4.+'
- androidTestImplementation 'androidx.test.ext:junit:1.1.2'
- androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'
}
\ No newline at end of file
diff --git a/app/src/androidTest/java/com/yinuo/commonlibtest/ExampleInstrumentedTest.java b/app/src/androidTest/java/com/yinuo/commonlibtest/ExampleInstrumentedTest.java
deleted file mode 100644
index 82e98bd..0000000
--- a/app/src/androidTest/java/com/yinuo/commonlibtest/ExampleInstrumentedTest.java
+++ /dev/null
@@ -1,26 +0,0 @@
-package com.yinuo.commonlibtest;
-
-import android.content.Context;
-
-import androidx.test.platform.app.InstrumentationRegistry;
-import androidx.test.ext.junit.runners.AndroidJUnit4;
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-
-import static org.junit.Assert.*;
-
-/**
- * Instrumented test, which will execute on an Android device.
- *
- * @see Testing documentation
- */
-@RunWith(AndroidJUnit4.class)
-public class ExampleInstrumentedTest {
- @Test
- public void useAppContext() {
- // Context of the app under test.
- Context appContext = InstrumentationRegistry.getInstrumentation().getTargetContext();
- assertEquals("com.yinuo.commonlibtest", appContext.getPackageName());
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/com/yinuo/commonlibtest/MainActivity.java b/app/src/main/java/com/yinuo/commonlibtest/MainActivity.java
index f3ade52..f8320a4 100644
--- a/app/src/main/java/com/yinuo/commonlibtest/MainActivity.java
+++ b/app/src/main/java/com/yinuo/commonlibtest/MainActivity.java
@@ -4,11 +4,14 @@ import androidx.appcompat.app.AppCompatActivity;
import android.os.Bundle;
+import com.yinuo.commonlibtest.databinding.ActivityMainBinding;
+
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
- setContentView(R.layout.activity_main);
+ ActivityMainBinding binding = ActivityMainBinding.inflate(getLayoutInflater());
+ setContentView(binding.getRoot());
}
}
\ No newline at end of file
diff --git a/app/src/test/java/com/yinuo/commonlibtest/ExampleUnitTest.java b/app/src/test/java/com/yinuo/commonlibtest/ExampleUnitTest.java
deleted file mode 100644
index cf66f31..0000000
--- a/app/src/test/java/com/yinuo/commonlibtest/ExampleUnitTest.java
+++ /dev/null
@@ -1,17 +0,0 @@
-package com.yinuo.commonlibtest;
-
-import org.junit.Test;
-
-import static org.junit.Assert.*;
-
-/**
- * Example local unit test, which will execute on the development machine (host).
- *
- * @see Testing documentation
- */
-public class ExampleUnitTest {
- @Test
- public void addition_isCorrect() {
- assertEquals(4, 2 + 2);
- }
-}
\ No newline at end of file
diff --git a/commonLib/build.gradle b/commonLib/build.gradle
index 07004a9..060c04b 100644
--- a/commonLib/build.gradle
+++ b/commonLib/build.gradle
@@ -23,16 +23,23 @@ android {
debug {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
+ buildConfigField 'String', 'BASE_URL_CONFIG_PATH', '"baseUrl.properties"'
}
release {
minifyEnabled true
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
+ buildConfigField 'String', 'BASE_URL_CONFIG_PATH', '"baseUrl.properties"'
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
+
+ androidExtensions {
+ // kotlin序列化
+ experimental = true
+ }
}
dependencies {
@@ -47,6 +54,18 @@ dependencies {
// 添加kotlin依赖
implementation rootProject.ext.dependencies.kotlin
implementation rootProject.ext.dependencies.kotlin_android
+ // 添加okhttp依赖
+ implementation rootProject.ext.dependencies.okhttp
+ // 添加retrofit依赖
+ implementation rootProject.ext.dependencies.retrofit
+ // 添加retrofit转化gson能力依赖
+ implementation rootProject.ext.dependencies.converter_gson
+ // 添加rxjava依赖
+ implementation rootProject.ext.dependencies.rxjava
+ // 添加rxAndroid依赖
+ implementation rootProject.ext.dependencies.rxandroid
+ // 添加retrofit和rxjava适配器
+ implementation rootProject.ext.dependencies.retrofit_rxjava
//luban图片压缩
implementation rootProject.ext.dependencies.luban
diff --git a/commonLib/src/main/assets/baseUrl.properties b/commonLib/src/main/assets/baseUrl.properties
new file mode 100644
index 0000000..8f9b83a
--- /dev/null
+++ b/commonLib/src/main/assets/baseUrl.properties
@@ -0,0 +1,2 @@
+debug1 = https://www.wanandroid.com
+debug2 = https://www.baidu.com
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/CommonApplication.kt b/commonLib/src/main/java/com/yinuo/commonlib/CommonApplication.kt
new file mode 100644
index 0000000..7fc9f2e
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/CommonApplication.kt
@@ -0,0 +1,17 @@
+package com.yinuo.commonlib
+
+import android.annotation.SuppressLint
+import android.content.Context
+
+@SuppressLint("StaticFieldLeak")
+object CommonApplication {
+ private var commonContext: Context? = null
+
+ fun intLibs(context: Context) {
+ commonContext = context
+ }
+
+ fun getContext(): Context? {
+ return commonContext
+ }
+}
\ No newline at end of file
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/net/BaseObserve.kt b/commonLib/src/main/java/com/yinuo/commonlib/net/BaseObserve.kt
new file mode 100644
index 0000000..1eda43a
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/net/BaseObserve.kt
@@ -0,0 +1,98 @@
+package com.common.commonlib.net
+
+import android.net.ParseException
+import android.util.Log
+import com.google.gson.JsonParseException
+import io.reactivex.Observable
+import io.reactivex.Observer
+import io.reactivex.android.schedulers.AndroidSchedulers
+import io.reactivex.disposables.Disposable
+import io.reactivex.schedulers.Schedulers
+import org.json.JSONException
+import retrofit2.HttpException
+import java.net.ConnectException
+import java.net.SocketTimeoutException
+import java.net.UnknownHostException
+import javax.net.ssl.SSLHandshakeException
+
+/**
+ * 请求基类
+ */
+open class BaseObserve {
+ /**
+ * 初始化服务类
+ */
+ fun initService(clazz: Class): T {
+ return RequestManager.INSTANCE.create(clazz)
+ }
+
+ /**
+ * 调用接口
+ * @param observable 可订阅
+ * @param callBack 请求回调
+ */
+ fun observe(observable: Observable, callBack: RequestCallBack?) {
+ observable
+ .subscribeOn(Schedulers.io())
+ .unsubscribeOn(Schedulers.io())
+ .observeOn(AndroidSchedulers.mainThread())
+ .subscribe(object : Observer {
+ override fun onSubscribe(d: Disposable) {
+ }
+
+ override fun onNext(t: R) {
+ callBack?.onResult(t)
+ }
+
+ override fun onError(e: Throwable) {
+ e.message?.let { Log.e(TAG, it) }
+ callBack?.onError(dealError(e))
+ }
+
+ override fun onComplete() {
+ callBack?.onComplete()
+ }
+ })
+ }
+
+ /**
+ * 处理错误
+ * @param e 异常
+ */
+ private fun dealError(e: Throwable): String? {
+ if (e is HttpException) {
+ return when (e.code()) {
+ UNAUTHORIZED -> "登录验证过期"
+ INTERNAL_SERVER_ERROR -> "服务器错误"
+ FORBIDDEN, NOT_FOUND -> "无效的请求"
+ REQUEST_TIMEOUT, GATEWAY_TIMEOUT, BAD_GATEWAY, SERVICE_UNAVAILABLE -> e.message()
+ else -> e.message()
+ }
+ } else if (e is ConnectException) {
+ return "网络连接异常,请检查您的网络状态"
+ } else if (e is SocketTimeoutException) {
+ return "网络连接超时,请检查您的网络状态,稍后重试"
+ } else if (e is UnknownHostException) {
+ return "网络异常,请检查您的网络状态"
+ } else if (e is JsonParseException || e is JSONException || e is ParseException) {
+ return "数据解析错误"
+ } else if (e is SSLHandshakeException) {
+ return "网络异常,请检查您的网络状态"
+ } else if (e is RuntimeException) {
+ return "运行时异常"
+ }
+ return e.message
+ }
+
+ companion object {
+ const val TAG: String = "BaseLoader"
+ const val UNAUTHORIZED = 401
+ const val FORBIDDEN = 403
+ const val NOT_FOUND = 404
+ const val REQUEST_TIMEOUT = 408
+ const val INTERNAL_SERVER_ERROR = 500
+ const val BAD_GATEWAY = 502
+ const val SERVICE_UNAVAILABLE = 503
+ const val GATEWAY_TIMEOUT = 504
+ }
+}
\ No newline at end of file
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/net/RequestCallBack.kt b/commonLib/src/main/java/com/yinuo/commonlib/net/RequestCallBack.kt
new file mode 100644
index 0000000..4f290af
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/net/RequestCallBack.kt
@@ -0,0 +1,10 @@
+package com.common.commonlib.net
+
+/**
+ * 请求回调
+ */
+interface RequestCallBack {
+ fun onResult(result: T)
+ fun onError(error: String?)
+ fun onComplete()
+}
\ No newline at end of file
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/net/RequestManager.kt b/commonLib/src/main/java/com/yinuo/commonlib/net/RequestManager.kt
new file mode 100644
index 0000000..a4ea8a0
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/net/RequestManager.kt
@@ -0,0 +1,51 @@
+package com.common.commonlib.net
+
+import com.yinuo.commonlib.net.interceptor.BaseUrlInterceptor
+import com.yinuo.commonlib.net.interceptor.HttpCommonInterceptor
+import okhttp3.OkHttpClient
+import retrofit2.Retrofit
+import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory
+import retrofit2.converter.gson.GsonConverterFactory
+import java.util.concurrent.TimeUnit
+
+/**
+ * 网络请求管理器
+ */
+enum class RequestManager {
+ INSTANCE;
+
+ /**
+ * 默认超时时间
+ */
+ private val defaultTimeOut: Long = 5
+
+ /**
+ * 默认读取超时时间
+ */
+ private val defaultReadTimeOut: Long = 10
+
+ private var mRetrofit: Retrofit? = null
+
+ init {
+ val builder: OkHttpClient.Builder = OkHttpClient.Builder()
+ builder.connectTimeout(defaultTimeOut, TimeUnit.SECONDS)
+ builder.readTimeout(defaultReadTimeOut, TimeUnit.SECONDS)
+ val commonInterceptor: HttpCommonInterceptor = HttpCommonInterceptor.Builder().build()
+ builder.addInterceptor(commonInterceptor)
+ builder.addInterceptor(BaseUrlInterceptor())
+
+ mRetrofit = Retrofit.Builder()
+ .client(builder.build())
+ .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
+ .addConverterFactory(GsonConverterFactory.create())
+ .baseUrl("https://www.wanandroid.com")
+ .build()
+ }
+
+ /**
+ * 创建service
+ */
+ fun create(service: Class): T {
+ return mRetrofit!!.create(service)
+ }
+}
\ No newline at end of file
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/net/bean/BaseResponse.kt b/commonLib/src/main/java/com/yinuo/commonlib/net/bean/BaseResponse.kt
new file mode 100644
index 0000000..f5d894d
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/net/bean/BaseResponse.kt
@@ -0,0 +1,21 @@
+package com.yinuo.commonlib.net.bean
+
+import android.os.Parcelable
+import kotlinx.android.parcel.Parcelize
+
+/**
+ * 基础响应类
+ */
+@Parcelize
+open class BaseResponse : Parcelable {
+ var errorCode: Int = 0
+ var errorMessage: String = ""
+
+ fun getMErrorCode(): Int {
+ return errorCode
+ }
+
+ fun getMErrorMessage(): String {
+ return errorMessage
+ }
+}
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/net/bean/RequestParam.kt b/commonLib/src/main/java/com/yinuo/commonlib/net/bean/RequestParam.kt
new file mode 100644
index 0000000..b81cf00
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/net/bean/RequestParam.kt
@@ -0,0 +1,9 @@
+package com.yinuo.commonlib.net.bean
+
+/**
+ * 请求参数
+ */
+data class RequestParam(var baseUrl: String) {
+ var params: Map? = null
+}
+
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/net/interceptor/BaseUrlInterceptor.kt b/commonLib/src/main/java/com/yinuo/commonlib/net/interceptor/BaseUrlInterceptor.kt
new file mode 100644
index 0000000..95d1640
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/net/interceptor/BaseUrlInterceptor.kt
@@ -0,0 +1,83 @@
+package com.yinuo.commonlib.net.interceptor
+
+import android.text.TextUtils
+import android.util.Log
+import com.yinuo.commonlib.BuildConfig
+import com.yinuo.commonlib.CommonApplication
+import okhttp3.HttpUrl
+import okhttp3.HttpUrl.Companion.toHttpUrlOrNull
+import okhttp3.Interceptor
+import okhttp3.Request
+import okhttp3.Response
+import java.io.BufferedInputStream
+import java.util.*
+
+/**
+ * BaseUrl链接拦截器
+ */
+class BaseUrlInterceptor : Interceptor {
+ /**
+ * 拦截替换BaseUrl
+ */
+ override fun intercept(chain: Interceptor.Chain): Response {
+ val oldRequest: Request = chain.request()
+ val requestBuilder: Request.Builder = oldRequest.newBuilder()
+ val headKey = BASE_URL_KEY
+ val headValue: String? = oldRequest.header(headKey)
+ // 判断是否需要替换BaseUrl,不需要则直接跳转
+ if (TextUtils.isEmpty(headValue)) {
+ return chain.proceed(chain.request())
+ }
+ // 该HEAD只用于替换BaseUrl,将对应的自定义HEAD去除
+ requestBuilder.removeHeader(headKey)
+ // 尝试获取新BaseUrl
+ val newUrlValue = getValueFromProperties(headValue)
+ val newBaseUrl: HttpUrl? = newUrlValue.toHttpUrlOrNull()
+ // 获取到新BaseUrl进行替换
+ return if (newBaseUrl != null) {
+ val oldHttpUrl: HttpUrl = oldRequest.url
+ val newUrl = oldHttpUrl.newBuilder()
+ .scheme(newBaseUrl.scheme)
+ .host(newBaseUrl.host)
+ .port(newBaseUrl.port)
+ .build()
+ chain.proceed(requestBuilder.url(newUrl).build())
+ } else {
+ chain.proceed(chain.request())
+ }
+ }
+
+ /**
+ * 通过KEY从配置文件中获取值
+ */
+ private fun getValueFromProperties(key: String?): String {
+ val prop = Properties()
+ var value = ""
+ try {
+ val context = CommonApplication.getContext()
+ if (context == null) {
+ Log.e(TAG, "got context null, please init context!")
+ return value
+ }
+ val mAssets = context.assets
+ if (mAssets == null) {
+ Log.e(TAG, "got assets null, please check the assets folder")
+ }
+ // 通过输入缓冲流进行读取配置文件
+ val inputStream =
+ BufferedInputStream(mAssets.open((BuildConfig.BASE_URL_CONFIG_PATH)))
+ // 加载输入流
+ prop.load(inputStream)
+ // 根据关键字获取value值
+ value = prop.getProperty(key);
+ } catch (e: Exception) {
+ Log.e(TAG, e.toString())
+ }
+ return value
+ }
+
+ companion object {
+ const val TAG = "BaseUrlInterceptor"
+ const val BASE_URL_KEY = "baseurl"
+ }
+}
\ No newline at end of file
diff --git a/commonLib/src/main/java/com/yinuo/commonlib/net/interceptor/HttpCommonInterceptor.kt b/commonLib/src/main/java/com/yinuo/commonlib/net/interceptor/HttpCommonInterceptor.kt
new file mode 100644
index 0000000..b4d40a0
--- /dev/null
+++ b/commonLib/src/main/java/com/yinuo/commonlib/net/interceptor/HttpCommonInterceptor.kt
@@ -0,0 +1,70 @@
+package com.yinuo.commonlib.net.interceptor
+
+import okhttp3.Interceptor
+import okhttp3.Request
+import okhttp3.Response
+
+/**
+ * 公共请求拦截器
+ */
+class HttpCommonInterceptor : Interceptor {
+ /**
+ * 请求头部参数
+ */
+ var mHeaderHashMap: HashMap? = null
+
+ /**
+ * 拦截请求并添加参数
+ */
+ override fun intercept(chain: Interceptor.Chain): Response {
+ val oldRequest: Request = chain.request()
+ val requestBuilder: Request.Builder = oldRequest.newBuilder()
+ requestBuilder.method(oldRequest.method, oldRequest.body)
+ if (mHeaderHashMap != null && mHeaderHashMap!!.size > 0) {
+ for (item: Map.Entry in mHeaderHashMap!!.entries) {
+ requestBuilder.addHeader(item.key, item.value)
+ }
+ }
+ return chain.proceed(requestBuilder.build())
+ }
+
+ /**
+ * builder构造函数
+ */
+ class Builder {
+ private var mHttpCommonInterceptor: HttpCommonInterceptor? = null
+
+ init {
+ mHttpCommonInterceptor = HttpCommonInterceptor()
+ }
+
+ fun addHeadParams(key: String, value: String): Builder {
+ mHttpCommonInterceptor?.mHeaderHashMap?.set(key, value)
+ return this
+ }
+
+ fun addHeadParams(key: String, value: Int): Builder {
+ mHttpCommonInterceptor?.mHeaderHashMap?.set(key, value.toString())
+ return this
+ }
+
+ fun addHeadParams(key: String, value: Long): Builder {
+ mHttpCommonInterceptor?.mHeaderHashMap?.set(key, value.toString())
+ return this
+ }
+
+ fun addHeadParams(key: String, value: Float): Builder {
+ mHttpCommonInterceptor?.mHeaderHashMap?.set(key, value.toString())
+ return this
+ }
+
+ fun addHeadParams(key: String, value: Double): Builder {
+ mHttpCommonInterceptor?.mHeaderHashMap?.set(key, value.toString())
+ return this
+ }
+
+ fun build(): HttpCommonInterceptor {
+ return mHttpCommonInterceptor!!
+ }
+ }
+}
\ No newline at end of file
diff --git a/yinuoapp.jks b/yinuoapp.jks
new file mode 100644
index 0000000..3ddd979
Binary files /dev/null and b/yinuoapp.jks differ