当前位置: 首页 > 后端技术 > Node.js

使用fst-json自动生成更快的json序列化方式

时间:2023-04-04 01:30:44 Node.js

fst-json的全称是“fast-safe-typescriptjson”,其实质是直接使用你定义的Typescript文件来生成更高效的序列化方式。其目的是在编译和开发阶段利用现有资源(开发过程编写的Typescript文件)尽可能提高运行时性能,同时在这个过程中没有额外的开发负担。github:https://github.com/aircloud/f...背景由于JSONschema的概念是fastify引入的,我们先介绍一下。fastify是一个高性能的Node.JS服务端框架,其特点是高性能,其高性能的主要原因是它引入了JSONschema,通过对参数添加约束来获得更快的序列化速度。同时,fastify还开源了一个独立的json序列化库fast-json-stringify,可以在非fastify项目中使用。在fastify中,JSONschema的写法大致如下:constschema={schema:{response:{200:{type:'object',properties:{hello:{type:'string'}}}}}fastify.get('/',schema,function(req,reply){reply.send({hello:'world'})})我们可以看出这种写法不仅会带来额外的学习成本,而且由于目前大多数项目都是使用Typescript开发的,这组定义将与我们的Typescript定义重叠。事实上,上面的示例代码虽然比较短,但是在接口很多的实际项目中,这些代码的开发量和额外的学习/维护成本是不可低估的。那么是否可以不重新定义JSONschema而直接使用Typescript呢?答案是肯定的。fst-json就是这样一个工具,它可以复用我们在Typescript中定义的schema来自动生成fastify需要的schema,这样我们就不需要额外维护schema定义了。如何使用接下来我们简单介绍一下fst-json的使用方法。首先,安装它(全局或到项目中):npmifst-json-g假设我们的项目使用Typescript,我们已经提前有一个模式文件:exportinterfaceHellWorld{attr1:string;attr2:字符串;attr3?:string;}我们在项目目录下新建一个.fstconfig.js来声明配置。配置如下:module.exports={sourceFiles:['./src/schema/*.ts'],distFile:"./src/schema-dist.ts",format:'fastify'}我们运行后:fst-jsongen然后这个时候会生成一个src/schema-dist.ts,这里会自动生成JSONschema定义,然后我们就可以在项目:从'./schema-dist'导入*作为模式;importtype{HellWorld}from"./schema";constschema={schema:{response:{200:schemas.HellWorldSchema}}}server.get('/',schema,function(req,reply){letres:hellWorld={attr1:'hello',attr2:'world',attr3:'optional'}reply.send(res);})当然fst-json不仅可以在fastify中使用,其他任何地方都可以使用需要JSON加速的地方,用法也很简单,可以参考这篇HelloWorld原理和优点fst-json其实就是通过解析Typescript的语法树来导出导出的各种类型生成对应的fast-json-stringifyJSONschema,所以运行速度和手写没有区别。因此,既可以充分利用fast-json-stringify的效率优势,又可以减少重复开发量如下优点:根据schema进行字段校验:首先会进行Tyepscript语法校验,报错必要的属性缺失时会直接报错(比如定义接口时没有用?修饰符修饰的属性缺失)。过滤不需要的schema字段:比如在使用Node.JS作为BFF层时,可以严格按照Typescript的定义返回字段,避免返回不需要的字段,从而防止上游服务的敏感字段直接透传。也意味着从接口层面出发,真正做到FullyTyped。更快的序列化速度:根据fast-json-stringify的测试,可以达到近2倍于JSON序列化的速度。目前fst-json支持接口、类、类型等常用类型,并增加了各种示例和90%覆盖率测试。当然,因为Typescript在书写上更加灵活。由于JSONschema本身的限制,我们无法覆盖所有场景,所以大家也可以参考这里的注意事项,有针对性的避免出现比较有问题的写法。限制fst-json只是一个语法分析和生成工具。具体运行时其实是使用fast-json-stringify,所以需要在项目中安装fast-json-stringify依赖。另外,对于fast-json-stringify的测试,在payload比较小的情况下,它的速度是有优势的。当payload太大时,它的优势就不再明显,甚至不如JSON.stringify。官方的描述是:fast-json-stringify比JSON.stringify()对于小负载要快得多。它的性能优势会随着负载的增长而缩小。但其实这时候还是可以使用fst-json做一些事情的,比如笔者使用fst-json做bff层对下游服务接口的持续集成兼容性测试。在预先定义好Typescript的情况下,每次测试只需要请求依赖的服务,序列化response字段即可。如果没有报错且序列化后该字段没有变为null(在更复杂的接口定义中,如果个别属性的定义类型与返回类型不一致,fast-json-stringify会直接转为null),这意味着界面没有改变。可以有效避免依赖服务接口变化,但没有及时同步到位而造成暗坑的情况。另外,其实fast-json-stringify生成的序列化代码还是在运行时完成的。这里的问题可能在于代码的不透明性,以及运行时的开销和风险。作者希望将其生成的代码变成编译时的过程。但是这样的话,其实有点重新发明轮子的错觉,所以我还没有做这个。最后,fst-json是不久前开源的一个小项目,肯定还有一些需要优化和改进的地方。欢迎星级支持和建议。