spider RPC入门指南
请访问https://git.oschina.net/zhjh256/io-spider获取最新更新。
本部分将介绍使用spider RPC开发分布式应用的客户端和服务端。
spider RPC中间件基于J2SE 8开发,因此需要确保服务器上安装了JDK 8及以上版本,不依赖于任何额外需要独立安装和配置的依赖程序。
注:spider RPC 1.0.1版本之前基于JDK 1.7开发,最后改为了使用JDK 1.8主要是出于公司内部系统对接的考虑,使用了1.8新增的Parameter类,因为内部系统需要解析参数名。
spider RPC中间件的核心设计初衷是像调用本地服务一样调用远程服务,能够灵活的在运行时确定目标服务在哪台服务器,且高效的管理上百台的大规模服务器集群。
依赖jar包引入
spider包括下列依赖包:
|
点击下载 |
spider核心包 | <dependency>
<groupId>com.ld.net.spider</groupId> <artifactId>com.ld.net.spider</artifactId> <version>1.0.X-SNAPSHOT</version> </dependency> |
|
点击下载 |
Spider扩展包,比如管理、监控spider运行状态,与服务中心交互等等 | <dependency>
<groupId>com.ld.net.spider</groupId> <artifactId>com.ld.net.spider.ext</artifactId> <version>1.0.X-SNAPSHOT</version> </dependency> |
|
com.ld.net.spider.sc.client.api.jar 点击下载 |
服务中心管理模式下,客户端提供的主要管理功能接口 | <dependency>
<groupId>com.ld.net.spider</groupId> <artifactId>com.ld.net.spider.sc.client.api</artifactId> <version>1.0.X-SNAPSHOT</version> </dependency> |
|
com.ld.net.spider.sc.center.api.jar 点击下载 |
服务中心管理模式下,服务中心端提供的主要功能接口 | <dependency>
<groupId>com.ld.net.spider</groupId> <artifactId>com.ld.net.spider.sc.center.api </artifactId> <version>1.0.X-SNAPSHOT</version> </dependency> |
定义服务接口
开发spider服务的第一步是定义spider服务接口,spider服务以java interface的方式进行定义。本示例涉及POJO定义如下:
package com.medsoft.spider.api;
public class Demo {
private int id;
private String name;
private double bonus;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getBonus() {
return bonus;
}
public void setBonus(double bonus) {
this.bonus = bonus;
}
}
public class DemoReq extends SpiderBizHead {
private int id;
private String name;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
package com.medsoft.spider.api;
import com.ld.net.remoting.LDParam;
public class DemoResp {
private int errorNo;
private String errorInfo;
public int getErrorNo() {
return errorNo;
}
public void setErrorNo(int errorNo) {
this.errorNo = errorNo;
}
public String getErrorInfo() {
return errorInfo;
}
public void setErrorInfo(String errorInfo) {
this.errorInfo = errorInfo;
}
}
package com.medsoft.spider.api;
import java.util.List;
import java.util.Map;
import com.ld.net.spider.meta.SpiderBizHead;
public class DemoQuery extends SpiderBizHead {
private Map<String,String> param;
private List<Demo> result;
public List<Demo> getResult() {
return result;
}
public void setResult(List<Demo> result) {
this.result = result;
}
public Map<String,String> getParam() {
return param;
}
public void setParam(Map<String,String> param) {
this.param = param;
}
public void addParam(String key,String value) {
this.param.put(key, value);
}
}
定义接口:
package com.medsoft.spider.api; import java.util.List; import com.ld.net.spider.annotation.Service;
import com.ld.net.spider.annotation.ServiceModule; @ServiceModule
public interface DemoDrpcpService {
@Service(desc = "Drpcp修改", serviceId = "99000011")
public DemoResp opDrpcpService(DemoReq req); @Service(desc = "Drpcp list查询", serviceId = "99000012")
public List<DemoResp> queryDrpcpService(DemoReq req); @Service(desc = "Drpcp分页查询", serviceId = "99000002")
public DemoQuery queryDrpcpService1(DemoQuery req); @Service(desc = "调用其他MS", serviceId = "99000003")
public String callAS(DemoQuery req);
}
@ ServiceModule标识接口DemoDrpcpService为spider服务模块,@Service定义了具体的服务。
需要注意的是,spider运行时要求所有参数必须通过单个DTO进行传递,否则在启动时会出错而终止,这更多的出于服务管理的需要而非技术的限制或性能的下降。
服务端开发
spider服务的实现和标准的j2ee开发一样,创建一个标准的java web工程,只要定义java类实现服务接口即可,没有任何额外的侵入性。
package com.medsoft.spider.server; import java.util.ArrayList;
import java.util.List; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service; import com.ld.net.base.utils.JsonUtils;
import com.ld.net.spider.exception.SpiderException;
import com.medsoft.spider.api.DemoDrpcpService;
import com.medsoft.spider.api.DemoQuery;
import com.medsoft.spider.api.DemoReq;
import com.medsoft.spider.api.DemoResp;
import com.medsoft.spider.other.api.OtherService; @Service
public class DemoDrpcpServiceImpl implements DemoDrpcpService { @Autowired
private OtherService otherService; @Override
public DemoResp opDrpcpService(DemoReq req) {
System.out.println("接收到spider调用请求: " + JsonUtils.toJson(req));
return new DemoResp();
} @Override
public DemoQuery queryDrpcpService1(DemoQuery req) {
System.out.println("接收到spider调用请求: " + JsonUtils.toJson(req));
return new DemoQuery();
} @Override
public String callAS(DemoQuery req) {
System.out.println("调用其他系统的AS");
try {
return otherService.doAs(req);
} catch (SpiderException e) {
throw e;
}
} @Override
public List<DemoResp> queryDrpcpService(DemoReq req) {
List<DemoResp> list = new ArrayList<DemoResp>();
DemoResp e1 = new DemoResp();
DemoResp e2 = new DemoResp();
list.add(e1);
list.add(e2);
return list;
}
}
如上所示,实现非常简单,没有任何spider侵入性,故不再重复讲解。
需要注意的是,上述红色字体的OtherService,该服务为标准Spring Bean服务或者微服务MS或其它子系统提供的公用业务服务,比如查询账户信息,视具体而定。
客户端开发
客户端调用spider服务在开发上和调用标准的本地spring bean服务完全相同,创建一个标准的java web工程,只要设置目标服务自动注入就可以直接使用了,如下所示:
@Controller
public class IndexAction {
@Autowired
private DemoDrpcpService demoDrpcpService; @RequestMapping(value="/to_pnp2_cnp1.html",method=RequestMethod.GET)
public @ResponseBody String indexV(Model model,HttpServletRequest request){
DemoQuery req = new DemoQuery();
DemoReq param = new DemoReq();
req.setAppVersion("v1.1");
req.setSystemId("02");
req.setCompanyId("100001");
param.setId(8888);
param.setName("zhangsan");
return JsonUtils.toJson(demoDrpcpService.queryDrpcpService1(req));
}
}
直接通过功能号调用spider服务
除了上述通过注入接口方式调用spider服务外,spider运行时还支持直接通过功能号的方式调用,如下所示:
DemoReq param = new DemoReq();
param.setId(8888);
param.setName("zhangsan");
param.setCompanyId(companyId);
param.setSystemId(systemId);
ServiceDefinition service = ServiceDefinitionContainer.getService("99000011");
try {
return (DemoResp) service.getMethod().invoke(BeanManagerHelper.getBean(service.getClz()), param);
} catch (IllegalAccessException | IllegalArgumentException
| InvocationTargetException e) {
e.printStackTrace();
}
两种方式的调用效果相同。
接口包与实现包的部署
使用Spider开发的分布式系统最简单的情况下通常具有如下的部署结构:

在复杂的生产部署中,其部署结构可能会异常复杂,如下所示:

本示例中,我们以简单的客户端/服务端为例介绍包的部署与配置文件的设置。
spider客户端只需要放置定义服务接口的jar或class即可。
spider服务端需要同时放置定义服务接口的jar或class,和服务实现。一般来说,这两者都打包在jar中而非分散的class会比较合理。
Spider配置
Spider包含一个配置文件,名称为spider.xml,可以修改,具体位置可参见《spider概要设计-配置文件一节》,目前支持三种配置文件指定方式,在标准的maven工程下,建议将其放在src/main/resources下,作为标准配置文件的一部分。
客户端spider.xml示例
<?xml version="1.0" encoding="UTF-8"?>
<spider>
<nodeName value="ANB" cloud="false" role="production"
serviceCenter="0.0.0.0" appVersion="" charset="GBK" />
<plugins>
<plugin pluginId="spider.localService" serviceTimeout="10000"
zlibCompress="false" encrypt="false" anonymous="true"
serviceProxyPackage="com.medsoft.spider.api">
<server enable="false" port="7070" reliable="false"
threadCount="200" serviceExportPackage="" />
</plugin>
<plugin pluginId="spider.channel">
<cluster clusterName="CNB-1" connectionSize="1">
<workNode address="127.0.0.1" port="18021" />
</cluster>
</plugin>
<plugin pluginId="spider.filter">
</plugin>
</plugins>
<routeItems>
<routeItem serviceId="99*" clusterName="CNB-1" />
<!-- <routeItem serviceId="*" appVersion="" subSystemId=""
systemId="" companyId="" clusterName="spider-server" /> -->
</routeItems>
</spider>
上述配置中,红色部分是与客户端直接相关的配置。
服务端spider.xml示例
<?xml version="1.0" encoding="UTF-8"?>
<spider>
<nodeName value="MSNP-1" cloud="false" role="production"
serviceCenter="0.0.0.0" appVersion="" serviceDefineType="spider" needLdPackAdapter="false" charset="GBK"/>
<plugins>
<plugin pluginId="spider.localService" serviceTimeout="10000"
zlibCompress="false" encrypt="false" anonymous="true"
serviceProxyPackage="">
<server enable="true" port="18051" reliable="false"
threadCount="200" serviceExportPackage="com.medsoft.spider.api" />
</plugin>
<plugin pluginId="spider.channel">
</plugin>
<plugin pluginId="spider.filter">
</plugin>
</plugins>
<routeItems>
<routeItem serviceId="*" clusterName="spider.localService" />
<!-- <routeItem serviceId="*" appVersion="" subSystemId=""
systemId="" companyId="" clusterName="spider-server" /> -->
</routeItems>
</spider>
上述配置中,红色部分是与客户端直接相关的配置。
服务端配置注意事项
spider启动时会进行下列自检操作:
1、在/tmp/spider/下检查是否存在${nodeName}.pid文件,如果存在,则说明本服务器上存在同名已启动spider实例,不允许启动;
2、运行服务器模式时,检查本节点spider.xml中定义的服务器端口号是否已经被占用,如果已经被占用,则提示端口号已经被占用,不允许启动;
运行方式
当前版本spider支持运行于标准java应用程序和web容器下两种模式,他们提供完全相同的核心服务。在运行于标准java程序模式下时,spider提供的RESTFUL管理控制台和API将不可用。
web.xml配置
客户端和服务端的web.xml配置要求相同,如不需要启用web监控,只需要包含如下即可:
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath*:spider-base-service.xml</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
如需启用web监控,则还需要包含如下:
<servlet>
<servlet-name>springMVC</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath*:spider-base-web.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
启动运行
上述步骤均完成后,就可以启动spider服务端和客户端进行验证了。Spider服务端和客户端的启动顺序无关紧要,spider运行时会每隔指定间隔自动进行检测并尝试建立断开和尚未建立的连接。
spider RPC入门指南的更多相关文章
- spider RPC开发指南
协议与兼容性 spider使用java语言开发,使用Spring作为IoC容器,采用TCP/IP协议,在此基础上,结合SaaS系统模式的特性进行针对性和重点设计,以更加灵活和高效的满足多租户系统.高可 ...
- spider RPC框架的需求来源与特性介绍(一)
spider RPC 特性介绍 spider RPC 性能测试 spider RPC 入门指南 spider RPC 配置文件参考 spider RPC 开发指南 spider RPC 安全性 spi ...
- Flume NG Getting Started(Flume NG 新手入门指南)
Flume NG Getting Started(Flume NG 新手入门指南)翻译 新手入门 Flume NG是什么? 有什么改变? 获得Flume NG 从源码构建 配置 flume-ng全局选 ...
- Web API 入门指南 - 闲话安全
Web API入门指南有些朋友回复问了些安全方面的问题,安全方面可以写的东西实在太多了,这里尽量围绕着Web API的安全性来展开,介绍一些安全的基本概念,常见安全隐患.相关的防御技巧以及Web AP ...
- Vue.js 入门指南之“前传”(含sublime text 3 配置)
题记:关注Vue.js 很久了,但就是没有动手写过一行代码,今天准备入手,却发现自己比菜鸟还菜,于是四方寻找大牛指点,才终于找到了入门的“入门”,就算是“入门指南”的“前传”吧.此文献给跟我一样“白痴 ...
- yii2实战教程之新手入门指南-简单博客管理系统
作者:白狼 出处:http://www.manks.top/document/easy_blog_manage_system.html 本文版权归作者,欢迎转载,但未经作者同意必须保留此段声明,且在文 ...
- 【翻译】Fluent NHibernate介绍和入门指南
英文原文地址:https://github.com/jagregory/fluent-nhibernate/wiki/Getting-started 翻译原文地址:http://www.cnblogs ...
- ASP.NET MVC 5 入门指南汇总
经过前一段时间的翻译和编辑,我们陆续发出12篇ASP.NET MVC 5的入门文章.其中大部分翻译自ASP.NET MVC 5 官方教程,由于本系列文章言简意赅,篇幅适中,从一个web网站示例开始讲解 ...
- 一起学微软Power BI系列-官方文档-入门指南(1)Power BI初步介绍
我们在前一篇文章微软新神器-Power BI,一个简单易用,还用得起的BI产品中,我们初步介绍了Power BI的基本知识.由于Power BI是去年开始微软新发布的一个产品,虽然已经可以企业级应用, ...
随机推荐
- 关于.NET异常处理的思考
年关将至,对于大部分程序员来说,马上就可以闲下来一段时间了,然而在这个闲暇的时间里,唯有争论哪门语言更好可以消磨时光,估计最近会有很多关于java与.net的博文出现,我表示要作为一个吃瓜群众,静静的 ...
- 闲来无聊,研究一下Web服务器 的源程序
web服务器是如何工作的 1989年的夏天,蒂姆.博纳斯-李开发了世界上第一个web服务器和web客户机.这个浏览器程序是一个简单的电话号码查询软件.最初的web服务器程序就是一个利用浏览器和web服 ...
- python笔记(持续更新)
1.编译python遇到下面的编码问题: SyntaxError: Non-ASCII character '\xe9' in file E:\projects\learn.py on lin ...
- 掌握javascript中的最基础数据结构-----数组
这是一篇<数据结构与算法javascript描述>的读书笔记.主要梳理了关于数组的知识.部分内容及源码来自原作. 书中第一章介绍了如何配置javascript运行环境:javascript ...
- [转]Patch文件结构详解
N久不来 于是不知道扔在哪儿于是放这里先 如果你觉得碍事的话 帮我扔到合适的版块去.. 导读这是一篇说明文 它介绍了标准冒险岛更新文件(*.patch;*.exe)的格式文章的最后附了一段C#的参考代 ...
- 【知识必备】RxJava+Retrofit二次封装最佳结合体验,打造懒人封装框架~
一.写在前面 相信各位看官对retrofit和rxjava已经耳熟能详了,最近一直在学习retrofit+rxjava的各种封装姿势,也结合自己的理解,一步一步的做起来. 骚年,如果你还没有掌握ret ...
- 深入.NET平台和C#编程总结大全
对于初学者的你,等到你把这个看完之后就更清楚地认知.NET和C#编程了,好了废话不多说,开始吧! ...
- php 基础代码大全(不断完善中)
下面是基础的PHP的代码,不断完善中~ //语法错误(syntax error)在语法分析阶段,源代码并未被执行,故不会有任何输出. /* [命名规则] */ 常量名 类常量建议全大写,单词间用下划线 ...
- MVC还是MVVM?或许VMVC更适合WinForm客户端
最近开始重构一个稍嫌古老的C/S项目,原先采用的技术栈是『WinForm』+『WCF』+『EF』.相对于现在铺天盖地的B/S架构来说,看上去似乎和Win95一样古老,很多新入行的,可能就没有见过经典的 ...
- Android之Pull解析XML
一.Pull解析方法介绍 除了可以使用SAX和DOM解析XML文件,也可以使用Android内置的Pull解析器解析XML文件.Pull解析器的运行方式与SAX解析器相似.它也是事件触发的.Pull解 ...