当前位置:首页 > 行业动态 > 正文

如何优化Android客户端与服务器之间的通信效率?

android客户端与服务器通信主要通过http或https协议,使用json或xml格式交换数据,常见库有volley, okhttp等。

Android客户端与服务器交互详解

如何优化Android客户端与服务器之间的通信效率?  第1张

一、基本概念与通信方式

1. Android客户端与服务器端通信方式

1.1 HTTP通信

HTTP通信是客户端向服务器发送一条请求,服务器收到后解析请求并返回数据,HTTP连接采取“请求—响应”的方式,即在请求时建立连接通道,客户端发送请求后,服务器再回复数据,这种方式适用于不需要时刻保持连接的场景,如获取资源、文件上传等。

1.2 Socket通信

Socket又称套接字,提供了与外界通信的端口,通过建立socket连接,双方可以进行数据传输,Socket的主要特点包括数据丢失率低、使用简单且易于移植,Socket通信类似于peer to peer的连接,一方可随时向另一方发送数据。

数据交互方式

2.1 数据流

从web服务器响应到手机终端的数据一般打包在一个字节数组中,这个字节数据包含了不同的数据类型,客户端采用Java数据流和过滤流的方式从字节数组中取出各种类型的数据。

2.2 XML

XML是WebService的标准数据格式。

2.3 Protocol Buffers

Protocol Buffers是一种轻便高效的结构化数据存储格式,适合做数据存储或RPC数据交换格式,其最大的优点是传输时数据体积可以压缩很小,传输效率比较高。

2.4 JSON

JSON是一种轻量级的数据交换格式,易于人阅读和编写,同时也易于机器解析和生成,JSON是目前最常用的数据交换格式之一。

二、服务器开发规范与RESTful API

RESTful API简介

RESTful是目前最流行的API设计规范,用于web数据接口的设计,它的核心原则是定义用少量方法就能操作的命名资源,RESTful API具有以下优点:

面向资源(URI):具有解释性。

行为与资源分离:更加轻量化。

数据描述简单:使用JSON、XML、Protocol Buffers即可全覆盖,主要使用JSON。

HTTP请求方式

GET:读取(Read)。

POST:新建(Create)。

PUT:更新(Update),通常是全部更新。

PATCH:更新(Update),通常是部分更新。

DELETE:删除(Delete)。

项目初期,客户端和服务器一般使用Get和Post的方式进行交互,随着业务的演进和技术的规范迭代,后期都会按规范来设计服务器接口,移动端的请求方式也得与之对应。

三、Json交互数据类型与实际运用

JSON数据类型

JSON的值只有六种数据类型:

Number:整数或浮点数。

String:字符串。

Boolean:true 或 false。

Array:数组包含在方括号[]中。

Object:对象包含在大括号{}中。

Null:空类型。

传输的数据类型不能超过这六种数据类型,不能用Date数据类型,不同的解析库解析方式不同,可能会导致异常,如果遇到日期的数据,最好的方式就是使用毫秒数表示日期。

String的数据类型

String的数据类型通常用于返回状态和提示信息,例如用户退出登录时:

{
    "code": 1000,
    "message": "成功"
}

数据解析工具类:

abstract class BaseStringCallback: BaseCallback() {
    override fun onSuccess(data: String) {
        val responseData = JSONObject(data)
        val code = responseData.getInt("code")
        val message = responseData.getString("message")
        if (code == 1000) {
            success(message)
        } else {
            //其他状态处理
        }
    }
    abstract fun success(msg: String)
}

调用时(伪代码):

LogoutApi.execute(object : BaseStringCallback() {
                    override fun success(msg: String) {
                        //处理数据
                    }

Object数据类型

识别标示为:{},例如获取当前用户信息,返回owner实体类:

{
    "code": 1000,
    "message": "成功",
    "resp": {
        "owner": {
            "id": 58180,
            "name": "张三",
            "idCert": "",
            "certType": 1,
            "modifier": "jun5753"
        }
    }
}

数据解析工具类:

abstract class BaseOwnerCallback: BaseCallback() {
    override fun onSuccess(data: String) {
        val responseData = JSONObject(data)
        val code = responseData.getInt("code")
        val message = responseData.getString("message")
        if (code == 1000) {
            val owner = Gson().fromJson<Owner>(responseData.getJSONObject("resp").getJSONObject("owner").toString(), Owner::class.java)
            success(owner)
        } else {
            //其他状态处理
        }
    }
    abstract fun success(owner: Owner)
}

调用时(伪代码):

GetUserInfoApi.execute(object : BaseOwnerCallback() {
                    override fun success(owner: Owner) {
                        //处理数据
                    }

四、Android客户端与服务器端交互示例

1. 传统方式:HttpURLConnection类

以GET方式向服务端发送请求,并将服务端的响应结果以字符串方式返回,如果没有响应内容则返回空字符串。

public static String getDataByGet(String url, Map<String, String> params, String charset) {
    if (url == null) {
        return null;
    }
    url = url.trim();
    URL targetUrl = null;
    if (params == null) {
        targetUrl = new URL(url);
    } else {
        StringBuilder sb = new StringBuilder(url + "?");
        for (Map.Entry<String, String> me : params.entrySet()) {
            sb.append(me.getKey()).append("=").append(URLEncoder.encode(me.getValue(), charset)).append("&");
        }
        sb.deleteCharAt(sb.length() 1);
        targetUrl = new URL(sb.toString());
    }
    Log.i(TAG, "get:url----->" + targetUrl.toString()); //打印log
    HttpURLConnection conn = (HttpURLConnection) targetUrl.openConnection();
    conn.setConnectTimeout(3000);
    conn.setRequestMethod("GET");
    conn.setDoInput(true);
    int responseCode = conn.getResponseCode();
    if (responseCode == HttpURLConnection.HTTP_OK) {
        return stream2String(conn.getInputStream(), charset);
    }
    return null;
}

2. Apache httpClient框架

以POST方式向服务端发送请求,并将服务端的响应结果以字符串方式返回,如果没有响应内容则返回空字符串。

public static String getDataByPost(String url, Map<String, String> params, String charset) {
    if (url == null) {
        return null;
    }
    url = url.trim();
    URL targetUrl = null;
    OutputStream out = null;
    try {
        targetUrl = new URL(url);
        HttpURLConnection conn = (HttpURLConnection) targetUrl.openConnection();
        conn.setConnectTimeout(3000);
        conn.setRequestMethod("POST");
        conn.setDoInput(true);
        conn.setDoOutput(true);
        StringBuilder sb = new StringBuilder();
        if (params != null && !params.isEmpty()) {
            for (Map.Entry<String, String> me : params.entrySet()) {
                sb.append(me.getKey()).append("=").append(URLEncoder.encode(me.getValue(), charset)).append("&");
            }
            sb.deleteCharAt(sb.length() 1);
        }
        byte[] outBytes = sb.toString().getBytes(charset);
        out = conn.getOutputStream();
        out.write(outBytes);
        out.flush();
        int responseCode = conn.getResponseCode();
        if (responseCode == HttpURLConnection.HTTP_OK) {
            return stream2String(conn.getInputStream(), charset);
        }
    } catch (UnsupportedEncodingException e1) {
        e1.printStackTrace();
    } catch (ClientProtocolException e2) {
        e2.printStackTrace();
    } catch (IOException e3) {
        e3.printStackTrace();
    } finally {
        try {
            if (out != null) {
                out.close();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    return null;
}

以上就是关于“android客户端 服务器”的问题,朋友们可以点击主页了解更多内容,希望可以够帮助大家!

0