desc:封装心跳和文件上传联调成功

main
xiaowusky 2 years ago
parent 8500eaf385
commit 8c107e5711

@ -30,6 +30,7 @@
android:allowBackup="true" android:allowBackup="true"
android:icon="@mipmap/ic_launcher" android:icon="@mipmap/ic_launcher"
android:label="@string/app_name" android:label="@string/app_name"
android:networkSecurityConfig="@xml/network_security_config"
android:roundIcon="@mipmap/ic_launcher_round" android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true" android:supportsRtl="true"
android:theme="@style/AppTheme"> android:theme="@style/AppTheme">

@ -1,10 +1,10 @@
package com.yinuo.safetywatcher.watcher package com.yinuo.safetywatcher.watcher
import android.app.Application import com.common.commonlib.CommonApplication
import com.lztek.toolkit.Lztek import com.lztek.toolkit.Lztek
import com.yinuo.safetywatcher.watcher.utils.LztekUtil import com.yinuo.safetywatcher.watcher.utils.LztekUtil
class App : Application() { class App : CommonApplication() {
override fun onCreate() { override fun onCreate() {
super.onCreate() super.onCreate()

@ -4,8 +4,8 @@ import com.common.commonlib.net.BaseObserve
import com.common.commonlib.net.bean.BaseResponse import com.common.commonlib.net.bean.BaseResponse
import com.common.commonlib.net.callback.RequestNoResultCallBack import com.common.commonlib.net.callback.RequestNoResultCallBack
import io.reactivex.rxjava3.core.Observable import io.reactivex.rxjava3.core.Observable
import retrofit2.http.FormUrlEncoded
import retrofit2.http.GET import retrofit2.http.GET
import retrofit2.http.Headers
import retrofit2.http.Query import retrofit2.http.Query
/** /**
@ -13,7 +13,7 @@ import retrofit2.http.Query
*/ */
class HeartbeatApi : BaseObserve<HeartbeatApi.Api>(Api::class.java) { class HeartbeatApi : BaseObserve<HeartbeatApi.Api>(Api::class.java) {
open fun heartBeat(sn: String) { fun heartBeat(sn: String) {
observe(api.heartBeat(sn), object : RequestNoResultCallBack<BaseResponse>() { observe(api.heartBeat(sn), object : RequestNoResultCallBack<BaseResponse>() {
override fun onError(error: String?) { override fun onError(error: String?) {
} }
@ -25,8 +25,8 @@ class HeartbeatApi : BaseObserve<HeartbeatApi.Api>(Api::class.java) {
interface Api { interface Api {
@GET("xx/xxx") @Headers("baseurl:host")
@FormUrlEncoded @GET("/api/device/refresh")
fun heartBeat(@Query("sn") sn: String): Observable<BaseResponse> fun heartBeat(@Query("deviceSn") sn: String): Observable<BaseResponse>
} }
} }

@ -3,26 +3,30 @@ package com.yinuo.safetywatcher.watcher.net
import com.common.commonlib.net.BaseObserve import com.common.commonlib.net.BaseObserve
import com.common.commonlib.net.bean.BaseResponse import com.common.commonlib.net.bean.BaseResponse
import com.common.commonlib.net.callback.RequestResultCallBack import com.common.commonlib.net.callback.RequestResultCallBack
import com.yinuo.safetywatcher.watcher.utils.LztekUtil
import io.reactivex.rxjava3.core.Observable import io.reactivex.rxjava3.core.Observable
import okhttp3.MediaType.Companion.toMediaTypeOrNull import okhttp3.MediaType.Companion.toMediaTypeOrNull
import okhttp3.MultipartBody import okhttp3.MultipartBody
import okhttp3.RequestBody import okhttp3.RequestBody
import okhttp3.RequestBody.Companion.asRequestBody import okhttp3.RequestBody.Companion.asRequestBody
import okhttp3.RequestBody.Companion.toRequestBody
import retrofit2.http.Headers
import retrofit2.http.Multipart import retrofit2.http.Multipart
import retrofit2.http.POST import retrofit2.http.POST
import retrofit2.http.Part import retrofit2.http.Part
import retrofit2.http.PartMap import retrofit2.http.PartMap
import java.io.File import java.io.File
const val FORM_DATA = "multipart/form-data";
/** /**
* 文件上传 * 文件上传
*/ */
class UploadFileApi : BaseObserve<UploadFileApi.Api>(Api::class.java) { class UploadFileApi : BaseObserve<UploadFileApi.Api>(Api::class.java) {
open fun singleUpload(path: String) { open fun singleUpload(path: String, videoTime: Long) {
observe( observe(
api.singleUpload(makeMultipartBodyPart(path)), api.singleUpload(makeParamsMaps(videoTime), makeFileBodyPart(path)),
object : RequestResultCallBack<BaseResponse>() { object : RequestResultCallBack<BaseResponse>() {
override fun onResult(result: BaseResponse) { override fun onResult(result: BaseResponse) {
} }
@ -32,45 +36,30 @@ class UploadFileApi : BaseObserve<UploadFileApi.Api>(Api::class.java) {
}) })
} }
open fun multiUpload(paths: List<String>) {
observe(
api.multiUpload(makefileMaps(paths)),
object : RequestResultCallBack<BaseResponse>() {
override fun onResult(result: BaseResponse) {
}
override fun onError(error: String?) {
}
})
}
interface Api { interface Api {
@Headers("baseurl:host")
@Multipart @Multipart
@POST("xxx/upload") @POST("/common/uploadVideo")
fun singleUpload(@Part file: MultipartBody.Part?): Observable<BaseResponse> fun singleUpload(
@PartMap params: Map<String, @JvmSuppressWildcards RequestBody>,
@Multipart @Part file: MultipartBody.Part
@POST("xxx/uploads") ): Observable<BaseResponse>
fun multiUpload(@PartMap fileMap: Map<String, MultipartBody.Part>): Observable<BaseResponse>
} }
private fun makefileMaps(paths: List<String>): Map<String, MultipartBody.Part> { private fun makeFileBodyPart(path: String): MultipartBody.Part {
val map = HashMap<String, MultipartBody.Part>()
paths.forEach {
val file = File(it)
val part = makeMultipartBodyPart(it)
map["file; filename=${file.name}"] = part
}
return map
}
private fun makeMultipartBodyPart(path: String): MultipartBody.Part {
val file = File(path) val file = File(path)
//构建requestbody //构建requestBody
val requestFile: RequestBody = val requestFile: RequestBody =
file.asRequestBody("multipart/form-data".toMediaTypeOrNull()) file.asRequestBody(FORM_DATA.toMediaTypeOrNull())
//将resquestbody封装为MultipartBody.Part对象 //将requestBody封装为MultipartBody.Part对象
return MultipartBody.Part.createFormData("file", file.name, requestFile) return MultipartBody.Part.createFormData("file", file.name, requestFile)
} }
private fun makeParamsMaps(videoTime: Long): Map<String, RequestBody> {
val map = HashMap<String, RequestBody>()
map["deviceSn"] = LztekUtil.getSn().toRequestBody(FORM_DATA.toMediaTypeOrNull())
map["videoTime"] =
videoTime.toString().toRequestBody(FORM_DATA.toMediaTypeOrNull())
return map
}
} }

@ -1,9 +1,12 @@
package com.yinuo.safetywatcher.watcher.services package com.yinuo.safetywatcher.watcher.services
import android.annotation.SuppressLint
import android.app.IntentService import android.app.IntentService
import android.content.Context import android.content.Context
import android.content.Intent import android.content.Intent
import android.util.Log import com.yinuo.safetywatcher.watcher.net.HeartbeatApi
import com.yinuo.safetywatcher.watcher.utils.LztekUtil
private const val ACTION_START = "com.yinuo.safetywatcher.watcher.services.action.Heartbeat" private const val ACTION_START = "com.yinuo.safetywatcher.watcher.services.action.Heartbeat"
@ -12,6 +15,10 @@ private const val ACTION_START = "com.yinuo.safetywatcher.watcher.services.actio
*/ */
class HeartbeatService : IntentService("HeartbeatService") { class HeartbeatService : IntentService("HeartbeatService") {
private val heartbeatApi by lazy {
HeartbeatApi()
}
override fun onHandleIntent(intent: Intent?) { override fun onHandleIntent(intent: Intent?) {
when (intent?.action) { when (intent?.action) {
ACTION_START -> { ACTION_START -> {
@ -20,8 +27,9 @@ class HeartbeatService : IntentService("HeartbeatService") {
} }
} }
@SuppressLint("HardwareIds")
private fun handleActionStart(intent: Intent) { private fun handleActionStart(intent: Intent) {
Log.i("cyy", "heartBeat") heartbeatApi.heartBeat(LztekUtil.getSn())
Thread.sleep(30000) Thread.sleep(30000)
handleActionStart(intent) handleActionStart(intent)
} }

@ -4,12 +4,18 @@ import android.view.View
import com.yinuo.safetywatcher.R import com.yinuo.safetywatcher.R
import com.yinuo.safetywatcher.databinding.ActivityCloudBinding import com.yinuo.safetywatcher.databinding.ActivityCloudBinding
import com.yinuo.safetywatcher.watcher.base.NoOptionsActivity import com.yinuo.safetywatcher.watcher.base.NoOptionsActivity
import com.yinuo.safetywatcher.watcher.net.UploadFileApi
import com.yinuo.safetywatcher.xls.utils.PathUtils
class CloudActivity : NoOptionsActivity() { class CloudActivity : NoOptionsActivity() {
private val mBinding: ActivityCloudBinding by lazy { private val mBinding: ActivityCloudBinding by lazy {
ActivityCloudBinding.inflate(layoutInflater) ActivityCloudBinding.inflate(layoutInflater)
} }
private val uploadApi by lazy {
UploadFileApi()
}
override fun getTopBarTitle(): String? { override fun getTopBarTitle(): String? {
return getString(R.string.cloud) return getString(R.string.cloud)
} }
@ -21,8 +27,10 @@ class CloudActivity : NoOptionsActivity() {
override fun initView() { override fun initView() {
mBinding.apply { mBinding.apply {
syncSensor.setOnClickListener { } syncSensor.setOnClickListener { }
syncWarn.setOnClickListener { } syncVedio.setOnClickListener {
syncVedio.setOnClickListener { } val path = PathUtils.getExternalStorageDirectory() + "/test2.mp4"
uploadApi.singleUpload(path, System.currentTimeMillis())
}
syncOnce.setOnClickListener { } syncOnce.setOnClickListener { }
} }
} }

@ -1,11 +1,15 @@
package com.yinuo.safetywatcher.watcher.utils package com.yinuo.safetywatcher.watcher.utils
import com.lztek.toolkit.Lztek import com.lztek.toolkit.Lztek
import java.math.BigInteger
import java.security.MessageDigest
object LztekUtil { object LztekUtil {
private var mLztek: Lztek? = null; private var mLztek: Lztek? = null;
private var sn: String? = null;
fun setObject(value: Lztek) { fun setObject(value: Lztek) {
mLztek = value mLztek = value
} }
@ -13,4 +17,26 @@ object LztekUtil {
fun getLztek(): Lztek { fun getLztek(): Lztek {
return mLztek!! return mLztek!!
} }
fun getSn(): String {
if (sn == null) {
val mac = LztekUtil.getLztek().ethMac ?: "unKnow"
val md = MessageDigest.getInstance("MD5") // 生成一个MD5加密计算摘要
md.update(mac.toByteArray()) // 计算md5函数
/**
* digest()最后确定返回md5 hash值返回值为8位字符串
* 因为md5 hash值是16位的hex值实际上就是8位的字符
* BigInteger函数则将8位的字符串转换成16位hex值用字符串来表示得到字符串形式的hash值
* 一个byte是八位二进制也就是2位十六进制字符2的8次方等于16的2次方
*/
/**
* digest()最后确定返回md5 hash值返回值为8位字符串
* 因为md5 hash值是16位的hex值实际上就是8位的字符
* BigInteger函数则将8位的字符串转换成16位hex值用字符串来表示得到字符串形式的hash值
* 一个byte是八位二进制也就是2位十六进制字符2的8次方等于16的2次方
*/
sn = BigInteger(1, md.digest()).toString(16) // 16是表示转换为16进制数
}
return sn!!
}
} }

@ -16,7 +16,7 @@
android:textColor="@color/white" android:textColor="@color/white"
android:textSize="@dimen/_30dp" /> android:textSize="@dimen/_30dp" />
<TextView <!--<TextView
android:id="@+id/sync_warn" android:id="@+id/sync_warn"
android:layout_width="@dimen/_340dp" android:layout_width="@dimen/_340dp"
android:layout_height="@dimen/_100dp" android:layout_height="@dimen/_100dp"
@ -25,7 +25,7 @@
android:gravity="center" android:gravity="center"
android:text="@string/sync_warn_txt" android:text="@string/sync_warn_txt"
android:textColor="@color/white" android:textColor="@color/white"
android:textSize="@dimen/_30dp" /> android:textSize="@dimen/_30dp" />-->
<TextView <TextView
android:id="@+id/sync_vedio" android:id="@+id/sync_vedio"

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<network-security-config>
<base-config cleartextTrafficPermitted="true" />
</network-security-config>

@ -1,2 +1,2 @@
debug1 = https://www.wanandroid.com host=http://192.168.5.6:8080
debug2 = https://www.baidu #host=http://192.168.51.123:8080

Loading…
Cancel
Save