发表于: 2017-08-25 23:40:27

2 1173


今天做的事:

今天一天还是被传视频的事情牵制了,然后还花了点时间在别的事上

今天没有继续进行任务6的Memcache的学习,学习了JSON,因为这个知识点已经拖了很久了,所以决定今天解决一下,大致能够使用


话不多说,开始介绍JSON

首先看一下百度对于JSON的释义

JSON(JavaScript Object Notation)是一种轻量级的数据交换语言,以文字为基础,且易于让人阅读,同时也方便了机器进行解析和生成。JSON简单说就是javascript中的对象和数组,所以这两种结构就是对象和数组两种结构,通过这两种结构可以表示各种复杂的结构,其可以将JavaScript 对象中表示的一组数据转换为字符串,然后就可以在函数之间轻松地传递这个字符串,或者在异步应用程序中将字符串从Web客户机传递给服务器端程序。


简单的说,我理解的JSON和数组,List,Map等一类的数据类型很相似。这么说有点干,接下来就看一下代码吧

而且这些东西应该就是我的下一次小课堂的内容。


首先我没看一个springMVC传输json的简单例子吧

package POJO;

import java.util.Arrays;

/**
* Created by Administrator on 2017/08/25.
*/
public class Shop {
String name;
   String staffName[];
   
   public String getName() {
return name;
   }

public void setName(String name) {
this.name = name;
   }

public String[] getStaffName() {
return staffName;
   }

public void setStaffName(String[] staffName) {
this.staffName = staffName;
   }

@Override
   public String toString() {
return "Shop{" +
"name='" + name + '\'' +
", staffName=" + Arrays.toString(staffName) +
'}';
   }
}

Controller

package JController;

import POJO.Shop;
import org.json.JSONObject;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;


/**
* Created by Administrator on 2017/08/25.
*/
@Controller
@RequestMapping(value = "/kfc/brands")
public class JsonController {

@RequestMapping(value = "{name}",method = RequestMethod.GET)
public @ResponseBody Shop getShopInJson(@PathVariable String name){
       System.out.println("-----------请求json数据---------");
       Shop shop = new Shop();
       shop.setName(name);
       shop.setStaffName(new String[]{"你是中文?","我也是中文!"});
       
       return shop;

   }

}

想要运行后展示json数据,是不需要相应的jsp页面的,但是需要引入几个jar包

<!-- https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-core -->
<dependency>
 <groupId>com.fasterxml.jackson.core</groupId>
 <artifactId>jackson-core</artifactId>
 <version>2.8.9</version>
</dependency>

<!-- https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-databind -->
<dependency>
 <groupId>com.fasterxml.jackson.core</groupId>
 <artifactId>jackson-databind</artifactId>
 <version>2.8.9</version>
</dependency>

<!-- https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-annotations -->
<dependency>
 <groupId>com.fasterxml.jackson.core</groupId>
 <artifactId>jackson-annotations</artifactId>
 <version>2.8.9</version>
</dependency>


此时使用json和之前web容器启动动态jsp页面的配置还略有不同,需要在spring-servlet.xml配置文件中进行相关的json配置

<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter">
   <property name="messageConverters">
       <list>
           <!--json转换器-->
           <ref bean="mappingJacksonHttpMessageConverter"/>
       </list>
   </property>
</bean>
<bean id="mappingJacksonHttpMessageConverter" class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
   <property name="supportedMediaTypes">
       <list>
           <value>application/json;charset=UTF-8</value>
       </list>
   </property>
</bean>

 @ResponseBody 注解返回JSON时可以配置Json转换器,这个就是MappingJackson2HttpMessageConverter这个类的作用

json转换器,过不加入这两个标签,在我们访问相应的url时会有报错。

No converter found for return value of type

大概是这种错误

而这两个标签的配置其实还有一点讲究,看一下我的注解把

<!--废弃的org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter-->
<!--最新使用org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter-->
<!--<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter">-->


<!--如果是在@RequestMapping中加入produces = "application/json;charset=UTF-8",则这两个标签可以不使用,-->
<!--Spring3.0.5以下没有produces特性-->

首先,有的教程使用的是AnnotationMethodHandlerAdapter这个类,但是这个类在Spring的某个版本被废弃了,具体是哪个版本记不得了,有兴趣可以查一下。

还有第二块的注解,这个亲测有效


最后,看一下执行效果


然后这个简单的返回json的例子我们看完了,接下来看一下json的一些其他知识。

首先是json在java中的实现,我们需要引用一个jar包

<!-- https://mvnrepository.com/artifact/org.json/json -->
<dependency>
 <groupId>org.json</groupId>
 <artifactId>json</artifactId>
 <version>20170516</version>
</dependency>


然后有几个小例子,大概是json和其他数据类型的转换,看看了解一下即可

package JSONSomething;

import org.json.JSONArray;
import org.json.JSONException;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
* Created by Administrator on 2017/08/25.
*/
public class ToJSONArray {
public static void main(String[] args)throws JSONException{
List<String> list = new ArrayList<String>();
       list.add("username");
       list.add("age");
       list.add("sex");
       System.out.println("List: " + list);
   
       Map map = new HashMap();
       map.put("bookname","这书贼贵");
       map.put("price",66.6);
       System.out.println("Map: " + map);
   
       JSONArray array = new JSONArray();
       array.put(list);
       array.put(map);
   
       System.out.println("JSONArray: " + array);
   }
}


package JSONSomething;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.util.List;

/**
* Created by Administrator on 2017/08/25.
*/
public class StringToJSON {
public static void main(String[] args)throws JSONException{
System.out.println("abc");
      //定义json字符串
      String jsonStr = "{\"id\": 2," +
" \"title\": \"json title\", " +
"\"config\": {" +
"\"width\": 34," +
"\"height\": 35," +
"},\"data\": [" +
"\"JAVA\",\"JAVAScript\",\"PHP\"" +
"]}";
      //转换为JSON对象
      JSONObject jsonObject = new JSONObject(jsonStr);
   
      System.out.println(jsonObject);
   
      System.out.println("********************");
   
      System.out.println(jsonObject.toString());
   
      System.out.println("********************");
     
      //从JSON对象中获取数据
      JavaBean bean = new JavaBean();
     
//       根据属性名获取int类型
      bean.setId(jsonObject.getInt("id"));
     
//       根据属性名获取String类型
      bean.setTitle(jsonObject.getString("title"));
     
//       根据属性名获取JSON的Object对象
      JSONObject config = jsonObject.getJSONObject("config");
      bean.setWidth(config.getInt("width"));
      bean.setHeight(config.getInt("height"));
     
//       根据属性名获取JSONArray数组
      JSONArray data = jsonObject.getJSONArray("data");
     
      bean.setLanguages(data.toList());
   
      System.out.println(bean);
  }

}


class JavaBean{
private int id;
   private String title;
   private int width;
   private int height;
   private List languages;
   
   public int getId() {
return id;
   }

public void setId(int id) {
this.id = id;
   }

public String getTitle() {
return title;
   }

public void setTitle(String title) {
this.title = title;
   }

public int getWidth() {
return width;
   }

public void setWidth(int width) {
this.width = width;
   }

public int getHeight() {
return height;
   }

public void setHeight(int height) {
this.height = height;
   }

public List getLanguages() {
return languages;
   }

public void setLanguages(List languages) {
this.languages = languages;
   }

@Override
   public String toString() {
return "JavaBean{" +
"id=" + id +
", title='" + title + '\'' +
", width=" + width +
", height=" + height +
", languages=" + languages +
'}';
   }
}


package JSONSomething;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

/**
* Created by Administrator on 2017/08/25.
*/
public class JSONToString {
public static void main(String[] args)throws JSONException{
//创建JSON对象
       JSONObject jsonObject = new JSONObject();
       
       //像json中添加数据
       jsonObject.put("username","yubotao");
       jsonObject.put("height",10);
       jsonObject.put("age",24);
   
       System.out.println("Json: " + jsonObject);
       
       //创建JSON数组。并将json添加到数组中
       JSONArray array = new JSONArray();
       array.put(jsonObject);
       System.out.println("JSONArray: " + array);
       
       //转换为字符串
       String str = array.toString();
   
       System.out.println("str: " + str);
       
   }
}



上面的这几个例子,我们可以看到一个新的类JSONObject,所以我想,可不可以直接使用springMVC直接返回一个JSONObject,但是会有一些问题,接下来看一下

@RequestMapping(value = "/json",method = RequestMethod.GET)
public @ResponseBody JSONObject getJson(){
//创建JSON对象
   JSONObject jsonObject = new JSONObject();

   //像json中添加数据
   jsonObject.put("username","yubotao");
   jsonObject.put("height",10);
   jsonObject.put("age",24);

   return jsonObject;
}


当我进行访问时,会报如下错误

java.lang.IllegalArgumentException: No converter found for return value of type: class org.json.JSONObject

经过一番查阅,在Stack Overflow中看到一个最贴近这个问题的解答,我认为还不错

这是链接:https://stackoverflow.com/questions/42027491/why-does-spring-mvc-report-no-converter-found-for-return-value-of-type-class-o


看不懂没关系,我们翻译一下

可以看到这个解答把一些具体的有点底层的东西解释了,我们可以不用太关心,当然如果想要认真了解,还是再探究一下。通过该解答,我可以获得如下解答:

在springMVC中对于JSONObject的一个转换器是没法实现的,因为JSONObject中没有相关的setter和getter方法,因此获取不到这个类中的任何属性,就会报错。所以我们使用替代的方法,除了该回答中的toString方法,也可以使用toMap方法,如下代码

@RequestMapping(value = "/json",method = RequestMethod.GET)
public @ResponseBody Map getJson(){
//创建JSON对象
   JSONObject jsonObject = new JSONObject();

   //像json中添加数据
   jsonObject.put("username","yubotao");
   jsonObject.put("height",10);
   jsonObject.put("age",24);

   return jsonObject.toMap();
}

启动服务后,发现可以实现了

在解决问题的过程中遇到了406状态码问题,这是第一次遇到该问题,所以简单了解一下

是因为我的代码是这样的

@RequestMapping(value = "/json",method = RequestMethod.GET,produces = "application/json;charset=UTF-8")
public @ResponseBody JSONObject getJson(){
//创建JSON对象
   JSONObject jsonObject = new JSONObject();

   //像json中添加数据
   jsonObject.put("username","yubotao");
   jsonObject.put("height",10);
   jsonObject.put("age",24);

   return jsonObject;
}

报错如下

查了一下406错误原因

一般是指客户端浏览器不接受所请求页面的 MIME 类型。


MIME类型就是设定某种扩展名的文件用一种应用程序来打开的方式类型,当该扩展名文件被访问的时候,浏览器会自动使用指定应用程序来打开。


也就是说浏览器找不到JSONObject的打开方式,所以报错。


最后,今天的json收尾,来一波jsp页面的json标签

。。。明天继续测试,还是有点失误的。


明天计划:继续任务六Memcache的学习


问题:算是已解决


收获:json的知识


进度:开始时间:2017.08.25

    预计demo:2017.08.30

    是否有延期风险:未知,先放着看看,延期另说

    禅道链接:http://task.ptteng.com/zentao/project-task-285-unclosed.html



返回列表 返回列表
评论

    分享到