一种残膜回收机防缠绕挑膜装置的制 一种秧草收获机用电力驱动行走机构

一种protobuf数据编码方法及装置与流程

2022-08-13 23:11:30 来源:中国专利 TAG:
1.本公开涉及数据处理
技术领域
:,尤其涉及一种protobuf数据编码方法及装置。
背景技术
::2.目前,在线服务应用、离线数据传输、实时数据处理等场景,均需要使用到二进制的工程代码,因此,需要将实例map对象内实例字段内的目标字段值,构建为动态消息对象,再通过对动态消息对象进行数据编码,从而获得二进制的工程代码。3.相关技术中,在获得动态消息对象时,通常先根据所要描述的数据结构,定义proto协议描述文件,然后,需要通过人工从proto协议描述文件中,提取出目标实例字段中的目标字段值,添加到动态消息对象中。4.然而,由于相关技术中的这种方式,需要人工手动提取目标字段值,并且,若proto协议描述文件中的目标实例字段被修改,则仍然需要通过人工对动态消息对象进行修改,因此,相关技术中的这种编码方式效率较低,且容易出现编码错误的情况。技术实现要素:5.本公开实施例提供一种protobuf数据编码方法及装置,以提高数据编码的效率和准确度。6.本公开实施例提供的具体技术方案如下:7.一种protobuf数据编码方法,应用于转化客户端,包括:8.响应于针对实例map对象的序列化请求,获取元数据,其中,所述元数据中至少包括:各字段名和对应的字段类型,每个字段名对应一种字段类型;9.依次遍历所述各字段名,执行以下操作:根据任意一字段名,从所述实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出所述目标实例字段中的目标字段值,将所述目标字段值添加至动态消息对象中;10.对生成的动态消息对象进行序列化编码,获得编码数据。11.一种protobuf数据编码方法,应用于数据管理设备,包括:12.根据获取到的各属性数据,生成初始属性文件;13.将所述初始属性文件发送给转化客户端,以使所述转化客户端根据所述初始属性文件,生成元数据,依次遍历所述元数据中包含的各字段名,执行以下操作:根据任意一字段名,从所述实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出所述目标实例字段中的目标字段值,将所述目标字段值添加至动态消息对象中,对生成的动态消息对象进行序列化编码,获得编码数据。14.一种protobuf数据编码装置,应用于转化客户端,包括:15.获取模块,用于响应于针对实例map对象的序列化请求,获取元数据,其中,所述元数据中至少包括:各字段名和对应的字段类型,每个字段名对应一种字段类型;16.第一处理模块,用于依次遍历所述各字段名,执行以下操作:根据任意一字段名,从所述实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出所述目标实例字段中的目标字段值,将所述目标字段值添加至动态消息对象中;17.编码模块,用于对生成的动态消息对象进行序列化编码,获得编码数据。18.一种protobuf数据编码装置,应用于数据管理设备,包括:19.获取模块,用于根据获取到的各属性数据,生成初始属性文件;20.第一处理模块,用于将所述初始属性文件发送给转化客户端,以使所述转化客户端根据所述初始属性文件,生成元数据,依次遍历所述元数据中包含的各字段名,执行以下操作:根据任意一字段名,从所述实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出所述目标实例字段中的目标字段值,将所述目标字段值添加至动态消息对象中,对生成的动态消息对象进行序列化编码,获得编码数据。21.一种电子设备,包括存储器、处理器及存储在存储器上并可在处理器上运行的计算机程序,所述处理器执行所述程序时实现上述protobuf数据编码方法的步骤。22.一种计算机可读存储介质,其上存储有计算机程序,所述计算机程序被处理器执行时实现上述protobuf数据编码方法的步骤。23.本公开实施例中,响应于针对实例map对象的序列化请求,获取元数据,其中,元数据中至少包括:各字段名和对应的字段类型,每个字段名对应一种字段类型;依次遍历各字段名,执行以下操作:根据任意一字段名,从实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出目标实例字段中的目标字段值,将目标字段值添加至动态消息对象中;对生成的动态消息对象进行序列化编码,获得编码数据。这样,当需要解析protobuf数据时,采用字段类型对应的字段值提取方式,获得动态消息对象,并基于动态消息对象获得编码数据,能够将人工配置动态消息对象的过程转化为自动化过程,提高了数据编码的效率,简化了protobuf使用时的流程,并且,通过这种自动化方式,能够减少数据编码的出错率,提高数据编码的准确度。附图说明24.图1为本公开实施例中protobuf数据编码方法的第一流程示意图;25.图2为本公开实施例中实例map对象的示例图;26.图3为本公开实施例中protobuf数据编码方法的第二流程示意图;27.图4为本公开实施例中的界面示意图;28.图5为本公开实施例中转换客户端的结构示意图;29.图6为本公开实施例中数据管理设备的结构示意图;30.图7为本公开实施例protobuf数据编码装置的第一结构示意图;31.图8为本公开实施例protobuf数据编码装置的第二结构示意图;32.图9为本公开实施例中电子设备的结构示意图。具体实施方式33.下面将参考若干示例性实施方式来描述本公开的原理和精神。应当理解,给出这些实施方式仅仅是为了使本领域技术人员能够更好地理解进而实现本公开,而并非以任何方式限制本公开的范围。相反,提供这些实施方式是为了使本公开更加透彻和完整,并且能够将本公开的范围完整地传达给本领域的技术人员。34.本领域技术人员知道,本公开的实施方式可以实现为一种系统、装置、设备、方法或计算机程序产品。因此,本公开可以具体实现为以下形式,即:完全的硬件、完全的软件(包括固件、驻留软件、微代码等),或者硬件和软件结合的形式。35.在本文中,需要理解的是,附图中的任何元素数量均用于示例而非限制,以及任何命名都仅用于区分,而不具有任何限制含义。36.为了方便理解,下面对本公开实施例中涉及的名词进行解释:37.map《string,object》:指java语言中完整包名为java.util.map的类,其表示一种映射容器,其中存放的元素是从string到object对象的映射。容器提供的get方法可以根据提供的string从容器中快速获取到object对象,在本公开实施例中,实例map对象为map《string,object》。38.schema:数据的模式,即描述数据的数据,描述了一份数据从整体含义到字段类型的元数据信息。在数据库领域,schema包含表名、字段名、字段类型、字段约束等信息。也有自描述模式的数据,比如parquet格式数据,这种数据内部本身就包含schema,读取数据文件就可以取到schema。39.下面参考本公开的若干代表性实施方式,详细阐释本公开的原理和精神。40.发明概述41.相关技术中,通常在获得动态消息对象时,需要人工从protobuf协议描述文件中,提取出目标实例字段中的目标字段值,添加到动态消息对象中,然而,通过人工手动提取目标字段值,若proto协议描述文件中的目标实例字段被修改,则需要人工对动态消息对象进行修改,因此,相关技术中的protobuf数据编码方式的效率不高,且准确度不高。42.为了解决上述问题,本公开提供了一种protobuf数据编码方法,具体包括如下步骤:响应于针对实例map对象的序列化请求,获取元数据,其中,元数据中至少包括:各字段名和对应的字段类型,每个字段名对应一种字段类型;依次遍历各字段名,执行以下操作:根据任意一字段名,从实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出目标实例字段中的目标字段值,将目标字段值添加至动态消息对象中;对生成的动态消息对象进行序列化编码,获得编码数据。这样,能够实现在运行时对动态消息对象的动态构建,并简化了数据编码过程,不仅提高了数据编码效率,还降低了错误率。43.在介绍了本公开的基本原理之后,下面具体介绍本公开的各种非限制性实施方式。44.应用场景总览45.本公开实施例中的方法可以应用于spark离线数据传输场景中,具体的,可将离线hdfs中的hive表、parquet格式文件等的数据记录经过提取、转换、序列化过程后,写入线上kv存储中,其中,spark在读取hive或parquet数据时,先加载成dataframe抽象概念,对于dataframe中的每个row对象,将row转换为实例map对象,即map《string,object》对象,然后,调用转换客户端的序列化接口,将map《string,object》对象序列化为protobuf二进制字节数组,即可写入kv存储。46.需要说明的是,在转换实例map的过程中,准备一个存放返回值的结果map《string,object》,通过数据表的元数据遍历schema中所有需要上线的实例字段,从row对象中提取实例字段的值,转换为对应的java数据类型,添加至map《string,object》。47.本公开实施例中的方法还可以应用于flink实时数据计算中,具体的,在flink框架中,实时消费来自消息队列的流式数据,按照业务逻辑进行提取、处理、计算、序列化后,写入线上kv存储中,通过本公开实施例中的方法,flink的代码只要将结果数据构造成map《string,object》对象,然后调用转换客户端的序列化接口,即可把map对象序列化为protobuf二进制字节数组,写入kv存储。48.示例性方法49.下面结合上述应用场景,来描述根据本公开示例性实施方式的语音检测方法。需要注意的是,上述应用场景仅是为了便于理解本公开的精神和原理而示出,本公开的实施方式在此方面不受任何限制。相反,本公开的实施方式可以应用于适用的任何场景。50.基于上述实施例,参阅图1所示,为本公开实施例中protobuf数据编码方法的第一流程示意图,具体包括:51.步骤100:响应于针对实例map对象的序列化请求,获取元数据。52.其中,元数据中至少包括:各字段名和对应的字段类型,每个字段名对应一种字段类型。53.本公开实施例中,接收针对实例map对象的序列化请求,响应接收到的序列化请求,执行针对实例map对象的序列化过程,获取元数据。54.可选的,本公开实施例中,为获取元数据提供了一种可能的实施方式,具体包括:55.s1:从数据管理设备中,获取包含有各初始元数据的初始属性文件。56.本公开实施例中,转换客户端通过数据管理设备的设备接口,从数据管理设备中获取数据表的元信息,其中,元信息包括数据表的初始属性文件,初始属性文件中包含有各初始元数据。57.需要说明的是,本公开实施例中,为获取初始属性文件提供了三种可能的实施方式,下面对本公开实施例中获取初始属性文件的过程进行说明:58.第一种实施方式:若确定首次启动程序,则从数据管理设备中,获取包含有各初始元数据的初始属性文件。59.本公开实施例中,若确定运行的程序为首次启动,则通过数据管理设备的设备接口,从数据管理设备中,获取包含有各初始元数据的初始属性文件。60.第二种实施方式:若确定预设的计时时间段到时,则从数据管理设备中,获取包含有各初始元数据的初始属性文件。61.本公开实施例中,当程序启动时,开始计时,在程序运行的过程中,持续进行计时,若确定预设的计时时间段到时,则通过数据管理设备的设备接口,从数据管理设备中,获取包含有各初始元数据的初始属性文件。62.例如,假设计时时间段为5分钟,则在程序运行的过程中,每隔5分钟,从数据管理设备中获取初始属性文件。63.第三种实施方式:若确定检测到数据管理设备中的初始元数据更新,则从数据管理设备中,获取包含有各初始元数据的初始属性文件。64.本公开实施例中,在程序运行的过程中,当用户在数据管理设备中更新初始元数据时,存储至数据管理设备中的数据表的proto文件也同样被更新,生成更新反馈信息,并将更新反馈信息发送给转换客户端,从而转换客户端在接收到更新反馈信息后,检测到数据管理设备中的初始元数据更新,从数据管理设备中获取包含有各初始元数据的初始属性文件。65.s2:对初始属性文件进行文本编译,获得初始属性对象。66.本公开实施例中,转换客户端在运行过程中,对初始属性文件进行动态文本编译,从而获得初始属性对象。67.需要说明的是,本公开实施例中获得初始属性对象的过程可以通过设置在数据管理设备中的schema解析器实现,采用开源项目protostuff在运行过程中,可以动态地将初始属性文件编译为初始属性对象。68.其中,初始属性文件例如可以为proto文本,初始属性对象例如可以为proto对象。69.s3:将初始属性对象转换构造为包含有各元数据的属性描述对象。70.本公开实施例中,解析初始属性对象的内容,将初始属性对象转换构造为属性描述对象。71.例如,当本公开实施例中的方法应用至java场景时,初始属性对象为proto对象,属性描述对象为descriptor对象,解析proto对象的对象内容,将proto对象转换构造为descriptor对象,当descriptor对象构造好后,将《数据表名,descriptor对象》的键值对写入descriptor缓存中,直至程序停止。这样,当目标对象在数据管理设备中修改数据表的proto文本时,触发转换客户端获取元数据,拉取到新的proto文本后,schema解析器对其编译构造成新的descriptor对象,从而能够替换掉descriptor缓存中生成时间点较早的descriptor对象。72.需要说明的是,由于属性描述对象内包含有初始属性文件的所有初始元数据,因此,获得属性描述对象为本公开实施例中protobuf数据编码方法实现的基础。73.其中,初始属性文件中例如可以包括proto中的消息,每个消息中的字段类型、字段名、字段序号、字段注释等,本公开实施例中对此并不进行限制。74.s4:从属性描述对象内获取元数据。75.本公开实施例中,由于属性描述对象内包含有所有的元数据信息,因此,可以从属性描述对象内获取元数据。76.这样,转换客户端能够实现在运行时对proto文本的动态编译,在运行过程中,使用转换客户端的程序均能够在运行时动态感知到schema和proto的变更,能够简化使用protobuf开发的工作流程,无需人工使用protoc编译器编译proto文本生成含解析逻辑的.java文件,并且,也无需人工将编译后的.java文件应用到所有使用了protobuf对象的地方的过程。因此,proto的更新只需要在数据管理设备一处操作,便可生效到所有使用了该protobuf对象的地方,即达成一处配置,到处生效的效果。77.步骤110:依次遍历各字段名,执行以下操作:根据任意一字段名,从实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出目标实例字段中的目标字段值,将目标字段值添加至动态消息对象中。78.本公开实施例中,依次遍历各字段名,分别执行以下操作:根据任意一字段名,从实例map对象中确定出目标实例字段,由于每个字段名对应的一个字段类型,因此,基于字段名,确定出对应的字段类型,并确定字段类型对应的字段值提取方式,根据确定出的字段值提取方式,对目标实例字段进行字段值提取,获得目标字段值,最后,将获得的目标字段值添加至动态消息对象中。79.需要说明的是,本公开实施例中可通过转换客户端中的序列化接口,实现步骤110,具体的,在本实施例中,序列化接口的方法签名可以表示为:80.byte[]serialize(stringtable,map《string,object》data)[0081]在具体实现过程中,将数据表名table、实例map对象map《string,object》作为序列化接口的输入参数,首先,根据获取到的table,从descriptor缓存中获取到与table对应的descriptor对象,然后,再调用builddynamicmessage方法,将map《string,object》转换构造为dynamicmessage对象,最后,调用dynamicmessage对象的tobytearray方法,返回protobuf的二进制字节数组,完成数据编码。[0082]其中,上述tobytearray方法可以参考相关技术中的实现方式,tobytearray方法用于将dynamicmessage对象转换为二进制字节数组,上述builddynamicmessage方法,为步骤110的过程,builddynamicmessage的方法签名可以表示为:[0083]dynamicmessagebuilddynamicmessage(map《string,object》data,descriptordesc)[0084]其中,desc表征从descriptor缓存中提取出的descriptor对象。[0085]具体的,在builddynamicmessage方法内部,首先,设置一个用于构建结果的dynamicmessage.builder,该类是dynamicmessage类中的内部类,采用建造者模式构建dynamicmessage对象,通过descriptor对象的getfields方法,遍历各实例字段的fielddescriptor对象,对于每个fielddescriptor对象,获取字段名和字段类型,通过字段名,从实例map对象map《string,object》中提取出该实例字段待序列化前的取值,即实例字段值,若确定字段名在map《string,object》中不存在,则认为该实例字段无值,不作处理。[0086]具体的,本公开实施例中,基于字段名确定出的字段类型可以分为以下三种,分别为消息、枚举和其它,下面分别对本公开实施例中,字段类型为消息、枚举和其它时,获得动态消息对象的过程进行说明。[0087]第一种字段类型:消息。[0088]具体的,若确定字段类型为消息,则将目标实例字段对应的实例字段值,构建为第一目标格式的目标字段值,并将目标字段值添加至动态消息对象中。[0089]本公开实施例中,若目标实例字段对应的字段类型为消息,则读取目标实例字段对应的实例字段值,由于实例字段值为第二目标格式下的字段值,因此,确定目标实例字段所属的子类型,并根据确定出的子类型对应的第一格式转换方式,将第二目标格式下的实例字段值构建为第一目标格式下的目标字段值,并将目标字段值添加至动态消息对象中。[0090]其中,本公开实施例中,消息对应的子类型可以划分为以下三种,分别为键值对、重复消息和单消息,下面分别对本公开实施例中,子类型为键值对、重复消息和单消息时,获得动态消息对象的过程进行具体说明。[0091]第一种子类型:键值对。[0092]具体的,若确定消息为键值对,则将目标实例字段内包含的键值对数据中的各目标键数据和目标值,构建为第一目标格式的目标字段值,并将目标字段值添加至动态消息对象中。[0093]本公开实施例中,当消息的子类型为键值对时,目标实例字段以连续的键值对形式保存数据,因此,读取目标实例字段对应的取值,在该实施例中,读取出的取值为键值对数据,由于键值对数据内包含有多个目标键数据和每个目标键数据对应的目标值,因此,分别将键值对数据中的各目标键数据和相应的目标值,构建为第一目标格式下的目标字段值,目标实例字段值为对象字段的取值,即,对象字段的取值是由多个目标实例字段值组成的,最后,将对象字段及其各目标实例字段值添加至动态消息对象中。[0094]例如,当本公开实施例中的方法应用于java时,假设子类型为键值对,即,map,map在protobuf中的本质是一个消息,当子类型为map时,目标实例字段是以连续的《key,value》键值对的形式保存数据,因此,根据字段名,从map《string,object》中提取出的目标实例字段的数据形式仍然为map,然后,将map中的各目标键数据和相应的目标值,构建为第一目标格式下的相应的目标字段值,将目标字段值添加至list《dynamicmessage》对象中,因此,list《dynamicmessage》对象包含有各个目标字段值,将list《dynamicmessage》对象添加至dynamicmessage.builder中。[0095]下面采用一个具体的例子对本公开实施例中获得动态消息对象的过程进行说明,例如,参阅图2所示,为本公开实施例中实例map对象的示例图,其中,{}表示map数据结构,[]表示list数据结构,冒号左边表示map的key,冒号右边表示map的value。通过descriptor对象的getfields方法,遍历所有字段时,会依次遍历消息的第一级字段,即按照id、name、age、height、address、phone_numbers、course_scores、cars的顺序遍历,假设course_scores字段的类型为消息,且其属于子类型“键值对”,根据字段名“course_scores”从map《string,object》中读取出的键值对数据的数据形式依然为map,即{"数学":92,"英语":88},其中,将键值对数据《“数学”,92》中的目标键数据“数学”和目标值“92”构造为具有两个目标字段值(数学)和(92)的dynamicmessage,并将键值对数据《“英语”,88》中的目标键数据“英语”和目标值“88”构造为具有两个目标字段值(英语)和(88)的dynamicmessage,从而能够将键值对数据构建为list《dynamicmessage》对象,添加至dynamicmessage.builder中。[0096]第二种子类型:重复消息。[0097]具体的,若确定消息为重复消息,则从目标实例字段中,提取出消息集合,并依次遍历消息集合中的各实例字段值,构建为相应的第一目标格式的目标字段值,获得第一目标字段值集合,将第一目标字段值集合添加至动态消息对象中。[0098]本公开实施例中,当消息的子类型为重复消息时,读取目标实例字段对应的取值,在该实施例中,目标实例字段的取值为消息集合,依次遍历消息集合中的各实例字段值,分别将各第二目标格式下的实例字段值,构建为第一目标格式下相应的目标字段值,在获得各目标字段值后,生成包含有各目标字段值的第一目标字段值集合,并将第一目标字段值集合添加至动态消息对象中。[0099]例如,当本公开实施例中的方法应用于java时,假设字段类型的子类型为重复消息,即,repeatedmessage,从map《string,object》中确定出的目标实例字段对应的取值为消息集合,该消息集合是一个list《map《string,object》》对象,因此,遍历该消息集合中的各map对象,即,各实例字段值,分别将各map对象构建为第一目标格式下的目标字段值,生成包含有各目标字段值的第一目标字段值集合list《dynamicmessage》,因此,list《map《string,object》》对象整体上被构造为list《dynamicmessage》对象,将list《dynamicmessage》添加至dynamicmessage.builder对象中。[0100]下面采用一个具体的例子对本公开实施例中获得动态消息对象的过程进行说明,如图2所示,假设cars字段的子类型为重复消息,则根据字段名“cars”,从map《string,object》中确定出的目标实例字段对应的取值为列表list《map《string,object》》,遍历list《map《string,object》》中的各map对象,仅包含一辆车,即内容为{"brand":"大众","model":"朗逸","color":2}的map,将{"brand":"大众","model":"朗逸","color":2}转换构建为第一目标格式下的各目标字段值,并生成包含有各目标字段值的list《dynamicmessage》对象,并将list《dynamicmessage》对象添加至dynamicmessage.builder对象中。[0101]第三种子类型:若确定消息为单消息,则将目标实例字段对应的实例字段值,构建为第一目标格式的目标字段值,并将目标字段值添加至动态消息对象中。[0102]本公开实施例中,当消息的子类型为单消息时,读取目标实例字段对应的实例字段值,将第二目标格式下的实例字段值,构建为第一目标格式下的目标字段值,并将第一目标字段值添加至动态消息对象中。[0103]例如,当本公开实施例中的方法应用于java时,假设子类型为单消息,即单message,从map《string,object》对象中确定出的目标实例字段对应的目标实例字段值依然为map对象,因此,直接将map对象构建为第一目标格式下的目标字段值,并将目标字段值添加至dynamicmessage对象,将获得的dynamicmessage对象添加至dynamicmessage.builder对象中。[0104]第二种类型:枚举。[0105]具体的,若确定字段类型为枚举,则将目标实例字段中枚举数对应的枚举值作为目标字段值,并将目标字段值添加至动态消息对象中。[0106]本公开实施例中,若目标实例字段对应的字段类型为枚举,则读取目标实例字段对应的取值,在该实施例中,读取出的取值为枚举数,基于各枚举数与枚举值之间的对应关系,确定枚举数对应的枚举值,将确定出的枚举值作为目标字段值,并将目标字段值添加至动态消息对象中。[0107]其中,本公开实施例中,枚举对应的子类型可以划分为以下两种,分别为重复枚举和单枚举,下面对本公开实施例中,子类型为重复枚举和单枚举时,获得动态消息对象的过程进行具体说明。[0108]第一种子类型:重复枚举。[0109]具体的,若确定枚举为重复枚举,则从目标实例字段中,提取出枚举数集合,并依次遍历枚举数集合中的各枚举数,获得各枚举数对应的枚举值,将确定出的各枚举值作为相应的目标字段值,将包含有各目标字段值的第二目标字段值集合添加至动态消息对象中。[0110]本公开实施例中,当枚举的子类型为重复枚举时,读取目标实例字段的取值,在该实施例中,读取出的取值为枚举数集合,由于枚举数集合中包含有多个枚举数,因此,依次遍历枚举数集合中包含的各枚举数,结合各枚举数与枚举值之间的对应关系,分别获得各枚举数对应的枚举值,并分别将确定出的各枚举值作为相应的目标字段值,生成包含有各目标字段值的第二目标字段值集合,并将第二目标字段值集合添加至动态消息对象中。[0111]例如,当本公开实施例中的方法应用于java时,子类型为重复枚举,即,repeatedenum,从map《string,object》中提取出的目标实例字段对应的取值为枚举数集合,即,list《integer》,分别确定list《integer》中,各枚举数对应的枚举值,获得第二目标字段值集合list《enumvaluedescriptor》,并将list《enumvaluedescriptor》添加至dynamicmessage.builder对象中。[0112]第二种子类型:单枚举。[0113]具体的,若确定枚举为单枚举,则确定目标实例字段内包含的枚举数对应的枚举值,将确定出的枚举值作为目标字段值,将目标字段值添加至动态消息对象中。[0114]本公开实施例中,当枚举的子类型为单枚举时,读取目标实例字段对应的取值,在该实施例中,读取出的取值为枚举数,然后,根据各枚举数与枚举值之间的对应关系,确定枚举数对应的枚举值,将确定出的枚举值作为目标字段值,并将目标字段值添加至动态消息对象中。[0115]例如,当本公开实施例中的方法应用于java时,子类型为单枚举,即,单enum,从map《string,object》中提取出的目标实例字段对应的取值为枚举数,即,integer,确定integer对应的枚举值,将确定出的枚举值作为目标字段值,并基于目标字段值构建为enumvaluedescriptor对象,将enumvaluedescriptor对象添加至dynamicmessage.builder对象中。[0116]下面采用一个具体的例子进行说明,如图2所示,在构造一辆车的过程中,对于color字段,color字段对应的子类型为单枚举,根据字段名“color”从map《string,object》中获取到的枚举数为2,确定出对应的枚举值为blue,构造其对应的enumvaluedescriptor对象,并将enumvaluedescriptor对象dynamicmessage.builder对象中。[0117]第三种类型:若确定字段类型为其它,则将目标实例字段对应的实例字段值,作为目标字段值,添加至动态消息对象中。[0118]本公开实施例中,若确定字段类型为其它,则读取目标实例字段对应的实例字段值,并直接将确定出的实例字段值作为目标字段值,将目标字段值添加至动态消息对象中。[0119]例如,当本公开实施例中的方法应用于java,且目标实例字段对应的字段类型为其它时,从map《string,object》中提取出的目标实例字段值无需转换,可将目标实例字段值直接作为目标字段值,将目标字段值添加至dynamicmessage.builder对象中。[0120]下面采用一个具体的例子进行说明,如图2所示,对于id字段,其对应的字段类型为其它,根据字段名“id”,确定实例字段值为555,并将555作为目标实例字段值,直接添加至dynamicmessage.builder对象中,对于name、age、height、address、phone_numbers字段,为相似的处理过程,在此不过多赘述。[0121]需要说明的是,本公开实施例中字段类型“其它”为基本数据类型,例如bool、int32、int64、float、double等,还可以是string类型,还可以是基本数据类型前加有repeated关键字的数据类型。[0122]步骤120:对生成的动态消息对象进行序列化编码,获得编码数据。[0123]本公开实施例中,在获得动态消息对象后,则对动态消息对象进行序列化编码,从而获得二进制字节数组的编码数据,完成序列化。[0124]进一步地,本公开实施例中,在获得编码数据后,还可以对编码数据进行反序列化,从而获得实例map对象,下面对本公开实施例中对编码数据进行反序列化的过程进行说明,具体包括:[0125]s1:响应于针对编码数据的反序列化请求,获取编码数据。[0126]本公开实施例中,接收针对编码数据的反序列化请求,响应接收到的反序列化请求,获取编码数据,并执行针对编码数据的反序列化过程。[0127]s2:对编码数据进行解码,获得动态消息对象。[0128]其中,动态消息对象中至少包括各字段值。[0129]本公开实施例中,由于编码数据为二进制字节数组,因此,先对编码数据进行解码,从而获得动态消息对象。[0130]s3:依次遍历各字段值,执行以下操作:根据任意一个字段值对应的字段类型,确定字段值对应的字段转换方式,基于字段值转换方式,将字段值转换为目标实例字段对应的实例字段值,并将实例字段值添加至实例map对象中。[0131]本公开实施例中,依次遍历各字段值,分别针对各字段值,执行以下操作:根据任意一个字段值对应的字段类型,确定对该字段值进行反序列化时所采用的字段转换方式,然后,基于确定出的字段转换方式,将该字段值转换为实例字段值,转换获得的实例字段值为目标实例字段对应的取值,最后,将获得的实例字段值添加至实例map对象中,从而实现对于编码数据的反序列化过程。[0132]例如,本公开实施例中反序列化过程可以通过反序列化接口实现,反序列化接口能够实现在运行时动态地将protobuf二进制字节数组反序列化成map《string,object》的过程,其中,反序列化接口的方法签名可以表示为:[0133]map《string,object》deserialize(stringtable,byte[]data)[0134]需要说明的是,反序列化接口是序列化接口的逆过程,以数据表名table、protobuf二进制字节数组为输入参数,首先,根据数据表名从descriptor缓存中获取到对应的descriptor对象,再调用dynamicmessage.parsefrom(descriptortype,byte[]data)方法解析出dynamicmessage对象,从而获得动态消息对象,再对动态消息对象调用parsedynamicmessage方法,将dynamicmessage对象转换为map《string,object》对象返回,完成反序列化。[0135]其中,parsedynamicmessage方法的方法签名可以表示为:[0136]map《string,object》parsedynamicmessage(dynamicmessagedmsg)[0137]其中,在parsedynamicmessage方法内部,首先,设置一个用于保存结果的map《string,object》,然后,通过dynamicmessage.getallfields方法取到全部有值字段的字段值集合,再获得映射后的map《string,object》。[0138]具体的,本公开实施例中,基于字段名确定出的字段类型可以分为以下消息、枚举、字节和其它,下面分别对本公开实施例中,字段类型为消息、枚举、字节和其它时,获得实例map对象的过程进行说明。[0139]第一种字段类型:消息。[0140]具体的,若确定字段类型为消息,则将字段值,构建为第二目标格式的目标实例字段对应的实例字段值,并将实例字段值添加至实例map对象中。[0141]本公开实施例中,若目标字段对应的字段类型为消息,则读取对象字段对应的字段值,由于字段值为第一格式下的字段值,因此,确定对象字段所属的子类型,并根据确定出的子类型对应的第二格式转换方式,将第一目标格式下的字段值构建为第二目标格式下的实例字段值,将确定出的实例字段值作为相应实例字段对应的取值,并将实例字段添加至实例map对象中。[0142]其中,本公开实施例中,消息对应的子类型可以划分为以下三种,分别为键值对、重复消息和单消息,下面分别对本公开实施例中,子类型为键值对、重复消息和单消息时,获得实例map对象的过程进行说明。[0143]第一种子类型:键值对。[0144]具体的,若确定消息为键值对,则将字段值构建为第二目标格式的键值对数据,并将键值对数据作为目标实例字段对应的实例字段值,将实例字段值添加至实例map对象中。[0145]本公开实施例中,当消息的子类型为键值对时,读取对象字段对应的字段值,将字段值构建为第二目标格式下的键值对数据,键值对数据中包含有各目标键数据和相应的目标值,然后,将键值对数据作为目标实例字段对应的实例字段值,将具有实例字段值的目标实例字段添加至实例map对象中。[0146]例如,当本公开实施例中的方法应用于java时,子类型“键值对”为map,首先,从dynamicmessage.builder对象中包含的各对象字段中,确定出具有取值的对象字段,从而生成包含有各具有取值的对象字段的有值字段集合,从有值字段集合中遍历的各对象字段为list《dynamicmessage》对象,根据protobuf的map编码规则,list《dynamicmessage》对象中的每一个dynamicmessage均表示《key,value》键值对数据,因此,遍历该list《dynamicmessage》对象,对每个dynamicmessage取出并解析获得《key,value》键值对,将当前的对象字段的字段名到《key,value》键值对的映射添加至map《string,object》中。[0147]需要说明的是,若键值对的value依然为message类型,则需要递归调用parsedynamicmessage方法去获得实例字段值。[0148]第二种子类型:重复消息。[0149]具体的,若确定消息为重复消息,则依次遍历对象集合中的各字段值,分别将各字段值构建为第二目标格式的目标实例字段对应的实例字段值,生成包含有各实例字段值的消息集合,将消息集合添加至实例map对象中。[0150]本公开实施例中,当消息的子类型为重复消息时,读取对象字段对应的取值,在该实施例中,对象字段的取值为对象集合,对象集合中包含有各字段值,依次遍历对象集合中的各字段值,分别将各第一目标格式下的字段值,构建为第二目标格式下的实例字段值,获得的实例字段值为目标实例字段的取值,在获得各实例字段值后,生成包含有各实例字段值的消息集合,并将消息集合添加至实例map对象中。[0151]例如,当本公开实施例中的方法应用于java时,假设字段类型的子类型为重复消息,即,repeatedmessage,确定出的对象字段在list《dynamicmessage》对象中,读取对象字段对应的取值,获得对象集合,即list《dynamicmessage》,遍历list《dynamicmessage》,对其中的每一个dynamicmessage对象中的字段值,递归调用parsedynamicmessage方法去解析,从而将各第一目标格式下的字段值,构建为第二目标格式下的实例字段值,生成包含有各实例字段值的list《map《string,object》》,从而实现将list《dynamicmessage》对象转换构造为list《map《string,object》》对象,最后,将list《map《string,object》》对象添加至map《string,object》中。[0152]第三种子类型:单消息。[0153]具体的,若确定消息为单消息,则将字段值,构建为第二目标格式的目标实例字段对应的实例字段值,将实例字段值添加至实例map对象中。[0154]本公开实施例中,当消息的子类型为单消息时,读取对象字段对应的字段值,将第一目标格式下的字段值,构建为第二目标格式下的实例字段值,并将实例字段值添加至实例map对象中。[0155]例如,当本公开实施例中的方法应用于java时,假设字段类型为单消息,即message,则当前的对象字段是一个dynamicmessage对象,直接递归调用parsedynamicmessage方法去解析,parsedynamicmessage方法具体为,将第一目标格式下的dynamicmessage,构建为第二目标格式下的实例字段值,通过parsedynamicmessage方法能够将dynamicmessage对象转换为map《string,object》对象,最后,将实例字段值添加至map《string,object》中。[0156]第二种字段类型:枚举。[0157]具体的,若确定字段类型为枚举,则确定字段值中枚举值对应的枚举数,并将枚举数作为目标实例字段对应的实例字段值,并将实例字段值添加至实例map对象中。[0158]本公开实施例中,若对象字段对应的字段类型为枚举,则读取对象字段对应的取值,在该实施例中,读取出的取值为枚举值,基于各枚举值与枚举数之间的对应关系,确定枚举值对应的枚举数,将确定出的枚举数作为目标实例字段对应的实例字段值,将实例字段值添加至实例map对象中。[0159]其中,本公开实施例中,枚举对应的子类型可以划分为以下两种,分别为重复枚举和单枚举,下面对本公开实施例中,子类型为重复枚举和单枚举时,获得实例map对象的过程进行说明:[0160]第一种子类型:重复枚举。[0161]具体的,若确定枚举为重复枚举,则依次遍历枚举值集合中的各枚举值,执行以下操作:获得各枚举值对应的枚举数,并将确定出的各枚举数作为相应的目标实例字段对应的实例字段值,将包含有各实例字段的实例字段集合添加至实例map对象中。[0162]本公开实施例中,当枚举的子类型为重复枚举时,读取对象字段的取值,在该实施例中,读取出的取值为枚举值集合,由于枚举值集合中包含有多个枚举值,因此,依次遍历枚举值集合中包含的各枚举值,结合各枚举值与枚举数之间的对应关系,分别获得各枚举值对应的枚举数,并分别将确定出的各枚举数作为相应的目标实例字段对应的实例字段值,生成包含有各实例字段的实例字段集合,将实例字段集合添加至实例map对象中。[0163]例如,当本公开实施例中的方法应用于java时,子类型为重复枚举,即,repeatedenum,当前的对象字段的取值是list《enumvaluedescriptor》对象,即枚举值集合,对于list《enumvaluedescriptor》中的每个enumvaluedescriptor对象,均为一个枚举值,获取其中包含的各整数枚举值,并将各整数枚举值转换为相应的枚举数,分别将确定出的各枚举数作为相应的实例字段值,生成包含有各实例字段的实例字段集合,即,list《integer》对象,并将list《integer》对象添加至map《string,object》中。[0164]第二种子类型:单枚举。[0165]具体的,若确定枚举为单枚举,则确定枚举值对应的枚举数,并将确定出的枚举数作为目标实例字段对应的实例字段值,将实例字段值添加至实例map对象中。[0166]本公开实施例中,当枚举的子类型为单枚举时,读取对象字段内的枚举值,基于各枚举值与枚举数之间的对应关系,获得枚举值对应的枚举数,并分别将确定出的枚举数作为目标实例字段对应的实例字段值,将实例字段值添加至实例map对象中。[0167]例如,当本公开实施例中的方法应用于java时,子类型为单枚举,即,单enum,当前的对象字段是一个enumvaluedescriptor对象,获取enumvaluedescriptor对象的整数枚举值,并将整数枚举值转换为对应的枚举数,即integer对象,将integer对象添加至map《string,object》中。[0168]第三种字段类型:字节。[0169]具体的,若确定字段类型为字节,则对字段值进行映射,获得映射后的字段值,将映射后的字段值作为目标实例字段对应的实例字段值,并将实例字段值添加至实例map对象中。[0170]本公开实施例中,若对象字段对应的字段类型为字节,则读取对象对应的取值,在该实施例中,读取出的取值为字段值,对字段值进行映射,获得映射后的字段值,将映射后的字段值作为目标实例字段对应的实例字段值,并将实例字段值添加至实例map对象中。[0171]其中,本公开实施例中,字节对应的子类型可以划分为以下两种,分别为重复字节和单字节,下面对本公开实施例中,子类型为重复字节和单字节时,获得实例map对象的过程进行说明:[0172]第一种子类型:重复字节。[0173]具体的,若确定字节为重复字节,则依次遍历字节集合中的各字段值,分别获得各字段值对应的映射后的字段值,并将各映射后的字段值作为目标实例字段对应的实例字段值,将包含有各实例字段的实例字段值集合添加至实例map对象中。[0174]本公开实施例中,当字节的子类型为重复字节时,读取对象字段的取值,在该实施例中,读取出的取值为字节集合,由于字节集合中包含有多个字段值,因此,依次遍历字节集合中包含的各字段值,分别对各字段值进行映射,获得各映射后的字段值,分别将各映射后的字段值作为目标实例字段对应的实例字段值,将包含有各实例字段的实例字段值集合添加至实例map对象中。[0175]例如,当本公开实施例中的方法应用于java时,子类型为重复字节,即,repeatedbytes,对象字段为list《bytestring》对象,读取list《bytestring》对象的取值,在该实施例中,读取出的取值为字节集合,分别将字节集合中的各字段值进行映射,获得各映射后的字段值,分别将各映射后的字段值作为目标实例字段对应的实例字段值,获得包含有实例字段值集合的list《byte[]》对象,使得将list《bytestring》对象整体转换为list《byte[]》对象,最后,将list《byte[]》对象添加至map《string,object》中。[0176]第二种子类型:单字节。[0177]具体的,若确定字节为单字节,则基于映射关系,对字段值进行映射,获得映射后的字段值,将映射后的字段值作为目标实例字段对应的实例字段值,将实例字段值添加至实例map对象中。[0178]本公开实施例中,当字节的子类型为单字节时,读取对象字段的字段值,对字段值进行映射,获得映射后的字段值,将映射后的字段值作为目标实例字段对应的实例字段值,并将实例字段值添加至实例map对象中。[0179]例如,当本公开实施例中的方法应用于java时,子类型为单字节,即,单bytes,当前的对象字段为一个bytestring对象,对将其转换为字节数组byte[],将当前字段名到byte[]对象的映射添加至结果map《string,object》中。[0180]第四种字段类型:其它。[0181]具体的,若确定字段类型为其它,则将字段值作为目标实例字段对应的实例字段值,并将实例字段值添加至实例map对象中。[0182]本公开实施例中,当字段类型为其它时,读取对象字段的字段值,并直接将读取出的字段值作为目标实例字段对应的实例字段值,无需进行转换,将实例字段值添加至实例map对象中。[0183]例如,当字段类型是基本数据类型,如,boolean、int32、int64、float、double等,还可以为string,还可以在前面再加上repeated关键字时,当前的字段值不需要做转换,可直接将实例字段值添加至map《string,object》中。[0184]进一步地,由于进行转换的对象字段均为有值字段,因此,本公开实施例中,可以将无值的字段同样添加至实例map对象中,具体包括:[0185]n1:采用字段全集和各字段值,确定出无值的字段集合。[0186]本公开实施例中,使用字段全集减去有值字段集合,可到无值的字段集合。[0187]其中,字段全集包含有有值的对象字段和无值的对象字段,各字段值均为有值的对象字段。[0188]n2:遍历无值字段集合,对每一个字段,将默认值作为目标实例字段对应的实例字段值,添加至实例map对象中。[0189]本公开实施例中,遍历无值的字段集合,对每一个对象字段,构造其字段类型对应默认值后放入map《string,object》中。[0190]需要说明的是,本公开实施例中,parsedynamicmessage方法最后,将保存结果的map《string,object》返回。[0191]本公开实施例中,可从数据管理设备获取proto文件,内置了对proto文件的编译器,可在运行时动态地对proto文件进行编译,生成protobuf对象的元数据描述descriptor对象并缓存在程序内存中。因此,当需要解析protobuf数据时,利用descriptor对象中包含的元数据,实现java语言的map《string,object》数据结构与protobuf二进制数据的相互转换,既包括将map序列化成protobuf二进制数据的过程,也包括将protobuf二进制数据反序列化成map的过程。这样,能够提高数据编码和数据解码的效率,并且,本公开实施例中用java语言的转换客户端,可方便地集成到运行于jvm之上的在线应用和大数据框架中,使之具备可配置化的动态protobuf编解码能力,具有更宽的适用领域,另外,转换客户端只需要编译一次,即可对数据进行解析,且在传输数据是,只需要业务数据文件,无需传递业务数据描述文件,节约了网络传输开销。[0192]基于上述实施例,参阅图3所示,为本公开实施例中protobuf数据编码方法的第二流程示意图,具体包括:[0193]步骤300:根据获取到的各属性数据,生成初始属性文件。[0194]本公开实施例中,数据管理设备获取用户配置的各属性数据,并根据获取到的各属性数据,生成初始属性文件。[0195]可选的,本公开实施例中,为生成初始属性文件提供了一种可能的实施方式,具体地,响应于生成指令,按照各属性数据对应的属性字段的排列顺序,生成包含有各初始元数据的初始属性文件。[0196]本公开实施例中,用户在数据管理设备的用户界面中,点击操作控件,从而触发生成指令,然后,遍历schema配置中的所有属性字段,对于上线字段,按照各属性数据对应的属性字段的排列顺序,生成包含有各初始元数据的初始属性文件。[0197]需要说明的是,本公开实施例中,若确定字段类型为消息或键值对为消息的字段,采用递归调用方法,生成包含有各初始元数据的初始属性文件,即,对于字段类型为message或map值为message的字段,由于包含有嵌套的子消息,因此,需要递归调用生成方法,生成嵌套子消息的message。[0198]步骤310:将初始属性文件发送给转化客户端,以使转化客户端根据初始属性文件,生成元数据,依次遍历元数据中包含的各字段名,执行以下操作:根据任意一字段名,从实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出目标实例字段中的目标字段值,将目标字段值添加至动态消息对象中,对生成的动态消息对象进行序列化编码,获得编码数据。[0199]本公开实施例中,将初始属性文件发送给转化客户端,从而使得转化客户端能够根据初始属性文件,生成元数据,依次遍历元数据中包含的各字段名,执行以下操作:根据任意一字段名,从实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出目标实例字段中的目标字段值,将目标字段值添加至动态消息对象中,对生成的动态消息对象进行序列化编码,获得编码数据。[0200]例如,参阅图4所示,为本公开实施例中的界面示意图,用户可通过数据管理设备的数据管理界面配置数据表的初始元数据,即schema,包括数据表中的字段名、字段类型、字段描述、时间戳、分区、上线、监控等信息,还包括proto文本定义的配置,数据管理设备还实现了获取元数据的接口,使得转换客户端能够实时地获取数据表的初始元数据和proto文本,以便能够动态地编译proto文本。[0201]其中,界面schema配置的左上角,有一个消息名,对应了proto定义中的根消息名,根消息指的是proto定义中最外层的没有被其他消息依赖的消息。[0202]界面schema配置的右上角,设置有“导入schema”操作控件,用于从离线数据源一键导入数据的schema,从而能够免去逐个字段手工添加编辑的操作,大大提高了编辑效率,这样,在离线hdfs中,parquet格式的文件或hive表均自带schema信息,若需要将数据快速接入数据管理设备,仅需要触发“导入schema”操作控件即可完成导入,无需一个一个字段地去编辑,极大地提高了编辑效率。[0203]如图4可知,schema配置的表格有9列,分别是序号、字段名、字段类型、数组、pk、sk、时间戳、分区、上线、监控指标、描述、操作,下面分别进行说明:[0204]其中,序号:表征字段的序号,对应于proto定义中的字段编号,非上线字段的序号均为0,上线字段的序号从1开始递增,新增字段时,序号根据后台当前最大序号加1自动生成,用户不可编辑序号;字段名:字段的名字,命名规则与proto字段命名规则一致;字段类型:字段的数据类型,包括int32、int64、float、double、string、bytes、map、message、enum、sparsevector、densevector等,sparsevector、densevector是为了支持parquet文件中的vector而特殊设置的,其中的map类型,还需要指定key和value的数据类型;其中的message类型,会展开并需要编辑一个嵌套的子消息,子消息的模式与最外层的根消息相同;数组:表示该字段是否是连续重复的数组,对应于proto定义中的repeated关键字;pk:表示该字段是否是主键,即primarykey,或kv表的k,或kkv表的第一个k;sk:表示该字段是否是二级键,即secondarykey,或kkv表的第二个k;时间戳:表示该字段是否是时间戳字段,保存的是该条记录的生成时间;分区:表示该字段是否是hive表的分区字段;上线:表示该字段是否要包含在kv值里导入到线上存储,进行勾选的字段会包含在proto定义中;监控指标:表示是否要对该字段进行一些基本统计指标监控;描述:该字段的含义描述;操作:可对该字段进行的操作,支持保存、删除。[0205]本公开实施例中,schema管理功能支持在schema与proto之间进行相互转换,在如图4用户界面中,包含有“生成proto”操作控件,用于将schema一键生成proto定义文本,生成语法满足proto3版本,后台会遍历schema配置中的所有字段,非上线字段忽略,对于上线字段按照顺序逐一生成proto定义中的字段信息。[0206]需要说明的是,对于字段类型为message或map值为message的字段,包含嵌套的子消息,会递归调用生成方法去生成嵌套子消息的message。[0207]进一步地,本公开实施例中,还可以将初始属性文件转换为相应的属性数据,下面对本公开实施例中获得属性数据的过程进行说明,具体包括:[0208]m1:将数据库中的初始属性文件编译转换为初始属性对象。[0209]本公开实施例中,可以通过触发如图4中所示的用户界面中的“生成schema”操作控件,获得初始属性对象,具体的,后台调用schema解析器的接口,将proto文本编译并转换为proto对象。[0210]需要说明的是,proto语法版本支持proto2和proto3。[0211]m2:依次遍历初始属性对象中的各属性字段,转换为相应的属性数据。[0212]本公开实施例中,依次遍历初始属性对象中的各属性字段,分别将各属性字段转换为属性数据。[0213]例如,遍历proto对象中message的所有属性字段,并将属性字段转换为schema的形式,存入数据库。[0214]需要说明的是,对于字段类型为message或map值为message的字段,会递归解析子消息里的字段,转换为schema。[0215]进一步地,如图4所示的用户界面中,proto定义模块用于编辑保存数据表的proto文本,点击保存操作控件时,proto文本的修改会直接实时同步到线上服务的转换客户端中,经由schema解析器在运行时编译成新的descriptor对象,若修改前的proto与修改后的proto不兼容,则会直接导致数据读取反序列化出错,影响线上服务,因此需要严格限制proto的更新,保障proto修改向前兼容,因此,本公开实施例中还可以对初始属性文件的兼容性进行校验,下面对本公开实施例中对初始属性文件的兼容性进行校验的过程进行说明。[0216]本公开实施例中,在对初始属性文件进行校验时,可以通过以下方式对初始属性文件的兼容性进行校验,至少包括以下一种:[0217]第一种:对初始元数据对应的数据字段的序号进行校验。[0218]具体的,在生成初始属性文件时,不能更改任务已存在字段的序号,因此,当确定初始元数据对应的数据字段的序号未更改时,确定初始属性文件的兼容性校验结果为通过,当确定初始元数据对应的数据字段的序号更改时,确定初始属性文件的兼容性校验结果为未通过。[0219]其中,每个字段等号后的数字就是序号。[0220]第二种:对添加数据字段时所采用的序号是否被占用进行校验。[0221]具体的,在生成初始属性文件时,添加数据字段时所使用的序号应当为proto定义中未占用过的序号,因此,当确定添加数据字段时采用的序号未占用,确定初始属性文件的兼容性校验结果为通过,当确定添加数据字段时所采用的序号被占用,确定初始属性文件的兼容性校验结果为未通过。[0222]第三种:对是否添加或删除固定字段进行校验。[0223]具体的,在生成初始属性文件时,不能添加或删除固定字段,因此,当确定未删除或添加固定字段,确定初始属性文件的兼容性校验结果为通过,当确定删除或添加固定字段,确定初始属性文件的兼容性校验结果为未通过。[0224]需要说明的是,本公开实施例中,不能添加或删除任何required字段,可以删除optional或repeated字段。[0225]第四种:对是否修改数据字段的关键字进行校验。[0226]具体的,在生成初始属性文件时,不能修改数据字段的关键字,因此,当确定未修改数据字段的关键字,确定初始属性文件的兼容性校验结果为通过,当确定修改数据字段的关键字,确定初始属性文件的兼容性校验结果为未通过。[0227]需要说明的是,不能修改已有字段的修饰关键字,如required、optional、repeated等。[0228]本公开实施例中,通过对元数据进行统一管理,schema配置管理能力使得接入系统的数据能够统一以protobuf为编码标准来使用能够给离线数据管理、特征数据复用提供便捷,从而简化了数据编码的流程,并且,schema配置里各个字段包含详细的信息和描述,使数据含义更清晰,便于数据管理和复用。[0229]进一步地,本公开实施例中,可以通过点击如图4中的保存操作控件,当点击保存时,数据管理设备会在正式保存生效前,基于上述规则做proto修改前后兼容性校验,校验不通过的,不允许保存。[0230]基于上述实施例,参阅图5所示,为本公开实施例中转换客户端的结构示意图,其中:[0231]1、数据管理设备:用于获取表proto定义。[0232]2、转换客户端:包括schema解析器、descriptor缓存、序列化接口和反序列化接口。[0233](1)schema解析器:用于在运行时拉取protostuff-paeser,即,初始属性文本,并在运行时编译生成descriptor对象,即属性描述对象。[0234](2)descriptor缓存:用于存储数据表名与descriptor对象,及数据表明与descriptor对象之间的映射关系,因此,可通过数据表名,从descriptor缓存中获取到对应的descriptor对象。[0235](3)序列化接口:输入参数为数据表名和map《string,object》对象,调用byte[]serialize{stringtable,map《string,object》data},返回protobuf二进制字节数组。[0236]具体的,在动态序列化过程中,首先,解析descriptor对象,然后,采用序列化方式,获得动态消息对象,即dynamicmessage对象。[0237]其中,序列化方式可以表示为:[0238]dynamicmessage.newbuilder(descriptortype).setfield(fielddescriptorfield,objectvalue).build()[0239]然后,通过tobytearray方法,获得二进制字节数组,以及tablebyte[]。[0240](4)反序列化接口:输入参数为数据表名和protobuf二进制字节数组,调用map《string,object》deserialize{stringtable,byte[]data},返回map《string,object》对象。[0241]具体的,根据tablebyte[],从缓存中获取数据表名table对应的descriptor对象,然后在动态反序列化过程中,首先,解析descriptor对象,然后,采用反序列化方式,获得动态消息对象,即dynamicmessage对象,并构造map,获得map《string,object》对象。[0242]其中,反序列化方式可以表示为:[0243]dynamicmessage.parsefrom(descriptortype,byte[]data)[0244]本公开实施例中的转换客户端是一个采用java语言实现的jar包客户端,是动态protobuf数据编解码实现的核心,可快速便捷地集成进任何运行于jvm之上的框架中。比如,将转换客户端用于在线服务的spring框架,或用于离线数据处理任务的spark框架,或用于实时数据计算任务的flink框架。[0245]在spark里,做离线数据传输到线上存储时,可便捷地将离线的hive表、parquet格式数据序列化成protobuf二进制数据,离线写入线上存储。在flink里,可便捷地将实时数据流序列化成protobuf二进制数据,实时写入线上存储。[0246]基于上述实施例,下面对本公开实施例中的数据管理设备进行说明,参阅图6所示,为本公开实施例中数据管理设备的结构示意图。[0247]本公开实施例中,数据管理设备内包含schema配置模块和proto定义模块和schema对外接口。[0248]1、schema模块用于离线导入schema。包含有字段编辑配置模块,其中,字段编辑配置模块内包含有9个子模块,分别为序号、字段名、类型、数组、pk、sk、时间戳、分区、上线、监控、描述和操作。[0249]2、proto定义模块包含有proto兼容性校验模块、proto历史回滚模块。[0250]其中,proto兼容性校验模块用于对proto文本进行兼容性校验,proto历史回滚模块用于存储历史的proto文本。[0251]3、schema对外接口用于将schema发送给各处的转换客户端,包括在线服务客户端、离线任务客户端和实时任务客户端。[0252]示例性设备[0253]在介绍了本公开示例性实施方式的方法之后,接下来对本公开示例性实施方式的protobuf数据编码装置进行介绍。[0254]如图7所示,为本公开实施例提供的protobuf数据编码装置的第一结构示意图。在一个实施例中,protobuf数据编码装置70包括:获取模块700、第一处理模块710、编码模块720、第二处理模块730和第三处理模块740。[0255]获取模块700,用于响应于针对实例map对象的序列化请求,获取元数据,其中,所述元数据中至少包括:各字段名和对应的字段类型,每个字段名对应一种字段类型;[0256]第一处理模块710,用于依次遍历所述各字段名,执行以下操作:根据任意一字段名,从所述实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出所述目标实例字段中的目标字段值,将所述目标字段值添加至动态消息对象中;[0257]编码模块720,用于对生成的动态消息对象进行序列化编码,获得编码数据。[0258]可选的,所述获取元数据时,所述获取模块700还用于:[0259]从数据管理设备中,获取包含有各初始元数据的初始属性文件;[0260]对所述初始属性文件进行文本编译,获得初始属性对象;[0261]将所述初始属性对象转换构造为包含有各元数据的属性描述对象;[0262]从所述属性描述对象内获取元数据。[0263]可选的,所述从数据管理设备中,获取包含有各初始元数据的初始属性文件时,所述获取模块700还用于:[0264]若确定首次启动程序,则从数据管理设备中,获取包含有各初始元数据的初始属性文件;或,[0265]若确定预设的计时时间段到时,则从所述数据管理设备中,获取包含有各初始元数据的初始属性文件;或,[0266]若确定检测到数据管理设备中的所述初始属性数据更新,则从所述数据管理设备中,获取包含有各初始元数据的初始属性文件。[0267]可选的,所述根据字段类型对应的字段值提取方式,提取出所述目标实例字段中的目标字段值,将所述目标字段值添加至动态消息对象中时,所述第一处理模块710还用于:[0268]若确定所述字段类型为消息,则将所述目标实例字段对应的实例字段值,构建为第一目标格式的目标字段值,并将所述目标字段值添加至动态消息对象中;[0269]若确定所述字段类型为枚举,则将所述目标实例字段中枚举数对应的枚举值作为目标字段值,并将所述目标字段值添加至动态消息对象中;[0270]若确定所述字段类型为其它,则将所述目标实例字段对应的实例字段值,作为目标字段值,添加至所述动态消息对象中。[0271]可选的,所述将所述目标实例字段对应的实例字段值,构建为第一目标格式的目标字段值,并将所述目标字段值添加至动态消息对象中时,所述第一处理模块710还用于:[0272]若确定所述消息为键值对,则将所述目标实例字段内包含的键值对数据中的各目标键数据和目标值,构建为第一目标格式的目标字段值,并将所述目标字段值添加至动态消息对象中;[0273]若确定所述消息为重复消息,则从所述目标实例字段中,提取出消息集合,并依次遍历所述消息集合中的各实例字段值,构建为相应的第一目标格式的目标字段值,获得第一目标字段值集合,将所述第一目标字段值集合添加至动态消息对象中;[0274]若确定所述消息为单消息,则将所述目标实例字段对应的实例字段值,构建为第一目标格式的目标字段值,并将所述目标字段值添加至动态消息对象中。[0275]可选的,所述若确定所述字段类型为枚举,则将所述目标实例字段中枚举数对应的枚举值作为目标字段值,并将所述目标字段值添加至动态消息对象中时,所述第一处理模块710还用于:[0276]若确定所述枚举为重复枚举,则从所述目标实例字段中,提取出枚举数集合,并依次遍历所述枚举数集合中的各枚举数,获得所述各枚举数对应的枚举值,将确定出的各枚举值作为相应的目标字段值,将包含有各目标字段值的第二目标字段值集合添加至动态消息对象中;[0277]若确定所述枚举为单枚举,则确定所述目标实例字段内包含的枚举数对应的枚举值,将确定出的枚举值作为目标字段值,将所述目标字段值添加至动态消息对象中。[0278]可选的,所述获得编码数据之后,还包括第二处理模块730,所述第二处理模块730用于:[0279]响应于针对编码数据的反序列化请求,获取所述编码数据;[0280]对所述编码数据进行解码,获得动态消息对象,其中,所述动态消息对象中至少包括各字段值;[0281]依次遍历所述各字段值,执行以下操作:根据任意一个字段值对应的字段类型,确定所述字段值对应的字段转换方式,基于所述字段值转换方式,将所述字段值转换为目标实例字段对应的实例字段值,并将所述实例字段值添加至实例map对象中。[0282]可选的,所述基于所述字段值转换方式,将所述字段值转换为目标实例字段对应的实例字段值,并将所述实例字段值添加至实例map对象中时,所述第二处理模块730还用于:[0283]若确定所述字段类型为消息,则将所述字段值,构建为第二目标格式的目标实例字段对应的实例字段值,并将所述实例字段值添加至实例map对象中;[0284]若确定所述字段类型为枚举,则确定所述字段值中枚举值对应的枚举数,并将所述枚举数作为所述目标实例字段对应的实例字段值,并将所述实例字段值添加至实例map对象中;[0285]若确定所述字段类型为字节,则对所述字段值进行映射,获得映射后的字段值,将所述映射后的字段值作为目标实例字段对应的实例字段值,并将所述实例字段值添加至实例map对象中;[0286]若确定所述字段类型为其它,则将所述字段值作为目标实例字段对应的实例字段值,并将所述实例字段值添加至实例map对象中。[0287]可选的,所述将所述字段值,构建为第二目标格式的目标实例字段对应的实例字段值,并将所述实例字段值添加至实例map对象中时,所述第二处理模块730还用于:[0288]若确定所述消息为键值对,则将所述字段值构建为第二目标格式的键值对数据,并将所述键值对数据作为目标实例字段对应的实例字段值,将所述实例字段值添加至实例map对象中;[0289]若确定所述消息为重复消息,则依次遍历对象集合中的各字段值,分别将所述各字段值构建为第二目标格式的目标实例字段对应的实例字段值,生成包含有各实例字段值的消息集合,将所述消息集合添加至实例map对象中;[0290]若确定所述消息为单消息,则将所述字段值,构建为第二目标格式的目标实例字段对应的实例字段值,将所述实例字段值添加至实例map对象中。[0291]可选的,所述确定所述字段值中枚举值对应的枚举数,并将所述枚举数作为所述目标实例字段对应的实例字段值,将所述实例字段值添加至实例map对象中时,所述第二处理模块730还用于:[0292]若确定所述枚举为重复枚举,则依次遍历枚举值集合中的各枚举值,执行以下操作:获得所述各枚举值对应的枚举数,并将确定出的各枚举数作为相应的所述目标实例字段对应的实例字段值,将包含有各实例字段的实例字段集合添加至实例map对象中;[0293]若确定所述枚举为单枚举,则确定枚举值对应的枚举数,并将确定出的枚举数作为所述目标实例字段对应的实例字段值,将所述实例字段值添加至实例map对象中。[0294]可选的,所述对所述字段值进行映射,获得映射后的字段值,将所述映射后的字段值作为目标实例字段对应的实例字段值,将所述实例字段值添加至实例map对象中时,所述第二处理模块730还用于:[0295]若确定所述字节为重复字节,则依次遍历字节集合中的各字段值;获得任意一个字段值对应的映射后的字段值,并将所述映射后的字段值作为目标实例字段对应的实例字段值,将包含有各实例字段的实例字段值集合添加至实例map对象中;[0296]若确定所述字节为单字节,则基于映射关系,对所述字段值进行映射,获得映射后的字段值,将所述映射后的字段值作为目标实例字段对应的实例字段值,将所述实例字段值添加至实例map对象中。[0297]可选的,还包括第三处理模块740,所述第三处理模块740用于:[0298]采用字段全集和所述各字段值,确定出无值的字段集合;[0299]遍历所述无值字段集合,对每一个字段,将默认值作为目标实例字段对应的实例字段值,添加至实例map对象中。[0300]如图8所示,为本公开实施例提供的protobuf数据编码装置的第二结构示意图。在另一个实施例中,protobuf数据编码装置80包括:获取模块800、第一处理模块810、第二处理模块820和校验模块830。[0301]获取模块800,用于根据获取到的各属性数据,生成初始属性文件;[0302]第一处理模块810,用于将所述初始属性文件发送给转化客户端,以使所述转化客户端根据所述初始属性文件,生成元数据,依次遍历所述元数据中包含的各字段名,执行以下操作:根据任意一字段名,从所述实例map对象中确定出目标实例字段,并根据字段类型对应的字段值提取方式,提取出所述目标实例字段中的目标字段值,将所述目标字段值添加至动态消息对象中,对生成的动态消息对象进行序列化编码,获得编码数据。[0303]可选的,所述获取模块800还用于:[0304]响应于生成指令,按照各属性数据对应的属性字段的排列顺序,生成包含有各初始元数据的初始属性文件。[0305]可选的,所述按照初始元数据中包含的各初始字段各自对应的顺序,生成包含有各初始元数据的初始属性文件时,所述获取模块800还用于:[0306]若确定字段类型为消息或键值对为消息的字段,采用递归调用方法,生成包含有各初始元数据的初始属性文件。[0307]可选的,还包括第二处理模块820,所述第二处理模块820还用于:[0308]将数据库中的初始属性文件编译转换为初始属性对象;[0309]依次遍历所述初始属性对象中的各属性字段,转换为相应的属性数据。[0310]可选的,所述生成初始属性文件之后,还包括校验模块830,所述校验模块830用于:[0311]对所述初始属性文件的兼容性进行校验。[0312]可选的,所述对所述初始属性文件的兼容性进行校验之后,所述校验模块830还用于:[0313]当确定所述初始元数据对应的数据字段的序号未更改时,确定所述初始属性文件的兼容性校验结果为通过;和/或,[0314]当确定添加数据字段时采用的序号未占用,确定所述初始属性文件的兼容性校验结果为通过;和/或,[0315]当确定未删除或添加固定字段,确定所述初始属性文件的兼容性校验结果为通过;和/或,[0316]当确定未修改数据字段的关键字,确定所述初始属性文件的兼容性校验结果为通过。[0317]本公开实施例提供的protobuf数据编码装置,与上述protobuf数据编码方法采用了相同的发明构思,能够取得相同的有益效果,在此不再赘述。[0318]基于与上述protobuf数据编码方法相同的发明构思,本公开实施例还提供了一种电子设备。参阅图9所示,为本公开实施例中电子设备的结构示意图,该电子设备90可以包括处理器901和存储器902。[0319]处理器901可以是通用处理器,例如中央处理器(cpu)、数字信号处理器(digitalsignalprocessor,dsp)、专用集成电路(applicationspecificintegratedcircuit,asic)、现场可编程门阵列(fieldprogrammablegatearray,fpga)或者其他可编程逻辑器件、分立门或者晶体管逻辑器件、分立硬件组件,可以实现或者执行本公开实施例中公开的各方法、步骤及逻辑框图。通用处理器可以是微处理器或者任何常规的处理器等。结合本公开实施例所公开的方法的步骤可以直接体现为硬件处理器执行完成,或者用处理器中的硬件及软件模块组合执行完成。[0320]存储器902作为一种非易失性计算机可读存储介质,可用于存储非易失性软件程序、非易失性计算机可执行程序以及模块。存储器可以包括至少一种类型的存储介质,例如可以包括闪存、硬盘、多媒体卡、卡型存储器、随机访问存储器(randomaccessmemory,ram)、静态随机访问存储器(staticrandomaccessmemory,sram)、可编程只读存储器(programmablereadonlymemory,prom)、只读存储器(readonlymemory,rom)、带电可擦除可编程只读存储器(electricallyerasableprogrammableread-onlymemory,eeprom)、磁性存储器、磁盘、光盘等等。存储器是能够用于携带或存储具有指令或数据结构形式的期望的程序代码并能够由计算机存取的任何其他介质,但不限于此。本公开实施例中的存储器802还可以是电路或者其它任意能够实现存储功能的装置,用于存储程序指令和/或数据。[0321]示例性程序产品[0322]本公开实施例提供了一种计算机可读存储介质,用于储存为上述电子设备所用的计算机程序指令,其包含用于执行本公开任一示例性实施方式中的protobuf数据编码方法的程序。[0323]上述计算机存储介质可以是计算机能够存取的任何可用介质或数据存储设备,包括但不限于磁性存储器(例如软盘、硬盘、磁带、磁光盘(mo)等)、光学存储器(例如cd、dvd、bd、hvd等)、以及半导体存储器(例如rom、eprom、eeprom、非易失性存储器(nandflash)、固态硬盘(ssd))等。[0324]在一些可能的实施方式中,本公开的各个方面还可以实现为一种计算机程序产品,其包括程序代码,当该计算机程序产品在服务器设备上运行时,该计算机程序产品用于使服务器设备执行本说明书上述“示例性方法”部分中描述的根据本公开各种示例性实施方式的protobuf数据编码方法中的步骤。[0325]所述计算机程序产品可以采用一个或多个可读介质的任意组合。可读介质可以是可读信号介质或者可读存储介质。可读存储介质例如可以是——但不限于——电、磁、光、电磁、红外线、或半导体的系统、装置或器件,或者任意以上的组合。可读存储介质的更具体的例子(非穷举的列表)包括:具有一个或多个导线的电连接、便携式盘、硬盘、随机存取存储器(ram)、只读存储器(rom)、可擦式可编程只读存储器(eprom或闪存)、光纤、便携式紧凑盘只读存储器(cd-rom)、光存储器件、磁存储器件、或者上述的任意合适的组合。[0326]根据本公开的实施方式的用于即时通信应用的计算机程序产品,其可以采用便携式紧凑盘只读存储器(cd-rom)并包括程序代码,并可以在服务器设备上运行。然而,本公开的程序产品不限于此,在本文件中,计算机可读存储介质可以是任何包含或存储程序的有形介质,该程序可以被指令执行系统、装置或者器件使用或者与其结合使用。[0327]可读信号介质可以包括在基带中或者作为载波一部分传播的数据信号,其中承载了可读程序代码。这种传播的数据信号可以采用多种形式,包括——但不限于——电磁信号、光信号或上述的任意合适的组合。可读信号介质还可以是可读存储介质以外的任何可读介质,该可读介质可以发送、传播或者传输用于由指令执行系统、装置或者器件使用或者与其结合使用的程序。[0328]可读介质上包含的程序代码可以用任何适当的介质传输,包括——但不限于——无线、有线、光缆、rf等等,或者上述的任意合适的组合。[0329]可以以一种或多种程序设计语言的任意组合来编写用于执行本公开操作的程序代码,所述程序设计语言包括面向对象的程序设计语言—诸如java、c 等,还包括常规的过程式程序设计语言—诸如“c”语言或类似的程序设计语言。程序代码可以完全地在用户计算设备上执行、部分地在用户设备上执行、作为一个独立的软件包执行、部分在用户计算设备上部分在远程计算设备上执行、或者完全在远程计算设备或服务器上执行。在涉及远程计算设备的情形中,远程计算设备可以通过任意种类的网络——包括局域网(lan)或广域网(wan)—连接到用户计算设备,或者,可以连接到外部计算设备(例如利用因特网服务提供商来通过因特网连接)。[0330]应当注意,尽管在上文详细描述中提及了装置的若干单元或子单元,但是这种划分仅仅是示例性的并非强制性的。实际上,根据本公开的实施方式,上文描述的两个或更多单元的特征和功能可以在一个单元中具体化。反之,上文描述的一个单元的特征和功能可以进一步划分为由多个单元来具体化。[0331]此外,尽管在附图中以特定顺序描述了本公开方法的操作,但是,这并非要求或者暗示必须按照该特定顺序来执行这些操作,或是必须执行全部所示的操作才能实现期望的结果。附加地或备选地,可以省略某些步骤,将多个步骤合并为一个步骤执行,和/或将一个步骤分解为多个步骤执行。[0332]虽然已经参考若干具体实施方式描述了本公开的精神和原理,但是应该理解,本公开并不限于所公开的具体实施方式,对各方面的划分也不意味着这些方面中的特征不能组合以进行受益,这种划分仅是为了表述的方便。本公开旨在涵盖所附权利要求的精神和范围内所包括的各种修改和等同布置。当前第1页12当前第1页12
再多了解一些

本文用于企业家、创业者技术爱好者查询,结果仅供参考。

发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表

相关文献