百度360必应搜狗淘宝本站头条
当前位置:网站首页 > 技术文章 > 正文

基于Thrift搭建跨语言RPC服务(rpc可以跨语言调用吗)

ccwgpt 2024-10-15 08:59 59 浏览 0 评论

今天我们要分享的是Thrift这个框架,本来文章的题目叫《基于Thrift搭建微服务》,不过标题有点太大了,今天也没有太多时间讲解什么是微服务,什么是SOA架构以及他们的区别,所以今天我们不扯的这么大,就讲点实际的,如何使用Thrift实现跨语言服务呢?

我们公司之前前端是net,很多前端工程都是使用c#相关语言开发的,后来公司逐渐转向Java平台,但前端的net的项目都不能全部抛弃,该使用的还是要使用,这样就需要考虑对接的开发成本,后台是Java写的,而前端是php或者net的时候如何快速完成对接呢?我们可以使用基于 SOAP 消息格式的 Web Service,基于 JSON 消息格式的 RESTful 服务等。其中所用到的数据传输方式包括 XML,JSON 等,然而 XML 相对体积太大,传输效率低,JSON 体积较小,新颖,但还不够完善。我们选择的是由 Facebook 开发的远程服务调用框架 Apache Thrift,它采用接口描述语言定义并创建服务,支持可扩展的跨语言服务开发,所包含的代码生成引擎可以在多种语言中,如 C++, Java, Python, PHP, Ruby, Erlang, Perl, Haskell, C#, Cocoa, Smalltalk 等创建高效的、无缝的服务,其传输数据采用二进制格式,相对 XML 和 JSON 体积更小,对于高并发、大数据量和多语言的环境更有优势。废话不多说,我们从Helloworld讲起,使用thrift集成spring完成一个rpc的服务,跟着我的节奏一步步来。

1、搭建一个maven环境,引入相关jar包

各个包结构解释:

(1)app:服务的启动程序,我们使用main函数启动。

(2)client:客户端测试程序,我们再次连接thrift服务。

(3)common.param:调用服务接口需要的参数放置位置。

(4)common.result:调用服务接口返回的数据放置位置。

(5)registe:服务启动后需要向服务中心注册接口,这样客户端才能发现接口。

(6)service:服务接口定义。

(7)service.impl:服务接口的实现类。

pom中需要依赖的jar比较多,这里不一一截图了,主要是包括spring相关的jar和thrift的jar,以及相关依赖的jar包:

2、服务接口与实体定义

thrift为什么可以和其他语言无缝结合的原因,在于它定义了一套自己的 IDL,即语法规范,我们使用Thrift 的语法规范编写脚本文件,然后通过它提供的编译工具就可以生成多种语言对应的实现。现在我们首先定义我们的接口以及接口的参数和返回值的内容:

三个thrift文件,分别代表参数,结果,和接口。我们分别来看。首先是TestParam.thrift:

namespace为命名空间,文件编译完成后会将类文件放入对应的目录。struct是结构体的意思,UserParam为类名,其下有一个telphone的字符串属性字段。除此之外,thrift还支持多种数据结构,例如:短整型i16,整型i32,长整型i64 ,集合相关的list,map,set等。下面我们看TestResult.thrift

返回对象我们定义了一个UserResultMsg对象,存在code和msg属性,以及具体的返回内容data,它是一个list,而具体的内容是UserResult这个类,包括long型的id,整数的年龄,字符串的姓名和电话等。最后我们看一下TestService.thrift如何定义:

我们首先将参数文件,结果文件include(引入)到接口文件中,因为他们存在依赖关系,然后定义我们的service接口,包含一个方法:findUserList,意思是查询用户列表,参数包括字符串token,和UserParam。

3、编译脚本文件

我们通过thrift.exe这个工具帮助我们编译脚本文件,具体脚本内容如下:

最后它将生成Java语言对应的接口以及实体类,我们看一下生成的相关类:

由thrift编译生成类比较复杂,我们这里不做解释,我们就可以认为它是一个普通的java类即可。不过这里我们需要注意是,我们使用thrift就是使用它的这种RPC的功能,我们将生成的接口与相关类单独部署和启动,与客户端完全解耦,客户端需要通过rpc连接调用thrift服务,而不是通过依赖jar的方式调用。而创建RPC链接,需要依赖TestService.java中的相关类,例如:Client,通过构造Client对象,我们可以调用其定义的方法,Client是一个静态的内部类,具体的代码如下:

在截图中我们可以看到类的构造方式,TestService中有Iface和AsyncIface,分别代表同步和异步。我们这里使用的是同步接口,而Client类是我们要想办法构造的类,通过client实例我们可以调用findUserList方法。这里我们先不说,之后再说。

4、注册thrift接口

当前,thrift已经帮助我们生成了我们的TestService服务接口,但我们需要将这些服务注册到服务中心,即我们需要将其加载中实例当中,我们看一下注册服务的核心代码是:

代码中,我们需要先后获得TProcessor实例和TMultiplexedProcessor实例。不同的实现可以解决不同的问题,我们这里使用的是TProcessor是TMultiplexedProcessor,支持一个Server支持部署多个Service的情况,在Processor外面再加一层Map,消息名从“add”会变为“Caculator:add”,当然,这需要需要客户端发送时使用 TMultiplexedProtocol修饰原来的Protocol来实现。也就是说使用它我们可以在一个端口下部署多个服务接口(在thrift之前的版本里是不可以的)。

再接下来我们还需要创建TServer的实例,我们使用的是TThreadedSelectorServer实现类。它是最成熟,也是被业界所推崇的RPC服务模型。TThreadedSelectorServer是对以上NonblockingServer的扩充, 其分离了Accept和Read/Write的Selector线程, 同时引入Worker工作线程池. 它也是种Half-sync/Half-async的服务模型。

其实说实话,我也不太懂上述的概念,暂时先放在这,以后我们再来研究。创建TProcessor的代码如下:

这里要强调的是,serviceImplClass这个map的参数都是我们配置在配置文件中,在构造Tprocessor的时候我们需要用到TestService这个类的TProcessor。创建完成后,调用server方法完成服务启动。服务启动时绑定8110端口,服务器地址为本机ip。

5、客户端调用

客户端调用TestService的接口,首先要创建TestService.Iface的实现类:

然后创建与服务器的链接,其实就是创建TestService类中的Client对象,因为创建client对象的同时,我们就已经开启了对服务器的连接,代码如下:

在此之前,我们需要构造TrramedTransport实例,并开启:

如此就完成了服务接口的注册和客户端调用。

其实,我们发现我们要做的工作很简单,就是去构造TestService中的TProcessor对象,以及对应的Client对象就可以完成。因为Thrift已经帮助我们将所有的实现封装在了此类中,因正因为如此,所以它帮助我们实现了和其他语言的无缝结合,快速对接。

6、启动服务

使用ClassPathXmlApplicationContext构建spring容器,它会读取thrift-service帮助我们创建维护各种实例,以及执行ResigteServer类的start方法,在start方法中就帮助我们完成服务接口的注册。

6、测试

执行测试类中findUserList方法

得到查询结果。

总结:就实际开发的经验而言,thrift作为跨语言的rpc框架,我觉得还是不错的,整合zookeeper可以做一个分布式的rpc集群服务,只不过在生成相应语言的类时有些繁琐和麻烦,开发前统一定义好规范后,在开发时可以提高很多效率。

相关推荐

RACI矩阵:项目管理中的角色与责任分配利器

作者:赵小燕RACI矩阵RACI矩阵是项目管理中的一种重要工具,旨在明确团队在各个任务中的角色和职责。通过将每个角色划分为负责人、最终责任人、咨询人和知情人四种类型,RACI矩阵确保每个人都清楚自己...

在弱矩阵组织中,如何做好项目管理工作?「慕哲制图」

慕哲出品必属精品系列在弱矩阵组织中,如何做好项目管理工作?【慕哲制图】-------------------------------慕哲制图系列0:一图掌握项目、项目集、项目组合、P2、商业分析和NP...

Scrum模式:每日站会(Daily Scrum)

定义每日站会(DailyScrum)是一个Scrum团队在进行Sprint期间的日常会议。这个会议的主要目的是为了应对Sprint计划中的不断变化,确保团队能够有效应对挑战并达成Sprint目标。为...

大家都在谈论的敏捷开发&Scrum,到底是什么?

敏捷开发作为一种开发模式,近年来深受研发团队欢迎,与瀑布式开发相比,敏捷开发更轻量,灵活性更高,在当下多变环境下,越来越多团队选择敏捷开发。什么是敏捷?敏捷是一种在不确定和变化的环境中,通过创造和响应...

敏捷与Scrum是什么?(scrum敏捷开发是什么)

敏捷是一种思维模式和哲学,它描述了敏捷宣言中的一系列原则。另一方面,Scrum是一个框架,规定了实现这种思维方式的角色,事件,工件和规则/指南。换句话说,敏捷是思维方式,Scrum是规定实施敏捷哲学的...

敏捷项目管理与敏捷:Scrum流程图一览

敏捷开发中的Scrum流程通常可以用一个简单的流程图来表示,以便更清晰地展示Scrum框架的各个阶段和活动。以下是一个常见的Scrum流程图示例:这个流程图涵盖了Scrum框架的主要阶段和活动,其中包...

一张图掌握项目生命周期模型及Scrum框架

Mockito 的最佳实践(mock方法)

记得以前面试的时候,面试官问我,平常开发过程中自己会不会测试?我回答当然会呀,自己写的代码怎么不测呢。现在想想我好像误会他的意思了,他应该是想问我关于单元测试,集成测试以及背后相关的知识,然而当时说到...

EffectiveJava-5-枚举和注解(java枚举的作用与好处)

用enum代替int常量1.int枚举:引入枚举前,一般是声明一组具名的int常量,每个常量代表一个类型成员,这种方法叫做int枚举模式。int枚举模式是类型不安全的,例如下面两组常量:性别和动物种...

Maven 干货 全篇共:28232 字。预计阅读时间:110 分钟。建议收藏!

Maven简介Maven这个词可以翻译为“知识的积累”,也可以翻译为“专家”或“内行”。Maven是一个跨平台的项目管理工具。主要服务于基于Java平台的项目构建、依赖管理和项目信息管理。仔...

Java单元测试框架PowerMock学习(java单元测试是什么意思)

前言高德的技术大佬在谈论方法论时说到:“复杂的问题要简单化,简单的问题要深入化。”这句话让我感触颇深,这何尝不是一套编写代码的方法——把一个复杂逻辑拆分为许多简单逻辑,然后把每一个简单逻辑进行深入实现...

Spring框架基础知识-第六节内容(Spring高级话题)

Spring高级话题SpringAware基本概念Spring的依赖注入的最大亮点是你所有的Bean对Spring容器的存在是没有意识的。但是在实际的项目中,你的Bean必须要意识到Spring容器...

Java单元测试浅析(JUnit+Mockito)

作者:京东物流秦彪1.什么是单元测试(1)单元测试环节:测试过程按照阶段划分分为:单元测试、集成测试、系统测试、验收测试等。相关含义如下:1)单元测试:针对计算机程序模块进行输出正确性检验工作...

揭秘Java代码背后的质检双侠:JUnit与Mockito!

你有没有发现,现在我们用的手机App、逛的网站,甚至各种智能设备,功能越来越复杂,但用起来却越来越顺畅,很少遇到那种崩溃、卡顿的闹心事儿?这背后可不是程序员一拍脑袋写完代码就完事儿了!他们需要一套严谨...

单元测试框架哪家强?Junit来帮忙!

大家好,在前面的文章中,给大家介绍了以注解和XML的方式分别实现IOC和依赖注入。并且我们定义了一个测试类,通过测试类来获取到了容器中的Bean,具体的测试类定义如下:@Testpublicvoid...

取消回复欢迎 发表评论: