集成grpc,普通对象与grpc对象转换
分布式开发涉及到远程过程调用即RPC。需要集成grpc。但如果想无缝集成,则涉及到普通的请求对象转换为grpc请求对象。
由于null不能序列化,所以grpc的对象属性都会有默认值,这在开发中,很难区分,到底请求传的是默认值还是请求本身携带的值。所以使用protocol buffers 的oneof关键字,用于规避默认值。
新建员工类
package com.dld.hll.financial;
import java.math.BigDecimal;
import java.sql.Date;
import java.sql.Timestamp;
import java.util.List;
import java.util.Map;
import java.util.Set;
/**
* @Author yue chao
* @Date 2019/8/10 0010 下午 21:23
*/
public class EmpOne {
private Long empIdOne;
private String empNameOne;
private Boolean empSexOne;
private Long totalAssetOne;
private List<String> skills;
private Set<Integer> lucks;
private Map<String, String> relations;
private Date bornDate;
private Timestamp createTime;
private BigDecimal salary;
private DeptOne dept;
// ... 省略 get set
}
新建部门类
package com.dld.hll.financial;
/**
* @Author yue chao
* @Date 2019/8/10 0010 下午 21:24
*/
public class DeptOne {
private Long deptIdOne;
private String deptNameOne;
private Byte deptTypeOne;
// 省略 get set
}
proto文件
syntax = "proto3";
option java_multiple_files = true;
option java_package = "com.dld.hll.financial.grpc";
option java_outer_classname = "EmpProto";
message EmpOne {
oneof oneof_empId {
int64 empIdOne = 4;
}
oneof oneof_totalAssetOne {
int64 totalAssetOne = 8;
}
oneof oneof_empName {
string empNameOne = 5;
}
oneof oneof_empSex {
bool empSexOne = 6;
}
DeptOne dept = 7;
repeated string skills = 9;
repeated int32 lucks = 10;
map<string, string> relations = 11;
oneof oneof_bornDate {
string bornDate = 12;
}
oneof oneof_createTime {
string createTime = 13;
}
oneof oneof_salary {
string salary = 14;
}
}
message DeptOne {
oneof oneof_deptId {
int32 deptIdOne = 4;
}
oneof oneof_deptName {
string deptNameOne = 5;
}
oneof oneof_deptType {
int32 deptTypeOne = 6;
}
}
单元测试代码
package com.dld.hll.financial;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.protobuf.util.JsonFormat;
import org.apache.commons.lang3.StringUtils;
import org.junit.Test;
import java.io.IOException;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
/**
* @Author yue chao
* @Date 2019/8/12 0012 上午 11:40
*/
public class EmpOneTest {
/**
* oneof 普通请求转grpc请求,再转普通请求
* @throws IOException
*/
@Test
public void testOneCommonRequestTransformToGrpcRequest() throws IOException {
oneCommonRequestTransformToGrpcRequest();
}
public static void oneCommonRequestTransformToGrpcRequest() throws IOException {
DeptOne dept = new DeptOne();
dept.setDeptIdOne(0L);
dept.setDeptNameOne(StringUtils.EMPTY);
dept.setDeptTypeOne((byte)0);
List<String> skills = new ArrayList<>();
skills.add("EDVSD");
Set<Integer> lucks = new HashSet<>();
EmpOne emp = new EmpOne();
emp.setEmpIdOne(0L);
emp.setEmpNameOne(StringUtils.EMPTY);
emp.setEmpSexOne(false);
emp.setDept(dept);
emp.setSkills(skills);
emp.setLucks(lucks);
emp.setBornDate(new java.sql.Date(System.currentTimeMillis()));
emp.setCreateTime(new java.sql.Timestamp(System.currentTimeMillis()));
emp.setSalary(new BigDecimal("22.33"));
Gson gson = new GsonBuilder().serializeNulls()
.setPrettyPrinting()
.registerTypeAdapter(java.sql.Timestamp.class, new TimeStampGSON())
.registerTypeAdapter(java.sql.Date.class, new SqlDateGSON())
.create();
String empJson = gson.toJson(emp);
System.out.println("普通对象json==============");
System.out.println(empJson);
com.dld.hll.financial.grpc.EmpOne.Builder builder = com.dld.hll.financial.grpc.EmpOne.newBuilder();
JsonFormat.parser().merge(empJson, builder);
com.dld.hll.financial.grpc.EmpOne empOneGrpc = builder.build();
StringBuilder sb = new StringBuilder();
JsonFormat.printer()
.includingDefaultValueFields() // 设置采用默认值,当集合为空的时候会使用[]表示,map为空的时候采用{},这样可能有效防止直接使用而遇到的空指针
.appendTo(empOneGrpc, sb);
System.out.println("grpc对象Json==============");
// 可以观察到普通对象json与grpcJson的区别,grpcJson对象字段为null的字段不显示,集合或map为空,则使用以上规则处理了
System.out.println(sb);
Gson gson2 = new GsonBuilder()
.setPrettyPrinting()
.serializeNulls()
.registerTypeAdapter(java.sql.Timestamp.class, new TimeStampGSON())
.registerTypeAdapter(java.sql.Date.class, new SqlDateGSON())
.create();
EmpOne vo = gson2.fromJson(sb.toString(), EmpOne.class);
System.out.println("普通对象json==============");
System.out.println(gson2.toJson(vo));
}
}
测试结果
普通对象json==============
{
"empIdOne": 0,
"empNameOne": "",
"empSexOne": false,
"totalAssetOne": null,
"skills": [
"EDVSD"
],
"lucks": [],
"relations": null,
"bornDate": "2019-08-12",
"createTime": "2019-08-12 13:39:14",
"salary": 22.33,
"dept": {
"deptIdOne": 0,
"deptNameOne": "",
"deptTypeOne": 0
}
}
grpc对象Json==============
{
"empIdOne": "0",
"empNameOne": "",
"empSexOne": false,
"dept": {
"deptIdOne": 0,
"deptNameOne": "",
"deptTypeOne": 0
},
"skills": ["EDVSD"],
"lucks": [],
"relations": {
},
"bornDate": "2019-08-12",
"createTime": "2019-08-12 13:39:14",
"salary": "22.33"
}
普通对象json==============
{
"empIdOne": 0,
"empNameOne": "",
"empSexOne": false,
"totalAssetOne": null,
"skills": [
"EDVSD"
],
"lucks": [],
"relations": {},
"bornDate": "2019-08-12",
"createTime": "2019-08-12 13:39:14",
"salary": 22.33,
"dept": {
"deptIdOne": 0,
"deptNameOne": "",
"deptTypeOne": 0
}
}
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。