android客户端+JAVA WEB服务器实现json数据解析

来源:互联网 发布:武汉长江大数据交易所 编辑:程序博客网 时间:2024/05/22 04:52
    首先,项目中使用javaweb作为后台服务器,源码地址:服务器和客户端源码地址。
接下来进入正题。
   
   一、java web服务器
        
         这里就多说了,不太了解j2ee的请查阅相关书籍。
      
         项目结构如下:
       
        News类定义了之后解析的JSON对象的内容;
        NewsServer则是定义了一个获取最新新闻News的接口;
        NewsServer则是实现了这个接口,定义了获取最新新闻的方法;
        NewsListServlet则是一个实现客户端get和post请求的servlet,用于实现网络请求时的业务逻辑处理,主要返回含有News内容的json字符串;
        jsonnewslist.jsp是一个jsp文件用于测试服务器是否正常运行。
      
      服务器部分就不啰嗦了,直接贴代码和截图
      
  (1)News类
           
 public class News {private Integer id;private String title;private Integer timelength;public News(Integer id, String title, Integer timelength) {this.id = id;this.title = title;this.timelength = timelength;}public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public String getTitle() {return title;}public void setTitle(String title) {this.title = title;}public Integer getTimelength() {return timelength;}public void setTimelength(Integer timelength) {this.timelength = timelength;}}
         (2)NewsServer接口
      
public interface NewsServer {/* * 获取最新的新闻News */public java.util.List<News> getLastNews();}
          (3)NewsServerBean类 
import java.util.ArrayList;import java.util.List;public class NewsServerBean implements NewsServer {@Overridepublic List<News> getLastNews() {// TODO Auto-generated method stubList<News> news = new ArrayList<>();news.add(new News(10, "吕文健", 20));news.add(new News(45, "李昱喜", 10));news.add(new News(89, "android is amazing", 50));return news;}}
       (4)NewsListServlet类
import java.io.IOException;import java.util.List;import javax.servlet.ServletException;import javax.servlet.annotation.WebServlet;import javax.servlet.http.HttpServlet;import javax.servlet.http.HttpServletRequest;import javax.servlet.http.HttpServletResponse;@WebServlet(name="newslist",            urlPatterns={"/newslist"})//配置Servletpublic class NewsListServlet extends HttpServlet {/** *  */private static final long serialVersionUID = 1L;NewsServerBean serverbean =new NewsServerBean();@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {// TODO Auto-generated method stub   doPost(req, resp);}@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {// TODO Auto-generated method stubreq.setCharacterEncoding("GBK");
resp.setCharacterEncoding("GBK");//这里设置成gbk防止手机端显示乱码,之前设置为utf-8总是乱码List<News> news = serverbean.getLastNews();
StringBuilder json = new StringBuilder();json.append("[");for(News news2:news){json.append('{').append("\"id\":").append(news2.getId()).append(",");                                  json.append("\"title\":").append("\""+news2.getTitle()+"\"").append(",");            json.append("\"timelength\":").append(news2.getTimelength());            json.append('}').append(",");}json.deleteCharAt(json.length()-1);//?json.append("]");        req.setAttribute("json", json.toString());        req.getRequestDispatcher("/jsonnewslist.jsp").forward(req, resp);}}

    (5)jsonnewslist.jsp(在服务端测试服务器是否布置成功)
<%@ page language="java" contentType="text/plain; charset=GBK"    pageEncoding="GBK"%>   ${json}
             (6)服务器运行结果

    


      OK,运行成功,服务器解决了,楼主把它打包成war,放在阿里云服务器上,省去了用电脑做服务器的各种麻烦。接下来进入正题,客户端解析Json


二、android客户端

     客户端部分主要是一个简单的listview显示获取的news,运行结果如下:



接下来,开始贴代码:
    1、布局文件:
    (1)activity_main.xml
<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    xmlns:tools="http://schemas.android.com/tools"    android:id="@+id/activity_main"    android:layout_width="match_parent"    android:layout_height="match_parent"    android:orientation="vertical"    tools:context="wf.com.getnewsinjson.MainActivity"><Button    android:id="@+id/btn_refresh"    android:layout_width="match_parent"    android:layout_height="50dp"    android:text="刷新"    />    <ListView        android:id="@+id/listview"        android:layout_width="match_parent"        android:layout_height="wrap_content"        /></LinearLayout>
(2)item.xml(ListView中每一个item的布局)
<?xml version="1.0" encoding="utf-8"?><LinearLayout    xmlns:android="http://schemas.android.com/apk/res/android"    android:orientation="horizontal"    android:layout_width="match_parent"    android:layout_height="match_parent"    >    <TextView        android:id="@+id/title"        android:layout_width="0dp"        android:layout_height="50dp"        android:layout_weight="1"        android:gravity="center"        />    <TextView        android:layout_marginLeft="10dp"        android:id="@+id/timelength"        android:layout_width="0dp"        android:layout_weight="1"        android:layout_height="50dp"        android:gravity="center"        /></LinearLayout>
2、主要代码
  (1)、News类(和之前服务器中的一样,用于解析)
   (2)、NewsServer类(用于连接服务器并解析JSON字符串)
import android.util.Log;import org.json.JSONArray;import org.json.JSONException;import org.json.JSONObject;import java.io.IOException;import java.io.InputStream;import java.net.HttpURLConnection;import java.net.MalformedURLException;import java.net.URL;import java.util.ArrayList;import java.util.List;import Util.StreamTool;/** * Created by wangfeng on 2016/12/8. */public class NewsService {    public static List<News> getJsonLastNews() {        List<News> list = null;        InputStream in = null;                String path = "http://*****";//这里输入自己的服务器地址                try {                    list = new ArrayList<>();                    URL url = new URL(path);                    HttpURLConnection conn = (HttpURLConnection) url.openConnection();                    conn.setConnectTimeout(5000);                    conn.setRequestMethod("GET");                    if (conn.getResponseCode()==200){                        in = conn.getInputStream();                        list = parseJSON(in);                    }                } catch (MalformedURLException e) {                    e.printStackTrace();                    System.out.println("客户端未连接到服务器");                } catch (IOException e) {                    e.printStackTrace();                    System.out.println("客户端未连接到服务器");                }        return list;    }
/*
*解析json字符串并返回一个List
*/
    public static List<News>  parseJSON(InputStream in){        List<News> list = null;        try {            list = new ArrayList<>();//           String str = StreamTool.streamToString(in);//            System.out.println(str);            byte[] bytes = StreamTool.stream2Byte(in);//这里用到了StreamTool工具类,自己到CSDN上下载一个,这里是把                                                       //输入流转化为字节数组
             String str = new String (bytes,"GBK");//因为服务器设置了返回编码为GBK,这里也设置编码方式为GBK            System.out.println("解析成功"+str);            JSONArray jsonArray = new JSONArray(str);//将json字符串转化为JSONArray            for(int i =0;i< jsonArray.length();i++){                JSONObject jsonObject = jsonArray.getJSONObject(i);//循环JSONArray获得每一个JSONObject对象                int id = jsonObject.getInt("id");                String title = jsonObject.getString("title");                int timelength = jsonObject.getInt("timelength");                list.add(new News(id,title,timelength));            }        } catch (IOException e) {            e.printStackTrace();            Log.e("io","输入流读取错误");        } catch (JSONException e) {            e.printStackTrace();            Log.e("json","json数组转换错误");        } catch (Exception e) {            e.printStackTrace();        }        return list;    }}

    (3)MainActivity类
import android.os.Handler;import android.os.Message;import android.support.v7.app.AppCompatActivity;import android.view.View;import android.widget.Button;import android.widget.ListView;import android.widget.SimpleAdapter;import java.util.ArrayList;import java.util.HashMap;import java.util.List;import butterknife.BindView;import butterknife.ButterKnife;import butterknife.OnClick;public class MainActivity extends AppCompatActivity implements Runnable {    List<HashMap<String,Object>> data;    private static final int TAG =0X1;//用于Handler中的异步处理标志    Thread thread = null;//声明线程,用于执行NewsServer中的网络访问    Handler handler = new Handler() {        @Override        public void handleMessage(Message msg) {            super.handleMessage(msg);            switch (msg.what){                case TAG:                    SimpleAdapter simpleAdapter = new SimpleAdapter(MainActivity.this,data,R.layout.item,new String[]{"title","timelength"},new int[]{R.id.title,R.id.timelength});                    listview.setAdapter(simpleAdapter);                    break;            }        }    };    @BindView(R.id.btn_refresh)    Button btnRefresh;    @BindView(R.id.listview)    ListView listview;    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        ButterKnife.bind(this);//这里使用了ButterKnife组件来初始化组件和绑定id,不懂得自行百度    }        @OnClick(R.id.btn_refresh)    public void onClick(View view) {        switch (view.getId()) {            case R.id.btn_refresh:                thread = new Thread(this);                thread.start();                break;        }    }        @Override    public void run() {        String length = getResources().getString(R.string.timelength);        List<News> news = NewsService.getJsonLastNews();//这里必须另起一个线程访问,不能在主线程中访问         data = new ArrayList<>();        for(News news1:news){            HashMap<String,Object> item  = new HashMap<>();            item.put("id",news1.getId());            item.put("title",news1.getTitile());            item.put("timelength",length+": "+news1.getTimelength());            data.add(item);        }        Message msg = new Message();        msg.what=TAG;        handler.sendMessage(msg);//通知组件更新界面    }}

三、后记
      作为一只菜鸟不得不承认在这次练习中,犯了不少低级错误,比如,服务器端,没有设置返回的编码方式,json字符串忘记加“ ”;在客户端,在非UI线程中更新UI组件,在解析json时没有设置编码方式,在设置请求方式时将GET写成Get,哎,吃一堑长一智。
1 0
原创粉丝点击