其他

MessagePack:最可能取代JSON的存在。

今天咱们聊聊一个挺酷的数据序列化工具——Msgpack。

你可能听过JSON,它在数据交换领域可谓是超级明星。

但今天要介绍的这个选手,Msgpack,不仅速度快,体积还小,对于处理大数据来说是个不错的选择。

科普一个冷门的,但是很强的技术:MessagePack,简称msgpack。msgpack不是软件,是一个标准,可以先把它看成二进制的json,“二进制json”容易让人联想到一个更流行一点的标准:BSON。如果你不知道bson是啥可以去查一下,总之msgpack和bson是同类型的竞争产品,但是msgpack无论从速度还是体积上都秒杀bson,至少在网络传输上是这样的。

json都知道是啥吧,在序列化领域神一般的存在。什么是序列化呢,其实就是降维打击:任何多维的数据对象都必须被降维打击成一维才能进行存储和网络传输。

msgpack也是一个降维打击,哦不,序列化的手段,只不过它序列化的结果是二进制格式而非json的文本格式,不理解的可以类比http1.1和http2.0,就是一个由文本格式进化到二进制格式的例子。

这种进化有什么好处以后专门写一篇文章谈谈,题目暂定《从字符时代到二进制时代》。本文谈谈msgpack有什么好处,为啥说它能取代json?

首先按官方的话说,msgpack比json小,比json快。比json小是一定的,官网上有一个例子:

上面那个json串在utf8编码下每个字符一个字节,总共27字节,转换成msgpack格式之后只剩下18字节,压缩了三分之一。之所以msgpack能够压缩是因为json串本身有许多没用的信息,比如每一个key的双引号就可以省去,简单的Boolean类型非要用四五个字节来表示(true和false)。当然XML的没用信息就更多了,这些都是文本格式本身的弊端,二进制格式就是来解决这些问题的,比如数字就是数字,就应该用二进制表示。

Msgpack是啥?


首先,Msgpack是一种高效的二进制序列化格式,可以把各种数据结构,比如数组、哈希表之类的,转换成二进制格式。

这让它可以方便地在网络上传输或存储到文件里。

听起来是不是和JSON挺像的?

确实,Msgpack和JSON都是做数据序列化的好手,但Msgpack是用的二进制格式,这让它在处理速度和数据大小上都有不小的优势。

看下Msgpack与JSON的性能对比:

常见用法


Msgpack可以用在多种场景,常见的比如在客户端和服务器之间传输数据。

得益于它的二进制特性,Msgpack在网络上传输速度快,生成的数据包也更小。

对那些对性能要求极高的应用来说,简直是救星。

还有,Msgpack也经常被用来存储日志

想象一下,如果你的服务器每天要处理成千上万的请求,用JSON来存储日志,文件可能会非常大。

但如果换成Msgpack,就能大幅度减少存储空间的占用,同时也便于后续的数据分析。

Msgpack的原理 那Msgpack是怎么做到这么高效的呢?主要是几点:

  1. 二进制格式:使用二进制格式来表示数据,比JSON的文本格式更紧凑,自然就减少了数据体积。
  2. 类型共享:在Msgpack中,相同数据结构的不同实例可以共享类型信息,避免了重复的类型定义,数据大小也因此减少。
  3. 无需引号:在Msgpack里,字符串和二进制数据不需要用引号包围,这也节省了一些空间。
  4. 扩展类型:Msgpack还支持扩展类型,让你可以自定义数据类型,让数据表示更灵活。

与JSON的比较


比起JSON,Msgpack在序列化和反序列化的速度通常更快,特别是在处理复杂数据结构时。

由于是二进制格式,生成的数据包也通常比JSON小,这在网络传输和存储上都有优势。

不过,JSON的文本格式更易于人阅读和编辑,而Msgpack则需要专门的工具来处理。

Java代码示例


下面,让我们看一下在大家常用的Springboot项目中,该如何使用Msgpack:

引入依赖

<dependencies>
    <!-- Spring Boot Starter Web -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>

    <!-- Msgpack Dependency -->
    <dependency>
        <groupId>org.msgpack</groupId>
        <artifactId>msgpack</artifactId>
        <version>0.9.1</version> <!-- 版本号可能会有变化,请确保使用最新版本 -->
    </dependency>
</dependencies>

使用Msgpack进行序列化和反序列化

创建一个Controller来处理HTTP请求,并使用Msgpack来序列化和反序列化对象:

import org.msgpack.MessagePack;
import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/api")
public class MyController {

    @PostMapping("/serialize")
    public byte[] serialize(@RequestBody MyObject myObject) throws Exception {
        MessagePack msgpack = new MessagePack();
        return msgpack.write(myObject);
    }

    @PostMapping("/deserialize")
    public MyObject deserialize(@RequestBody byte[] bytes) throws Exception {
        MessagePack msgpack = new MessagePack();
        return msgpack.read(bytes, MyObject.class);
    }
}

MyObject是一个简单的POJO类,它将被Msgpack序列化和反序列化:

public class MyObject {
    private String name;
    private int age;

    // Getters and setters
}

测试结果:

最后,你可以通过发送HTTP请求来测试这个Controller。
例如,你可以使用curl来发送POST请求:

# Serialize
curl -X POST -H "Content-Type: application/json" -d '{"name":"John","age":30}' http://localhost:8080/api/serialize

# Deserialize
curl -X POST -H "Content-Type: application/json" -d '{"bytes":[...]}' http://localhost:8080/api/deserialize

总结


好了,朋友们,希望这篇文章帮你了解了Msgpack——一个高效、紧凑的数据序列化工具。

既然msgpack比json又小又快,json真的一无是处吗?虽然在网络传输的应用场景上msgpack可以完胜json,可作为配置文件的场景上又如何呢?我们知道JSON格式对用户是很友好的,可读性非常强,在编辑器中代码折叠,类型高亮都非常方便。msgpack作为二进制格式似乎不好直接编辑。

虽然它的可读性不如JSON,但在很多场合,它的性能优势足以弥补这点小缺陷。
如果你对自己项目的性能有着极致的追求,希望你能在项目中尝试使用Msgpack,选对工具,事半功倍!