学习Protobuf的一个小demo

学习Protobuf的一个小demo

  1. 需要导入的依赖

            <dependency>
                <groupId>com.google.protobuf</groupId>
                <artifactId>protobuf-java</artifactId>
                <version>3.1.0</version>
            </dependency>
    
            <!-- https://mvnrepository.com/artifact/junit/junit -->
            <dependency>
                <groupId>junit</groupId>
                <artifactId>junit</artifactId>
                <version>4.12</version>
            </dependency>
    
            <!-- https://mvnrepository.com/artifact/com.google.protobuf/protobuf-java-util -->
            <dependency>
                <groupId>com.google.protobuf</groupId>
                <artifactId>protobuf-java-util</artifactId>
                <version>3.1.0</version>
            </dependency>
    
    
  2. 一个Service_new.proto文件

 	/*
	cd .\src\main\resources
	.\protoc --java_out=..\..\..\src\main\java Service_new.proto
	*/
    syntax = "proto2";

	option java_package = "com.hexin.protobuf" ;
	option java_outer_classname = "ProtoEntityUtil" ;

	// 自定义主体定义 start
    message EntityFile{            //基本文件载体
    required bytes id = 1;         //文件唯一标识符,一般采用文件名
    optional int64 version = 2;    //文件版本号,客户端不关注。由服务端生成处理。
    optional bytes value = 3;      //文件内容,业务方自定义
    }
    // 自定义主体定义 end

    // 请求体及反馈体定义 start
    message UploadRequest{         //上传请求体
    repeated EntityFile file=1;    //必要属性file.id|file.value
    }
    message UploadResponse{        //上传反馈体
    required int32 code=1;         //处理状态码(详见上传接口的返回报文)
    optional int64 version=2;      //最大版本号
    }
    message DownloadResponse{      //下载反馈体
    required int32 code=1;         //处理状态码(详见下载接口的返回报文)
    optional int64 version=2;      //最大版本号
    repeated EntityFile file=3;    //必要属性file.id|file.value
    }
    // 请求体及反馈体定义 end

     message EntityFileValue{       //板块内容
     optional string ln = 1;        //板块长名称,即ln
     optional string xn = 2;        //选股问句,即xn
     optional string context =3;    //股票列表,即stocklist
     }
     message EntityFileId{          //板块id
     required int32 sn=1;           //板块名称,sn
     }
     message EntityFileValue_YuanShuJu{   //额外信息存储
     optional string sortstr = 1;         //多个板块的展示顺序的排序号
     }

3.通过命令,以及protoc.exe生成对应的.java文件, 命令大致如下:

//需注意,前面的路径是生成.java文件所在的路径,后面的路径是.proto文件所在的路径
protoc.exe --java_out=src/main/java/ src/main/resources/Service_new.proto

4.编写对应的测试类

import com.google.protobuf.ByteString;
import com.hexin.protobuf.ProtoEntityUtil;
import java.io.*;
import java.util.Base64;

public class TestServiceNew {

    /**
     * 上传 /序列化
     */
    public static  void uploadTest(String id,String value) throws IOException {
        // 1.构造一个上传请求的Builder
        ProtoEntityUtil.UploadRequest.Builder uploadReqBuilder = ProtoEntityUtil.UploadRequest.newBuilder();
        // 2.构造一个信息体 EntityFile 的Builder
        ProtoEntityUtil.EntityFile.Builder filebuilder = ProtoEntityUtil.EntityFile.newBuilder();
        // 3.把id 内容 set进 信息体的fileBuilder
        //filebuilder.setId(ByteString.copyFromUtf8(id));
        filebuilder.setId(ByteString.copyFrom(id.getBytes()));

        //filebuilder.setValue(ByteString.copyFromUtf8(value));
        filebuilder.setValue(ByteString.copyFrom(value.getBytes()));
        // 4.将EntityFile上传进Builder,可以加多个
        uploadReqBuilder.addFile(filebuilder);
        // 5.创建上传请求的实体对象
        ProtoEntityUtil.UploadRequest uploadRequest = uploadReqBuilder.build();
        // 6. 可能需要对内容base64化 Base64.getEncoder().encode(字节数组)
        //String upload = Base64.getEncoder().encode(uploadRequest.toByteArray()).toString();
        String upload = new String(Base64.getEncoder().encode(uploadRequest.toByteArray()));
        //String upload =uploadRequest.toByteArray().toString();
        System.out.println("upload :"+ "\n" + upload);
        System.out.println("---------------");
        // 控制台输出内容
            ProtoEntityUtil.EntityFile filebuild = filebuilder.build();
            // 解析内容
            ByteString value1 = ProtoEntityUtil.EntityFile.parseFrom(filebuild.toByteArray()).getValue();
            //解析内容转string并输出
            System.out.println(" 内容:"+ value1.toStringUtf8());
/*        // 7.上传操作/ 序列化本地
        OutputStream filename = new FileOutputStream("D:/testServiceNew.txt");
        uploadRequest.writeDelimitedTo(filename);*/
        PrintWriter out = new PrintWriter("D:/testServiceNew.txt");
        out.write(upload);
        out.close();
    }

    /**
     * 下载 /反序列化
     */
    public static void downloadTest(String url) throws IOException {
        // 1.通过穿进来的url找到对应的文件
        url = "D:/testServiceNew.txt";
        // 2.序列化
/*        ProtoEntityUtil.UploadRequest entityFile = ProtoEntityUtil.UploadRequest.parseFrom(new FileInputStream(url));
        System.out.println("entityfile" +"/n" + entityFile.toString());
        // 获取内容
        System.out.println("内容:"+entityFile.toString());*/
        FileReader in = new FileReader(url);
        BufferedReader bin = new BufferedReader(in);
        StringBuffer sb = new StringBuffer();
        String s = "";
        while ((s = bin.readLine()) != null) {
            sb.append(s);
        }
        System.out.println("读到的内容为:" + sb.toString());
        //ByteString value = ProtoEntityUtil.EntityFile.parseFrom(ByteString.copyFromUtf8(sb.toString())).getValue();
        String res = sb.toString();
        ProtoEntityUtil.UploadRequest uploadRequest = ProtoEntityUtil.UploadRequest.parseFrom(Base64.getDecoder().decode(res));

        System.out.println("内容:  " + uploadRequest.getFile(0).getValue().toStringUtf8());


        //HttpClient

    }

    public static void main(String[] args) {
        try {
            //uploadTest("123","新年快乐");
            downloadTest("D:/testServiceNew.txt");
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

白居不易.

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值