motan yar php,motan学习笔记 四 motan Demo 之yar 分析

发现了yar 这个东西, motan新增了 YarRpcProtocol 这个协议,主要支持php序列化。

来学习下yar协议的具体实现

从代码中看出,支持exporter,不支持refer 因为其走的http协议,所以php直接rest方式调用就行

@SpiMeta(name = "yar")

public class YarRpcProtocol extends AbstractProtocol {

private ConcurrentHashMap ipPort2RequestRouter = new ConcurrentHashMap();

@Override

protected Exporter createExporter(Provider provider, URL url) {

return new YarExporter(url, provider, this);

}

@Override

protected Referer createReferer(Class clz, URL url, URL serviceUrl) {

//TODO

throw new MotanFrameworkException("not yet implemented!");

}

public ProviderMessageRouter initRequestRouter(URL url, Provider> provider) {

String ipPort = url.getServerPortStr();

ProviderMessageRouter requestRouter = ipPort2RequestRouter.get(ipPort);

if (requestRouter == null) {

ipPort2RequestRouter.putIfAbsent(ipPort, new YarMessageRouter());

requestRouter = ipPort2RequestRouter.get(ipPort);

}

requestRouter.addProvider(provider);

return requestRouter;

}

public void unexport(URL url, Provider> provider){

String protocolKey = MotanFrameworkUtil.getProtocolKey(url);

String ipPort = url.getServerPortStr();

Exporter> exporter = (Exporter>) exporterMap.remove(protocolKey);

if (exporter != null) {

exporter.destroy();

}

synchronized (ipPort2RequestRouter) {

ProviderMessageRouter requestRouter = ipPort2RequestRouter.get(ipPort);

if (requestRouter != null) {

requestRouter.removeProvider(provider);

}

}

LoggerUtil.info("yarRpcExporter unexport Success: url={}", url);

}

}

接着看endpointFactory,具体的实现类是netty4yar

@SpiMeta(name = "netty4yar")

public class Netty4YarEndpointFactory extends AbstractEndpointFactory {

@Override

protected Server innerCreateServer(URL url, MessageHandler messageHandler) {

return new Netty4HttpServer(url, new YarMessageHandlerWarpper(messageHandler));

}

@Override

protected Client innerCreateClient(URL url) {

// TODO

throw new MotanFrameworkException("not yet implemented!");

}

}

看netty的server的initchannel

b.group(bossGroup, workerGroup).channel(NioServerSocketChannel.class).childHandler(new ChannelInitializer() {

@Override

public void initChannel(SocketChannel ch) throws Exception {

ch.pipeline().addLast("http-decoder", new HttpRequestDecoder());

ch.pipeline().addLast("http-aggregator", new HttpObjectAggregator(maxContentLength));

ch.pipeline().addLast("http-encoder", new HttpResponseEncoder());

ch.pipeline().addLast("http-chunked", new ChunkedWriteHandler());

ch.pipeline().addLast("serverHandler", handler);

}

}).option(ChannelOption.SO_BACKLOG, 1024).childOption(ChannelOption.SO_KEEPALIVE, false);

接着看看handler

public class YarMessageHandlerWarpper implements MessageHandler {

private YarMessageRouter orgHandler;

public YarMessageHandlerWarpper(MessageHandler orgHandler) {

if (orgHandler == null) {

throw new MotanFrameworkException("messageHandler is null!");

}

if (orgHandler instanceof YarMessageRouter) {

this.orgHandler = (YarMessageRouter) orgHandler;

} else {

throw new MotanFrameworkException("YarMessageHandlerWarper can not wrapper " + orgHandler.getClass().getSimpleName());

}

}

@Override

public Object handle(Channel channel, Object message) {

FullHttpRequest httpRequest = (FullHttpRequest) message;

String uri = httpRequest.getUri();

int index = uri.indexOf("?");// should not be null

String requestPath = uri;

Map attachments = null;

if (index > -1) {

requestPath = uri.substring(0, index);

if (index != uri.length() - 1) {

attachments = getAttachMents(uri.substring(index + 1, uri.length()));

}

}

YarResponse yarResponse = null;

String packagerName = "JSON";

try {

ByteBuf buf = httpRequest.content();

final byte[] contentBytes = new byte[buf.readableBytes()];

buf.getBytes(0, contentBytes);

YarRequest yarRequest = new AttachmentRequest(YarProtocol.buildRequest(contentBytes), attachments);

yarRequest.setRequestPath(requestPath);

yarResponse = (YarResponse) orgHandler.handle(channel, yarRequest);

} catch (Exception e) {

LoggerUtil.error("YarMessageHandlerWarpper handle yar request fail.", e);

yarResponse = YarProtocolUtil.buildDefaultErrorResponse(e.getMessage(), packagerName);

}

byte[] responseBytes;

try {

responseBytes = YarProtocol.toProtocolBytes(yarResponse);

} catch (IOException e) {

throw new MotanFrameworkException("convert yar response to bytes fail.", e);

}

FullHttpResponse httpResponse =

new DefaultFullHttpResponse(HttpVersion.HTTP_1_1, HttpResponseStatus.OK, Unpooled.wrappedBuffer(responseBytes));

httpResponse.headers().set(HttpHeaders.Names.CONTENT_TYPE, "application/x-www-form-urlencoded");

httpResponse.headers().set(HttpHeaders.Names.CONTENT_LENGTH, httpResponse.content().readableBytes());

if (HttpHeaders.isKeepAlive(httpRequest)) {

httpResponse.headers().set(HttpHeaders.Names.CONNECTION, Values.KEEP_ALIVE);

} else {

httpResponse.headers().set(HttpHeaders.Names.CONNECTION, Values.CLOSE);

}

return httpResponse;

}

private Map getAttachMents(String params) {

Map map = new HashMap();

String[] paramArray = params.split("&");

for (String param : paramArray) {

String[] kv = param.split("=");

if (kv.length == 2) {

map.put(kv[0], kv[1]);

} else {

LoggerUtil.warn("yar attachment parse fail. uri param:" + param);

}

}

return map;

}

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值