Apache Ignite零部署:完全为零?


我们是零售技术开发部门。 一次,管理层设定了通过结合使用Apache Ignite和MSSQL来加快体积计算的任务,并向该站点展示了精美的插图和Java代码示例。 该网站立即喜欢“ 零部署”Zero Deployment) ,其描述带来了奇迹:您不必在网格中的每个节点上手动部署Java或Scala代码,并在每次更改时重新部署它。 在工作过程中,事实证明“零部署”具有特定用途,我想分享其功能。 在猫的思考和实现细节。


1.问题陈述


问题的实质如下。 有一个用于SalesPoint的销售点目录和一个产品Sku(库存单位)目录。 销售点的属性“商店类型”具有值“小”和“大”。 每个销售点都连接有一个分类(一个销售点的商品清单)(从DBMS装载),并且提供了有关指定产品已标明日期的信息
从分类中排除或添加到分类中。


需要组织一个销售点分区缓存,并在其中提前一个月存储有关关联商品的信息。 与战斗系统的兼容性要求Ignite客户端节点下载数据,计算类型的总计(商店类型,产品代码,日期,销售点数)并将其上传回DBMS。


2.文学研究


尚无经验,所以我开始在炉子上跳舞。 即,对出版物进行审查。


2016年的一篇文章Apache Ignite简介:第一步提供了指向Apache Ignite项目文档的链接,并同时对其进行了指责以供参考。 我读了几次,没有澄清。 转到官方的入门教程,该教程
乐观地承诺:“您将很快就可以启动并运行!”。 我了解环境变量的设置,观看了两个Apache Ignite Essentials视频,事实证明它们对我的特定任务不是很有用。 我使用标准文件“ example-ignite.xml”从命令行成功启动了Ignite,并使用Maven构建了第一个Compute Application 。 该应用程序可以正常工作并使用零部署,真是太好了!


我进一步阅读,然后在该示例中立即使用了finityKey(通过SQL查询在前面创建),甚至应用了神秘的BinaryObject:


IgniteCache<BinaryObject, BinaryObject> people = ignite.cache("Person").withKeepBinary(); 

我读了一点 :二进制格式有点反映,可以按名称访问对象的字段。 它可以读取字段的值,而无需完全反序列化对象(节省内存)。 但是为什么要使用BinaryObject而不是Person,因为存在零部署? 为什么将IgniteCache <Key,Person>转换为IgniteCache <BinaryObject,BinaryObject>? 目前尚不清楚。


我根据情况重新制作了“计算应用程序”。 MSSQL中销售点目录的主键定义为[id] [int] NOT NULL,我以此类推创建了一个缓存


 IgniteCache<Integer, SalesPoint> salesPointCache=ignite.cache("spCache") 

在xml-config中,我指示缓存已分区


 <bean class="org.apache.ignite.configuration.CacheConfiguration"> <property name="name" value="spCache"/> <property name="cacheMode" value="PARTITIONED"/> </bean> 

按销售点划分假设,将在群集的每个节点上为此处可用的salesPointCache记录构建所需的汇总,此后客户端节点将执行最终求和。


我阅读了《 First Ignite计算应用程序》教程,以此类推。 在群集的每个节点上,我运行IgniteRunnable(),如下所示:


  @Override public void run() { SalesPoint sp=salesPointCache.get(spId); sp.calculateSalesPointCount(); .. } 

我添加了聚合和上传逻辑,并在测试数据集上运行。 在本地,一切都可以在开发服务器上运行。


我启动两个CentOs测试服务器,在default-config.xml中指定IP地址,在每个服务器上执行


 ./bin/ignite.sh config/default-config.xml 

两个Ignite节点都会启动并互相看到。 我在客户端应用程序的xml-config中指定了必要的地址,它启动,将第三个节点添加到拓扑中,然后立即又有两个节点。 日志在该行中读取“ ClassNotFoundException:model.SalesPoint”


 SalesPoint sp=salesPointCache.get(spId); 

StackOverflow说该错误的原因是CentOs服务器没有自定义的SalesPoint类。 到了 那么,您如何不必在每个节点及以后手动部署Java代码? 还是您的Java代码与SalesPoint有关?


我可能错过了一些东西-再次开始搜索,阅读并再次搜索。 随着时间的流逝,我觉得我读了有关该主题的所有内容,没有什么新鲜的。 在搜索时,我发现了一些有趣的评论。


GridGain Systems的首席架构师Valentin Kulichenko对StackOverflow的回应 ,2016年4月:


 Model classes are not peer deployed, but you can use withKeepBinary() flag on the cache and query BinaryObjects. This way you will avoid deserialization on the server side and will not get ClassNotFoundException. 

另一种权威意见:GridGain Systems产品管理总监Denis Magda


关于Habré的关于微服务的文章引用了Denis Magda的三篇文章: 微服务 第一部分微服务 第二部分微服务 第三部分 2016-2017。 在第二篇文章中,Denis建议通过MaintenanceServiceNodeStartup.jar启动群集节点。 您还可以将启动与xml配置和命令行一起使用,但随后需要在每个部署的群集节点上手动放置自定义类:


 That's it. Start (..) node using MaintenanceServiceNodeStartup file or pass maintenance-service-node-config.xml to Apache Ignite's ignite.sh/bat scripts. If you prefer the latter then make sure to build a jar file that will contain all the classes from java/app/common and java/services/maintenance directories. The jar has to be added to the classpath of every node where the service might be deployed. 

的确如此。 原来,为什么,这种神秘的二进制格式!


3.单罐


Denis在我的个人评价中名列第一,恕我直言,它是所有可用教程中最有用的。 他的github MicroServicesExample包含一个配置群集节点的完全现成的示例,该示例无需任何其他蹲坐即可进行编译。


我以图像和相似的方式进行操作,得到了一个jar文件,该文件根据命令行参数启动“数据节点”或“客户端节点”。 程序集开始并运行。 零部署失败。


从兆字节的测试数据到数十千兆字节的战斗数据的过渡表明,二进制格式的存在是有充分理由的。 有必要优化节点上的内存消耗,并且BinaryObject非常有用。


4.结论


我们遇到的关于Apache Ignite项目的文档化的第一次谴责是公平的,自2016年以来已经有所改变。 对于初学者来说,基于站点和/或存储库构建功能正常的原型并不容易。


作为完成工作的结果,“零部署”似乎有效,但仅在系统级别有效。 这样的事情:BinaryObject用于教导远程集群节点如何使用自定义类; 零部署-内部机制
Apache Ignite本身并在整个集群中分配系统对象。


我希望我的经验对新的Apache Ignite用户有用。

Source: https://habr.com/ru/post/zh-CN472568/


All Articles