使用jackson转json解决双向关联循环调用.docx
《使用jackson转json解决双向关联循环调用.docx》由会员分享,可在线阅读,更多相关《使用jackson转json解决双向关联循环调用.docx(10页珍藏版)》请在冰点文库上搜索。
使用jackson转json解决双向关联循环调用
使用jackson转json解决双向关联循环调用
如果对象间存在互相引用的场景,例如Hibernate的mapping关系。
或者自定义类也需要这种实现:
如Teacher类和Student
class Teacher {
private String name;
private String sex;
private Student student;
public Teacher(String name, String sex) {
this.name = name;
this.sex = sex;
}
public String getName() {
return name;
}
public String getSex() {
return sex;
}
public Student getStudent() {
return student;
}
public void setStudent(Student student) {
this.student = student;
}
}
class Student{
private String name;
private String grade;
private Teacher teacher;
public Student(String name, String grade) {
this.name = name;
this.grade = grade;
}
public String getName() {
return name;
}
public String getGrade() {
return grade;
}
public Teacher getTeacher() {
return teacher;
}
public void setTeacher(Teacher teacher) {
this.teacher = teacher;
}
}
可以设想一下,不加任何处理,对teacher或者student实例进行序列化的话,会不会循环序列化而导致程序出错。
测试用例:
@Test
public void test() throws Exception {
Student student = new Student("zhangsan", "一年级");
Teacher teacher = new Teacher("bailaoshi", "男");
teacher.setStudent(student);
student.setTeacher(teacher);
System.out.println(mapper.writeValueAsString(teacher));
System.out.println(mapper.writeValueAsString(student));
}
运行结果:
可以看到抛出了堆栈溢出的错误。
解决方案:
@JsonIdentityInfo(generator = ObjectIdGenerators.PropertyGenerator.class, property = "id", scope = Teacher.class)
class Student{
private String name;
private String grade;
//这个注解不是必须的
@JsonTypeInfo(use = JsonTypeInfo.Id.CLASS, include = JsonTypeInfo.As.PROPERTY, property = "@class")
private Teacher teacher;
private long id;
public long getId() {
return id;
}
public Student(String name, String grade) {
this.name = name;
this.grade = grade;
}
public String getName() {
return name;
}
public String getGrade() {
return grade;
}
public Teacher getTeacher() {
return teacher;
}
public void setTeacher(Teacher teacher) {
this.teacher = teacher;
}
}
JsonIdentityInfo标注是Jackson2.0提供的功能,可以解决类似循环引用的场景。
当给某个类(不仅仅用在类上)指定了这个标注后,也必须在这个类中指定某个字段来表示ObjectID,例如上面的id字段。
这样做的好处是,Jackson会对本类生成一个标识码,用id字段表示。
这个id最终会变成对student完全序列化后的引用。
然后teacher类实例对Student实例的引用就变成了对这个id的引用,也就是student完全序列化后的引用。
再运行上面的测试用例输出:
{"name":
"bailaoshi","sex":
"男","student":
{"id":
0,"name":
"zhangsan","grade":
"一年级","teacher":
{"@class":
"com.sonymoon.test.JacksonRefereceTest$Teacher","name":
"bailaoshi","sex":
"男","student":
0}}}
{"id":
0,"name":
"zhangsan","grade":
"一年级","teacher":
{"@class":
"com.sonymoon.test.JacksonRefereceTest$Teacher","name":
"bailaoshi","sex":
"男","student":
0}}
可以看到teacher对象输出为teacher本身序列化+student的完全序列化(student+teacher)
student序列化之后包含自己+teacher+一个ObjectId(id)
注:
博主使用的是UEditor-KityFormulaforwordpress 2.0.2版的wordpress插件。
不用看的人群。
用markdown或者wordpress自带插件的等等。
博主折腾了挺久,网上大部分是关于XX原生ueditor自定义按钮教程,却没有针对wordpress UEditor-KityFormula版插件的教程。
故写下此文作为记录。
写文章的时候发现ueditor只支持代码段,但是有时候需要插入代码短语或词语。
所以需要自己在工具栏里加入一个自定义的按钮。
能够在编辑的时候就能迅速将选定的文本变成选定的文字
样式。
效果就如同加粗按钮会把
选定的文本变成格式。
背后其实就是将选定的文本包裹了一层html标签。
如图所示。
自定义的工具栏:
步骤如下。
1.注册UI和绑定UI点击事件。
打开ueditorwordpress的插件的文件夹。
默认应该在wordpress/wp-content/plugins/UEditor-KityFormula-for-wordpress/ueditor下。
新建code文件夹。
然后添加如下js代码和code.png。
code.js:
UE.registerUI('button', function(editor, uiName) {
editor.registerCommand(uiName, {
execCommand:
function() {
var range = editor.selection.getRange();
range.select();
var txt = editor.selection.getText();
this.execCommand('insertHtml',""+txt+"
");
}
});
var iconUrl = editor.options.UEDITOR_HOME_URL + 'code/code.png';
var btn = new UE.ui.Button({
name:
uiName,
title:
uiName,
cssRules:
'background:
url("' + iconUrl + '") !
important',
onclick:
function() {
editor.execCommand(uiName);
}
});
editor.addListener('selectionchange', function() {
var state = editor.queryCommandState(uiName);
if (state == -1) {
btn.setDisabled(true);
btn.setChecked(false);
} else {
btn.setDisabled(false);
btn.setChecked(state);
}
});
return btn;
});
code.png的地址
下载code.png
2.在wordpressueditor插件中引入
然后打开wordpress/wp-content/plugins/UEditor-KityFormula-for-wordpress/ueditor.class.php
大致在60-71行。
在引入js的代码块下,引入自己的js文件。
博主使用的是
-- 公式编辑组件 jinaYang 2016-11-6 -->
效果如下:
没有点击C按钮时:
点击C之后:
文章发布后就会显示如图的css样式了: