赞
踩
网络请求时需要用户确定请求的权限,在xml中加入网络请求的权限
<uses-permission android:name="android.permission.INTERNET"/>
网络请求的简单实现
class HttpURLConnectionTest:AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.internet_layout) //第一种请求网络的方式HttpURLConnection get_date_by_url.setOnClickListener(){ sendRequestWithHttpUrl() } } private fun sendRequestWithHttpUrl(){ thread{ var connection:HttpURLConnection?=null try{ val response=StringBuilder() val url= URL("https://www.baidu.com") connection=url.openConnection() as HttpURLConnection connection.connectTimeout=8000 connection.readTimeout=8000 //指定请求方式 // connection.requestMethod="Post" //网络输出,附带参数请求 //val output=DataOutputStream(connection.outputStream) //output.writeBytes("username=admin&password=121231") //网络响应输入 val input=connection.inputStream val reader=BufferedReader(InputStreamReader(input)) reader.use{ reader.forEachLine { response.append(it) } } showResponse(response.toString()) }catch (e:Exception){ e.printStackTrace() }finally { //断开连接 connection?.disconnect() } } } private fun showResponse(response:String){ //此方法可以进行异步的ui界面更新 runOnUiThread { response_data.text=response } } }
首先需要在build.gradle文件中引入OkHttp的依赖,指定版本
//加入OKhttp的
implementation 'com.squareup.okhttp3:okhttp:4.9.0'
class HttpURLConnectionTest:AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.internet_layout) get_date_by_okHttp.setOnClickListener(){ sendRequestWithOkHttp() } } private fun sendRequestWithOkHttp(){ thread { try { val client= OkHttpClient() val request= Request.Builder() .url("https://www.baidu.com") .build() val response=client.newCall(request).execute() val responseData=response.body?.string() if(responseData!=null){ showResponse(responseData) } }catch (e:Exception){ e.printStackTrace() } } } private fun showResponse(response:String){ //此方法可以进行异步的ui界面更新 runOnUiThread { response_data.text=response } } }
注意如果使用OkHttpClient报错java.lang.ExceptionInInitializerError。可能是OKhttp包的引入版本问题,重新下载合适版本即可。
在有请求且比较少的时候,直接在代码中使用OKHttp也是可以的,但是如果请求过多,不可能将请求全都放在项目代码里,所以需要对请求的方法进行一个提取抽象到工具类里面,来实现更加简单的调用。并且在进行子线程任务时,需要将结果返回到主线程,所以需要使用回调接口的方式进行数据更新
在使用HttpURLRequest时需要自定义接口
interface HttpCallbackListener {
fun onFinish(response:String)
fun onError(e:Exception)
}
然后在工具类中进行方法的封装和回调接口的调用
object HttpUtil { fun sendHttpRequest(address:String,listener:HttpCallbackListener){ thread { var connection:HttpURLConnection?=null try{ val response=StringBuilder() val url=URL(address) connection=url.openConnection() as HttpURLConnection connection.connectTimeout=8000 connection.readTimeout=8000 val input=connection.inputStream val reader=BufferedReader(InputStreamReader(input)) reader.use { reader.forEachLine { response.append(it) } } listener.onFinish(response.toString()) }catch (e:Exception){ e.printStackTrace() listener.onError(e) }finally { connection?.disconnect() } } } //使用OkHttp的方法 fun sendOKHttpRequest(address:String,callback:okhttp3.Callback){ val client=OkHttpClient() val request=Request.Builder() .url(address) .build() //在enqueue的内部已经开启了子线程 client.newCall(request).enqueue(callback) }
使用方法
class HttpURLConnectionTest:AppCompatActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.internet_layout) //使用工具类进行逻辑的编写 get_date_by_util_Httpurl.setOnClickListener{ HttpUtil.sendHttpRequest("https://www.baidu.com",object :HttpCallbackListener{ override fun onFinish(response: String) { showResponse(response) } override fun onError(e: Exception) { println("在这里进行异常的处理") } }) } get_date_by_util_okHttp.setOnClickListener(){ HttpUtil.sendOKHttpRequest("https://www.baidu.com",object:Callback{ override fun onFailure(call: Call, e: IOException) { println("失败的话打印异常处理") } override fun onResponse(call: Call, response: Response) { val responseData=response.body?.string() if (responseData != null) { showResponse(responseData) } } }) } } private fun showResponse(response:String){ //此方法可以进行异步的ui界面更新 runOnUiThread { response_data.text=response } } }
Retrofit是在OKHttp基础之上的一个综合框架,有着更好的数据请求规范和响应规范
implementation 'com.squareup.retrofit2:retrofit:2.6.1'
implementation 'com.squareup.retrofit2:converter-gson:2.6.1'
class Student(val id:Int,val name:String,val className:String) {
}
interface StudentService {
//这里指定了网站下具体的资源地址
@GET("gete.json")
fun getStudentInfo(): Call<List<Student>>
}
use_Retrofit.setOnClickListener(){ val retrofit=Retrofit.Builder() //会和Service中的地址进行组合,来确定成为一个唯一的请求地址 .baseUrl("基础地址") .addConverterFactory(GsonConverterFactory.create()) .build() val studentService=retrofit.create(StudentService::class.java) studentService.getStudentInfo().enqueue(object:retrofit2.Callback<List<Student>>{ override fun onResponse( call: retrofit2.Call<List<Student>>, response: retrofit2.Response<List<Student>> ) { val students=response.body() if(students!=null){ for(student in students){ println("输出学生的信息${student.id}等即可") } } } //处理异常 override fun onFailure(call: retrofit2.Call<List<Student>>, t: Throwable) { t.printStackTrace() } }) }
interface StudentService { //这里指定了网站下具体的资源地址 @GET("/user/Student/getStudent.json") fun getStudentInfo(): Call<List<Student>> //处理路径中带有可变参数的情况,关键词Path @GET("{page}/getStudent.json") fun getStudentInfoByPage(@Path("page") page:Int):Call<List<Student>> //处理Get请求时路径中带有参数的情况关键词Query @GET("/user/Student/getStudent.json") fun getStudentInfoByNameAndClassName(@Query("name") name:String,@Query("calssName") className:String):Call<List<Student>> //按照id删除一个学生,如果对返回值不关心,就是用Call<ResponseBody>代替 @DELETE("/user/Student/{id}") fun deleteById(@Path("id") id:Int):Call<ResponseBody> //如果想要提交数据,直接按照对象进行提交 @POST("user/Student") fun createStudent(@Body student:Student):Call<ResponseBody> //如果希望在请求头header中加入请求参数,就按照键值对的方式进行填充数据静态方式 @Headers("User-Agent:okHttp","Cache-Control:max-age=0") @GET("地址") fun getStudentBy():Call<Student> //动态 @GET("地址2") fun getStudentByDynamic( @Header("User-Agent") userAgent:String, @Header("Cache-Control") cache_control:String):Call<Student> } }
在工具累中进行处理
object ServiceCreator {
private const val BASE_URL="自己的基础访问地址"
private val retrofit=Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.build()
//只提供一个方法即可对外返回创建的Service实例
fun <T> create(serviceClass: Class<T>):T= retrofit.create(serviceClass)
}
使用方法
use_Retrofit.setOnClickListener(){ /*val retrofit=Retrofit.Builder() .baseUrl("基础地址") .addConverterFactory(GsonConverterFactory.create()) .build()*/ val studentService=ServiceCreator.create(StudentService::class.java) studentService.getStudentInfo().enqueue(object:retrofit2.Callback<List<Student>>{ override fun onResponse( call: retrofit2.Call<List<Student>>, response: retrofit2.Response<List<Student>> ) { val students=response.body() if(students!=null){ for(student in students){ println("输出学生的信息${student.id}等即可") } } } //处理异常 override fun onFailure(call: retrofit2.Call<List<Student>>, t: Throwable) { t.printStackTrace() } }) }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。