You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@dubbo.apache.org by li...@apache.org on 2018/06/01 07:02:56 UTC
[incubator-dubbo] branch master updated: Merge pull request #1827,
support generic invoke and attachment for http/hessian protocol.
This is an automated email from the ASF dual-hosted git repository.
liujun pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/incubator-dubbo.git
The following commit(s) were added to refs/heads/master by this push:
new 286fb12 Merge pull request #1827, support generic invoke and attachment for http/hessian protocol.
286fb12 is described below
commit 286fb12b011fd878b3d44ff6985e082e2141a164
Author: Jerrick Zhu <di...@gmail.com>
AuthorDate: Fri Jun 1 15:02:53 2018 +0800
Merge pull request #1827, support generic invoke and attachment for http/hessian protocol.
fixes #1768, #19
---
.../dubbo/config/mock/MockProxyFactory.java | 5 +
.../java/com/alibaba/dubbo/rpc/ProxyFactory.java | 9 +
.../alibaba/dubbo/rpc/filter/GenericFilter.java | 9 +-
.../dubbo/rpc/filter/GenericImplFilter.java | 8 +-
.../dubbo/rpc/protocol/AbstractProxyProtocol.java | 6 +-
.../dubbo/rpc/proxy/AbstractProxyFactory.java | 15 ++
.../rpc/proxy/wrapper/StubProxyFactoryWrapper.java | 5 +
dubbo-rpc/dubbo-rpc-hessian/pom.xml | 6 +
....java => DubboHessianURLConnectionFactory.java} | 87 +++++----
.../rpc/protocol/hessian/HessianProtocol.java | 32 +++-
.../hessian/HttpClientConnectionFactory.java | 9 +-
.../rpc/protocol/hessian/HessianProtocolTest.java | 93 ++++++++++
.../dubbo/rpc/protocol/hessian/HessianService.java | 2 +
.../rpc/protocol/hessian/HessianServiceImpl.java | 6 +
dubbo-rpc/dubbo-rpc-http/pom.xml | 6 +
.../dubbo/rpc/protocol/http/HttpProtocol.java | 55 ++++--
.../rpc/protocol/http/HttpRemoteInvocation.java | 57 ++++++
.../dubbo/rpc/protocol/http/HttpProtocolTest.java | 198 +++++++++++++++++++++
.../dubbo/rpc/protocol/http/HttpService.java} | 8 +-
.../dubbo/rpc/protocol/http/HttpServiceImpl.java} | 8 +-
dubbo-rpc/dubbo-rpc-rest/pom.xml | 6 +
.../dubbo/rpc/protol/rest/RestProtocolTest.java | 48 +++++
.../dubbo/rpc/protol/rest/RestService.java} | 21 ++-
.../dubbo/rpc/protol/rest/RestServiceImpl.java} | 19 +-
24 files changed, 625 insertions(+), 93 deletions(-)
diff --git a/dubbo-config/dubbo-config-api/src/test/java/com/alibaba/dubbo/config/mock/MockProxyFactory.java b/dubbo-config/dubbo-config-api/src/test/java/com/alibaba/dubbo/config/mock/MockProxyFactory.java
index 3de2e3a..cd78366 100644
--- a/dubbo-config/dubbo-config-api/src/test/java/com/alibaba/dubbo/config/mock/MockProxyFactory.java
+++ b/dubbo-config/dubbo-config-api/src/test/java/com/alibaba/dubbo/config/mock/MockProxyFactory.java
@@ -28,6 +28,11 @@ public class MockProxyFactory implements ProxyFactory {
}
@Override
+ public <T> T getProxy(Invoker<T> invoker, boolean generic) throws RpcException {
+ return null;
+ }
+
+ @Override
public <T> Invoker<T> getInvoker(T proxy, Class<T> type, URL url) throws RpcException {
return null;
}
diff --git a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/ProxyFactory.java b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/ProxyFactory.java
index 6ba7057..fb03d6b 100644
--- a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/ProxyFactory.java
+++ b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/ProxyFactory.java
@@ -37,6 +37,15 @@ public interface ProxyFactory {
<T> T getProxy(Invoker<T> invoker) throws RpcException;
/**
+ * create proxy.
+ *
+ * @param invoker
+ * @return proxy
+ */
+ @Adaptive({Constants.PROXY_KEY})
+ <T> T getProxy(Invoker<T> invoker, boolean generic) throws RpcException;
+
+ /**
* create invoker.
*
* @param <T>
diff --git a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericFilter.java b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericFilter.java
index d393822..8404a99 100644
--- a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericFilter.java
+++ b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericFilter.java
@@ -32,10 +32,12 @@ import com.alibaba.dubbo.rpc.Filter;
import com.alibaba.dubbo.rpc.Invocation;
import com.alibaba.dubbo.rpc.Invoker;
import com.alibaba.dubbo.rpc.Result;
+import com.alibaba.dubbo.rpc.RpcContext;
import com.alibaba.dubbo.rpc.RpcException;
import com.alibaba.dubbo.rpc.RpcInvocation;
import com.alibaba.dubbo.rpc.RpcResult;
import com.alibaba.dubbo.rpc.service.GenericException;
+import com.alibaba.dubbo.rpc.service.GenericService;
import com.alibaba.dubbo.rpc.support.ProtocolUtils;
import java.io.IOException;
@@ -52,7 +54,7 @@ public class GenericFilter implements Filter {
if (inv.getMethodName().equals(Constants.$INVOKE)
&& inv.getArguments() != null
&& inv.getArguments().length == 3
- && !ProtocolUtils.isGeneric(invoker.getUrl().getParameter(Constants.GENERIC_KEY))) {
+ && !invoker.getInterface().equals(GenericService.class)) {
String name = ((String) inv.getArguments()[0]).trim();
String[] types = (String[]) inv.getArguments()[1];
Object[] args = (Object[]) inv.getArguments()[2];
@@ -63,6 +65,11 @@ public class GenericFilter implements Filter {
args = new Object[params.length];
}
String generic = inv.getAttachment(Constants.GENERIC_KEY);
+
+ if (StringUtils.isBlank(generic)) {
+ generic = RpcContext.getContext().getAttachment(Constants.GENERIC_KEY);
+ }
+
if (StringUtils.isEmpty(generic)
|| ProtocolUtils.isDefaultGenericSerialization(generic)) {
args = PojoUtils.realize(args, params, method.getGenericParameterTypes());
diff --git a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericImplFilter.java b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericImplFilter.java
index 99bced5..6be08fe 100644
--- a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericImplFilter.java
+++ b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/filter/GenericImplFilter.java
@@ -155,13 +155,13 @@ public class GenericImplFilter implements Filter {
for (Object arg : args) {
if (!(byte[].class == arg.getClass())) {
- error(byte[].class.getName(), arg.getClass().getName());
+ error(generic, byte[].class.getName(), arg.getClass().getName());
}
}
} else if (ProtocolUtils.isBeanGenericSerialization(generic)) {
for (Object arg : args) {
if (!(arg instanceof JavaBeanDescriptor)) {
- error(JavaBeanDescriptor.class.getName(), arg.getClass().getName());
+ error(generic, JavaBeanDescriptor.class.getName(), arg.getClass().getName());
}
}
}
@@ -172,10 +172,10 @@ public class GenericImplFilter implements Filter {
return invoker.invoke(invocation);
}
- private void error(String expected, String actual) throws RpcException {
+ private void error(String generic, String expected, String actual) throws RpcException {
throw new RpcException(
"Generic serialization [" +
- Constants.GENERIC_SERIALIZATION_NATIVE_JAVA +
+ generic +
"] only support message type " +
expected +
" and your message type is " +
diff --git a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/protocol/AbstractProxyProtocol.java b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/protocol/AbstractProxyProtocol.java
index 8136cc0..561520c 100644
--- a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/protocol/AbstractProxyProtocol.java
+++ b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/protocol/AbstractProxyProtocol.java
@@ -68,7 +68,7 @@ public abstract class AbstractProxyProtocol extends AbstractProtocol {
if (exporter != null) {
return exporter;
}
- final Runnable runnable = doExport(proxyFactory.getProxy(invoker), invoker.getInterface(), invoker.getUrl());
+ final Runnable runnable = doExport(proxyFactory.getProxy(invoker, true), invoker.getInterface(), invoker.getUrl());
exporter = new AbstractExporter<T>(invoker) {
@Override
public void unexport() {
@@ -89,12 +89,12 @@ public abstract class AbstractProxyProtocol extends AbstractProtocol {
@Override
public <T> Invoker<T> refer(final Class<T> type, final URL url) throws RpcException {
- final Invoker<T> tagert = proxyFactory.getInvoker(doRefer(type, url), type, url);
+ final Invoker<T> target = proxyFactory.getInvoker(doRefer(type, url), type, url);
Invoker<T> invoker = new AbstractInvoker<T>(type, url) {
@Override
protected Result doInvoke(Invocation invocation) throws Throwable {
try {
- Result result = tagert.invoke(invocation);
+ Result result = target.invoke(invocation);
Throwable e = result.getException();
if (e != null) {
for (Class<?> rpcException : rpcExceptions) {
diff --git a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/AbstractProxyFactory.java b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/AbstractProxyFactory.java
index 21c350d..d27f608 100644
--- a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/AbstractProxyFactory.java
+++ b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/AbstractProxyFactory.java
@@ -22,6 +22,7 @@ import com.alibaba.dubbo.rpc.Invoker;
import com.alibaba.dubbo.rpc.ProxyFactory;
import com.alibaba.dubbo.rpc.RpcException;
import com.alibaba.dubbo.rpc.service.EchoService;
+import com.alibaba.dubbo.rpc.service.GenericService;
/**
* AbstractProxyFactory
@@ -30,6 +31,11 @@ public abstract class AbstractProxyFactory implements ProxyFactory {
@Override
public <T> T getProxy(Invoker<T> invoker) throws RpcException {
+ return getProxy(invoker, false);
+ }
+
+ @Override
+ public <T> T getProxy(Invoker<T> invoker, boolean generic) throws RpcException {
Class<?>[] interfaces = null;
String config = invoker.getUrl().getParameter("interfaces");
if (config != null && config.length() > 0) {
@@ -46,6 +52,15 @@ public abstract class AbstractProxyFactory implements ProxyFactory {
if (interfaces == null) {
interfaces = new Class<?>[]{invoker.getInterface(), EchoService.class};
}
+
+ if (!invoker.getInterface().equals(GenericService.class) && generic) {
+ int len = interfaces.length;
+ Class<?>[] temp = interfaces;
+ interfaces = new Class<?>[len + 1];
+ System.arraycopy(temp, 0, interfaces, 0, len);
+ interfaces[len] = GenericService.class;
+ }
+
return getProxy(invoker, interfaces);
}
diff --git a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/wrapper/StubProxyFactoryWrapper.java b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/wrapper/StubProxyFactoryWrapper.java
index ec3db16..3f3ed3f 100644
--- a/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/wrapper/StubProxyFactoryWrapper.java
+++ b/dubbo-rpc/dubbo-rpc-api/src/main/java/com/alibaba/dubbo/rpc/proxy/wrapper/StubProxyFactoryWrapper.java
@@ -55,6 +55,11 @@ public class StubProxyFactoryWrapper implements ProxyFactory {
}
@Override
+ public <T> T getProxy(Invoker<T> invoker, boolean generic) throws RpcException {
+ return proxyFactory.getProxy(invoker, generic);
+ }
+
+ @Override
@SuppressWarnings({"unchecked", "rawtypes"})
public <T> T getProxy(Invoker<T> invoker) throws RpcException {
T proxy = proxyFactory.getProxy(invoker);
diff --git a/dubbo-rpc/dubbo-rpc-hessian/pom.xml b/dubbo-rpc/dubbo-rpc-hessian/pom.xml
index 00ca28c..98ad82d 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/pom.xml
+++ b/dubbo-rpc/dubbo-rpc-hessian/pom.xml
@@ -48,5 +48,11 @@
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
</dependency>
+ <dependency>
+ <groupId>com.alibaba</groupId>
+ <artifactId>dubbo-serialization-jdk</artifactId>
+ <version>${project.parent.version}</version>
+ <scope>test</scope>
+ </dependency>
</dependencies>
</project>
\ No newline at end of file
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HttpClientConnectionFactory.java b/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/DubboHessianURLConnectionFactory.java
similarity index 55%
copy from dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HttpClientConnectionFactory.java
copy to dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/DubboHessianURLConnectionFactory.java
index 033277d..8fe2f14 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HttpClientConnectionFactory.java
+++ b/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/DubboHessianURLConnectionFactory.java
@@ -1,47 +1,40 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.alibaba.dubbo.rpc.protocol.hessian;
-
-import com.caucho.hessian.client.HessianConnection;
-import com.caucho.hessian.client.HessianConnectionFactory;
-import com.caucho.hessian.client.HessianProxyFactory;
-import org.apache.http.client.HttpClient;
-import org.apache.http.impl.client.DefaultHttpClient;
-import org.apache.http.params.HttpConnectionParams;
-
-import java.io.IOException;
-import java.net.URL;
-
-/**
- * HttpClientConnectionFactory
- */
-public class HttpClientConnectionFactory implements HessianConnectionFactory {
-
- private final HttpClient httpClient = new DefaultHttpClient();
-
- @Override
- public void setHessianProxyFactory(HessianProxyFactory factory) {
- HttpConnectionParams.setConnectionTimeout(httpClient.getParams(), (int) factory.getConnectTimeout());
- HttpConnectionParams.setSoTimeout(httpClient.getParams(), (int) factory.getReadTimeout());
- }
-
- @Override
- public HessianConnection open(URL url) throws IOException {
- return new HttpClientConnection(httpClient, url);
- }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.alibaba.dubbo.rpc.protocol.hessian;
+
+import com.alibaba.dubbo.common.Constants;
+import com.alibaba.dubbo.rpc.RpcContext;
+import com.caucho.hessian.client.HessianConnection;
+import com.caucho.hessian.client.HessianURLConnectionFactory;
+
+import java.io.IOException;
+import java.net.URL;
+
+public class DubboHessianURLConnectionFactory extends HessianURLConnectionFactory {
+
+ @Override
+ public HessianConnection open(URL url) throws IOException {
+ HessianConnection connection = super.open(url);
+ RpcContext context = RpcContext.getContext();
+ for (String key : context.getAttachments().keySet()) {
+ connection.addHeader(Constants.DEFAULT_EXCHANGER + key, context.getAttachment(key));
+ }
+
+ return connection;
+ }
+}
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocol.java b/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocol.java
index f1eae5c..9733307 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocol.java
+++ b/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocol.java
@@ -25,8 +25,11 @@ import com.alibaba.dubbo.rpc.RpcContext;
import com.alibaba.dubbo.rpc.RpcException;
import com.alibaba.dubbo.rpc.protocol.AbstractProxyProtocol;
+import com.alibaba.dubbo.rpc.service.GenericService;
+import com.alibaba.dubbo.rpc.support.ProtocolUtils;
import com.caucho.hessian.HessianException;
import com.caucho.hessian.client.HessianConnectionException;
+import com.caucho.hessian.client.HessianConnectionFactory;
import com.caucho.hessian.client.HessianProxyFactory;
import com.caucho.hessian.io.HessianMethodSerializationException;
import com.caucho.hessian.server.HessianSkeleton;
@@ -37,6 +40,7 @@ import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.net.SocketTimeoutException;
import java.util.ArrayList;
+import java.util.Enumeration;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
@@ -73,12 +77,17 @@ public class HessianProtocol extends AbstractProxyProtocol {
serverMap.put(addr, server);
}
final String path = url.getAbsolutePath();
- HessianSkeleton skeleton = new HessianSkeleton(impl, type);
+ final HessianSkeleton skeleton = new HessianSkeleton(impl, type);
skeletonMap.put(path, skeleton);
+
+ final String genericPath = path + "/" + Constants.GENERIC_KEY;
+ skeletonMap.put(genericPath, new HessianSkeleton(impl, GenericService.class));
+
return new Runnable() {
@Override
public void run() {
skeletonMap.remove(path);
+ skeletonMap.remove(genericPath);
}
};
}
@@ -86,6 +95,13 @@ public class HessianProtocol extends AbstractProxyProtocol {
@Override
@SuppressWarnings("unchecked")
protected <T> T doRefer(Class<T> serviceType, URL url) throws RpcException {
+ String generic = url.getParameter(Constants.GENERIC_KEY);
+ boolean isGeneric = ProtocolUtils.isGeneric(generic) || serviceType.equals(GenericService.class);
+ if (isGeneric) {
+ RpcContext.getContext().setAttachment(Constants.GENERIC_KEY, generic);
+ url = url.setPath(url.getPath() + "/" + Constants.GENERIC_KEY);
+ }
+
HessianProxyFactory hessianProxyFactory = new HessianProxyFactory();
boolean isHessian2Request = url.getParameter(Constants.HESSIAN2_REQUEST_KEY, Constants.DEFAULT_HESSIAN2_REQUEST);
hessianProxyFactory.setHessian2Request(isHessian2Request);
@@ -96,6 +112,10 @@ public class HessianProtocol extends AbstractProxyProtocol {
hessianProxyFactory.setConnectionFactory(new HttpClientConnectionFactory());
} else if (client != null && client.length() > 0 && !Constants.DEFAULT_HTTP_CLIENT.equals(client)) {
throw new IllegalStateException("Unsupported http protocol client=\"" + client + "\"!");
+ } else {
+ HessianConnectionFactory factory = new DubboHessianURLConnectionFactory();
+ factory.setHessianProxyFactory(hessianProxyFactory);
+ hessianProxyFactory.setConnectionFactory(factory);
}
int timeout = url.getParameter(Constants.TIMEOUT_KEY, Constants.DEFAULT_TIMEOUT);
hessianProxyFactory.setConnectTimeout(timeout);
@@ -148,6 +168,16 @@ public class HessianProtocol extends AbstractProxyProtocol {
response.setStatus(500);
} else {
RpcContext.getContext().setRemoteAddress(request.getRemoteAddr(), request.getRemotePort());
+
+ Enumeration<String> enumeration = request.getHeaderNames();
+ while (enumeration.hasMoreElements()) {
+ String key = enumeration.nextElement();
+ if (key.startsWith(Constants.DEFAULT_EXCHANGER)) {
+ RpcContext.getContext().setAttachment(key.substring(Constants.DEFAULT_EXCHANGER.length()),
+ request.getHeader(key));
+ }
+ }
+
try {
skeleton.invoke(request.getInputStream(), response.getOutputStream());
} catch (Throwable e) {
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HttpClientConnectionFactory.java b/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HttpClientConnectionFactory.java
index 033277d..b19cd27 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HttpClientConnectionFactory.java
+++ b/dubbo-rpc/dubbo-rpc-hessian/src/main/java/com/alibaba/dubbo/rpc/protocol/hessian/HttpClientConnectionFactory.java
@@ -16,6 +16,8 @@
*/
package com.alibaba.dubbo.rpc.protocol.hessian;
+import com.alibaba.dubbo.common.Constants;
+import com.alibaba.dubbo.rpc.RpcContext;
import com.caucho.hessian.client.HessianConnection;
import com.caucho.hessian.client.HessianConnectionFactory;
import com.caucho.hessian.client.HessianProxyFactory;
@@ -41,7 +43,12 @@ public class HttpClientConnectionFactory implements HessianConnectionFactory {
@Override
public HessianConnection open(URL url) throws IOException {
- return new HttpClientConnection(httpClient, url);
+ HttpClientConnection httpClientConnection = new HttpClientConnection(httpClient, url);
+ RpcContext context = RpcContext.getContext();
+ for (String key : context.getAttachments().keySet()) {
+ httpClientConnection.addHeader(Constants.DEFAULT_EXCHANGER + key, context.getAttachment(key));
+ }
+ return httpClientConnection;
}
}
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocolTest.java b/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocolTest.java
index 877ecd3..bae0333 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocolTest.java
+++ b/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianProtocolTest.java
@@ -17,17 +17,29 @@
package com.alibaba.dubbo.rpc.protocol.hessian;
import com.alibaba.dubbo.common.URL;
+import com.alibaba.dubbo.common.beanutil.JavaBeanDescriptor;
+import com.alibaba.dubbo.common.beanutil.JavaBeanSerializeUtil;
import com.alibaba.dubbo.common.extension.ExtensionLoader;
+import com.alibaba.dubbo.common.serialize.ObjectInput;
+import com.alibaba.dubbo.common.serialize.ObjectOutput;
+import com.alibaba.dubbo.common.serialize.Serialization;
+import com.alibaba.dubbo.common.serialize.nativejava.NativeJavaSerialization;
import com.alibaba.dubbo.rpc.Exporter;
import com.alibaba.dubbo.rpc.Invoker;
import com.alibaba.dubbo.rpc.Protocol;
import com.alibaba.dubbo.rpc.ProxyFactory;
+import com.alibaba.dubbo.rpc.RpcContext;
import com.alibaba.dubbo.rpc.RpcException;
import com.alibaba.dubbo.rpc.protocol.hessian.HessianServiceImpl.MyException;
+import com.alibaba.dubbo.rpc.service.GenericService;
import org.junit.Assert;
import org.junit.Test;
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+
import static org.junit.Assert.fail;
/**
@@ -53,6 +65,87 @@ public class HessianProtocolTest {
}
@Test
+ public void testGenericInvoke() {
+ HessianServiceImpl server = new HessianServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("hessian://127.0.0.1:5342/" + HessianService.class.getName() + "?version=1.0.0");
+ Exporter<HessianService> exporter = protocol.export(proxyFactory.getInvoker(server, HessianService.class, url));
+ Invoker<GenericService> invoker = protocol.refer(GenericService.class, url);
+ GenericService client = proxyFactory.getProxy(invoker, true);
+ String result = (String) client.$invoke("sayHello", new String[]{"java.lang.String"}, new Object[]{"haha"});
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", result);
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testGenericInvokeWithNativeJava() throws IOException, ClassNotFoundException {
+ HessianServiceImpl server = new HessianServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("hessian://127.0.0.1:5342/" + HessianService.class.getName() + "?version=1.0.0&generic=nativejava");
+ Exporter<HessianService> exporter = protocol.export(proxyFactory.getInvoker(server, HessianService.class, url));
+ Invoker<GenericService> invoker = protocol.refer(GenericService.class, url);
+ GenericService client = proxyFactory.getProxy(invoker);
+
+ Serialization serialization = new NativeJavaSerialization();
+ ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
+
+ ObjectOutput objectOutput = serialization.serialize(url, byteArrayOutputStream);
+ objectOutput.writeObject("haha");
+ objectOutput.flushBuffer();
+
+ Object result = client.$invoke("sayHello", new String[]{"java.lang.String"}, new Object[]{byteArrayOutputStream.toByteArray()});
+ ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream((byte[]) result);
+ ObjectInput objectInput = serialization.deserialize(url, byteArrayInputStream);
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", objectInput.readObject());
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testGenericInvokeWithRpcContext() {
+ RpcContext.getContext().setAttachment("myContext", "123");
+
+ HessianServiceImpl server = new HessianServiceImpl();
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("hessian://127.0.0.1:5342/" + HessianService.class.getName() + "?version=1.0.0");
+ Exporter<HessianService> exporter = protocol.export(proxyFactory.getInvoker(server, HessianService.class, url));
+ Invoker<GenericService> invoker = protocol.refer(GenericService.class, url);
+ GenericService client = proxyFactory.getProxy(invoker, true);
+ String result = (String) client.$invoke("context", new String[]{"java.lang.String"}, new Object[]{"haha"});
+ Assert.assertEquals("Hello, haha context, 123", result);
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testGenericInvokeWithBean() {
+ HessianServiceImpl server = new HessianServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("hessian://127.0.0.1:5342/" + HessianService.class.getName() + "?version=1.0.0&generic=bean");
+ Exporter<HessianService> exporter = protocol.export(proxyFactory.getInvoker(server, HessianService.class, url));
+ Invoker<GenericService> invoker = protocol.refer(GenericService.class, url);
+ GenericService client = proxyFactory.getProxy(invoker);
+
+ JavaBeanDescriptor javaBeanDescriptor = JavaBeanSerializeUtil.serialize("haha");
+
+ Object result = client.$invoke("sayHello", new String[]{"java.lang.String"}, new Object[]{javaBeanDescriptor});
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", JavaBeanSerializeUtil.deserialize((JavaBeanDescriptor) result));
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
public void testOverload() {
HessianServiceImpl server = new HessianServiceImpl();
Assert.assertFalse(server.isCalled());
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java b/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
index 8629425..9df4524 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
+++ b/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
@@ -30,4 +30,6 @@ public interface HessianService {
String customException();
+ String context(String name);
+
}
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianServiceImpl.java b/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianServiceImpl.java
index 855de0a..68d14b3 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianServiceImpl.java
+++ b/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianServiceImpl.java
@@ -16,6 +16,8 @@
*/
package com.alibaba.dubbo.rpc.protocol.hessian;
+import com.alibaba.dubbo.rpc.RpcContext;
+
/**
* HessianServiceImpl
*/
@@ -53,6 +55,10 @@ public class HessianServiceImpl implements HessianService {
throw new MyException("custom exception");
}
+ public String context(String name) {
+ return "Hello, " + name + " context, " + RpcContext.getContext().getAttachment("myContext");
+ }
+
static class MyException extends RuntimeException {
private static final long serialVersionUID = -3051041116483629056L;
diff --git a/dubbo-rpc/dubbo-rpc-http/pom.xml b/dubbo-rpc/dubbo-rpc-http/pom.xml
index 427b70b..93d8a0f 100644
--- a/dubbo-rpc/dubbo-rpc-http/pom.xml
+++ b/dubbo-rpc/dubbo-rpc-http/pom.xml
@@ -48,5 +48,11 @@
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
</dependency>
+ <dependency>
+ <groupId>com.alibaba</groupId>
+ <artifactId>dubbo-serialization-jdk</artifactId>
+ <version>${project.parent.version}</version>
+ <scope>test</scope>
+ </dependency>
</dependencies>
</project>
\ No newline at end of file
diff --git a/dubbo-rpc/dubbo-rpc-http/src/main/java/com/alibaba/dubbo/rpc/protocol/http/HttpProtocol.java b/dubbo-rpc/dubbo-rpc-http/src/main/java/com/alibaba/dubbo/rpc/protocol/http/HttpProtocol.java
index 27a5913..3fc9087 100644
--- a/dubbo-rpc/dubbo-rpc-http/src/main/java/com/alibaba/dubbo/rpc/protocol/http/HttpProtocol.java
+++ b/dubbo-rpc/dubbo-rpc-http/src/main/java/com/alibaba/dubbo/rpc/protocol/http/HttpProtocol.java
@@ -24,12 +24,16 @@ import com.alibaba.dubbo.remoting.http.HttpServer;
import com.alibaba.dubbo.rpc.RpcContext;
import com.alibaba.dubbo.rpc.RpcException;
import com.alibaba.dubbo.rpc.protocol.AbstractProxyProtocol;
-
+import com.alibaba.dubbo.rpc.service.GenericService;
+import com.alibaba.dubbo.rpc.support.ProtocolUtils;
+import org.aopalliance.intercept.MethodInvocation;
import org.springframework.remoting.RemoteAccessException;
import org.springframework.remoting.httpinvoker.HttpComponentsHttpInvokerRequestExecutor;
import org.springframework.remoting.httpinvoker.HttpInvokerProxyFactoryBean;
import org.springframework.remoting.httpinvoker.HttpInvokerServiceExporter;
import org.springframework.remoting.httpinvoker.SimpleHttpInvokerRequestExecutor;
+import org.springframework.remoting.support.RemoteInvocation;
+import org.springframework.remoting.support.RemoteInvocationFactory;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
@@ -74,6 +78,22 @@ public class HttpProtocol extends AbstractProxyProtocol {
server = httpBinder.bind(url, new InternalHandler());
serverMap.put(addr, server);
}
+ final String path = url.getAbsolutePath();
+ skeletonMap.put(path, createExporter(impl, type));
+
+ final String genericPath = path + "/" + Constants.GENERIC_KEY;
+
+ skeletonMap.put(genericPath, createExporter(impl, GenericService.class));
+ return new Runnable() {
+ @Override
+ public void run() {
+ skeletonMap.remove(path);
+ skeletonMap.remove(genericPath);
+ }
+ };
+ }
+
+ private <T> HttpInvokerServiceExporter createExporter(T impl, Class<?> type) {
final HttpInvokerServiceExporter httpServiceExporter = new HttpInvokerServiceExporter();
httpServiceExporter.setServiceInterface(type);
httpServiceExporter.setService(impl);
@@ -82,21 +102,33 @@ public class HttpProtocol extends AbstractProxyProtocol {
} catch (Exception e) {
throw new RpcException(e.getMessage(), e);
}
- final String path = url.getAbsolutePath();
- skeletonMap.put(path, httpServiceExporter);
- return new Runnable() {
- @Override
- public void run() {
- skeletonMap.remove(path);
- }
- };
+ return httpServiceExporter;
}
@Override
@SuppressWarnings("unchecked")
protected <T> T doRefer(final Class<T> serviceType, final URL url) throws RpcException {
+ final String generic = url.getParameter(Constants.GENERIC_KEY);
+ final boolean isGeneric = ProtocolUtils.isGeneric(generic) || serviceType.equals(GenericService.class);
+
final HttpInvokerProxyFactoryBean httpProxyFactoryBean = new HttpInvokerProxyFactoryBean();
- httpProxyFactoryBean.setServiceUrl(url.toIdentityString());
+ httpProxyFactoryBean.setRemoteInvocationFactory(new RemoteInvocationFactory() {
+ @Override
+ public RemoteInvocation createRemoteInvocation(MethodInvocation methodInvocation) {
+ RemoteInvocation invocation = new HttpRemoteInvocation(methodInvocation);
+ if (isGeneric) {
+ invocation.addAttribute(Constants.GENERIC_KEY, generic);
+ }
+ return invocation;
+ }
+ });
+
+ String key = url.toIdentityString();
+ if (isGeneric) {
+ key = key + "/" + Constants.GENERIC_KEY;
+ }
+
+ httpProxyFactoryBean.setServiceUrl(key);
httpProxyFactoryBean.setServiceInterface(serviceType);
String client = url.getParameter(Constants.CLIENT_KEY);
if (client == null || client.length() == 0 || "simple".equals(client)) {
@@ -112,7 +144,8 @@ public class HttpProtocol extends AbstractProxyProtocol {
httpProxyFactoryBean.setHttpInvokerRequestExecutor(httpInvokerRequestExecutor);
} else if ("commons".equals(client)) {
HttpComponentsHttpInvokerRequestExecutor httpInvokerRequestExecutor = new HttpComponentsHttpInvokerRequestExecutor();
- httpInvokerRequestExecutor.setReadTimeout(url.getParameter(Constants.CONNECT_TIMEOUT_KEY, Constants.DEFAULT_CONNECT_TIMEOUT));
+ httpInvokerRequestExecutor.setReadTimeout(url.getParameter(Constants.TIMEOUT_KEY, Constants.DEFAULT_TIMEOUT));
+ httpInvokerRequestExecutor.setConnectTimeout(url.getParameter(Constants.CONNECT_TIMEOUT_KEY, Constants.DEFAULT_CONNECT_TIMEOUT));
httpProxyFactoryBean.setHttpInvokerRequestExecutor(httpInvokerRequestExecutor);
} else {
throw new IllegalStateException("Unsupported http protocol client " + client + ", only supported: simple, commons");
diff --git a/dubbo-rpc/dubbo-rpc-http/src/main/java/com/alibaba/dubbo/rpc/protocol/http/HttpRemoteInvocation.java b/dubbo-rpc/dubbo-rpc-http/src/main/java/com/alibaba/dubbo/rpc/protocol/http/HttpRemoteInvocation.java
new file mode 100644
index 0000000..5054c4f
--- /dev/null
+++ b/dubbo-rpc/dubbo-rpc-http/src/main/java/com/alibaba/dubbo/rpc/protocol/http/HttpRemoteInvocation.java
@@ -0,0 +1,57 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.alibaba.dubbo.rpc.protocol.http;
+
+import com.alibaba.dubbo.common.Constants;
+import com.alibaba.dubbo.common.utils.StringUtils;
+import com.alibaba.dubbo.rpc.RpcContext;
+import org.aopalliance.intercept.MethodInvocation;
+import org.springframework.remoting.support.RemoteInvocation;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.HashMap;
+import java.util.Map;
+
+public class HttpRemoteInvocation extends RemoteInvocation {
+
+ private static final long serialVersionUID = 1L;
+ private static final String dubboAttachmentsAttrName = "dubbo.attachments";
+
+ public HttpRemoteInvocation(MethodInvocation methodInvocation) {
+ super(methodInvocation);
+ addAttribute(dubboAttachmentsAttrName, new HashMap<String, String>(RpcContext.getContext().getAttachments()));
+ }
+
+ @Override
+ public Object invoke(Object targetObject) throws NoSuchMethodException, IllegalAccessException,
+ InvocationTargetException {
+ RpcContext context = RpcContext.getContext();
+ context.setAttachments((Map<String, String>) getAttribute(dubboAttachmentsAttrName));
+
+ String generic = (String) getAttribute(Constants.GENERIC_KEY);
+ if (StringUtils.isNotEmpty(generic)) {
+ context.setAttachment(Constants.GENERIC_KEY, generic);
+ }
+ try {
+ return super.invoke(targetObject);
+ } finally {
+ context.setAttachments(null);
+
+ }
+ }
+}
diff --git a/dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpProtocolTest.java b/dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpProtocolTest.java
new file mode 100644
index 0000000..014eed6
--- /dev/null
+++ b/dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpProtocolTest.java
@@ -0,0 +1,198 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.alibaba.dubbo.rpc.protocol.http;
+
+import com.alibaba.dubbo.common.URL;
+import com.alibaba.dubbo.common.beanutil.JavaBeanDescriptor;
+import com.alibaba.dubbo.common.beanutil.JavaBeanSerializeUtil;
+import com.alibaba.dubbo.common.extension.ExtensionLoader;
+import com.alibaba.dubbo.common.serialize.ObjectInput;
+import com.alibaba.dubbo.common.serialize.ObjectOutput;
+import com.alibaba.dubbo.common.serialize.Serialization;
+import com.alibaba.dubbo.common.serialize.nativejava.NativeJavaSerialization;
+import com.alibaba.dubbo.rpc.*;
+import com.alibaba.dubbo.rpc.service.GenericService;
+import junit.framework.Assert;
+import org.junit.Test;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+
+import static org.junit.Assert.fail;
+
+/**
+ * HttpProtocolTest
+ */
+public class HttpProtocolTest {
+
+ @Test
+ public void testHttpProtocol() {
+ HttpServiceImpl server = new HttpServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<HttpService> invoker = protocol.refer(HttpService.class, url);
+ HttpService client = proxyFactory.getProxy(invoker);
+ String result = client.sayHello("haha");
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", result);
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testGenericInvoke() {
+ HttpServiceImpl server = new HttpServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<GenericService> invoker = protocol.refer(GenericService.class, url);
+ GenericService client = proxyFactory.getProxy(invoker, true);
+ String result = (String) client.$invoke("sayHello", new String[]{"java.lang.String"}, new Object[]{"haha"});
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", result);
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testGenericInvokeWithNativeJava() throws IOException, ClassNotFoundException {
+ HttpServiceImpl server = new HttpServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0&generic=nativejava");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<GenericService> invoker = protocol.refer(GenericService.class, url);
+ GenericService client = proxyFactory.getProxy(invoker);
+
+ Serialization serialization = new NativeJavaSerialization();
+ ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
+
+ ObjectOutput objectOutput = serialization.serialize(url, byteArrayOutputStream);
+ objectOutput.writeObject("haha");
+ objectOutput.flushBuffer();
+
+ Object result = client.$invoke("sayHello", new String[]{"java.lang.String"}, new Object[]{byteArrayOutputStream.toByteArray()});
+ ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream((byte[]) result);
+ ObjectInput objectInput = serialization.deserialize(url, byteArrayInputStream);
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", objectInput.readObject());
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testGenericInvokeWithBean() {
+ HttpServiceImpl server = new HttpServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0&generic=bean");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<GenericService> invoker = protocol.refer(GenericService.class, url);
+ GenericService client = proxyFactory.getProxy(invoker);
+
+ JavaBeanDescriptor javaBeanDescriptor = JavaBeanSerializeUtil.serialize("haha");
+
+ Object result = client.$invoke("sayHello", new String[]{"java.lang.String"}, new Object[]{javaBeanDescriptor});
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", JavaBeanSerializeUtil.deserialize((JavaBeanDescriptor) result));
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testOverload() {
+ HttpServiceImpl server = new HttpServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0&hessian.overload.method=true&hessian2.request=false");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<HttpService> invoker = protocol.refer(HttpService.class, url);
+ HttpService client = proxyFactory.getProxy(invoker);
+ String result = client.sayHello("haha");
+ Assert.assertEquals("Hello, haha", result);
+ result = client.sayHello("haha", 1);
+ Assert.assertEquals("Hello, haha. ", result);
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testSimpleClient() {
+ HttpServiceImpl server = new HttpServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0&client=simple");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<HttpService> invoker = protocol.refer(HttpService.class, url);
+ HttpService client = proxyFactory.getProxy(invoker);
+ String result = client.sayHello("haha");
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", result);
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ @Test
+ public void testTimeOut() {
+ HttpServiceImpl server = new HttpServiceImpl();
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0&timeout=10");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<HttpService> invoker = protocol.refer(HttpService.class, url);
+ HttpService client = proxyFactory.getProxy(invoker);
+ try {
+ client.timeOut(6000);
+ fail();
+ } catch (RpcException expected) {
+ Assert.assertEquals(true, expected.isTimeout());
+ } finally {
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+ }
+
+ @Test
+ public void testCustomException() {
+ HttpServiceImpl server = new HttpServiceImpl();
+ ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+ Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ URL url = URL.valueOf("http://127.0.0.1:5342/" + HttpService.class.getName() + "?version=1.0.0");
+ Exporter<HttpService> exporter = protocol.export(proxyFactory.getInvoker(server, HttpService.class, url));
+ Invoker<HttpService> invoker = protocol.refer(HttpService.class, url);
+ HttpService client = proxyFactory.getProxy(invoker);
+ try {
+ client.customException();
+ fail();
+ } catch (HttpServiceImpl.MyException expected) {
+ }
+ invoker.destroy();
+ exporter.unexport();
+ }
+
+}
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java b/dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpService.java
similarity index 87%
copy from dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
copy to dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpService.java
index 8629425..0d0d22c 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
+++ b/dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpService.java
@@ -14,16 +14,16 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package com.alibaba.dubbo.rpc.protocol.hessian;
+package com.alibaba.dubbo.rpc.protocol.http;
/**
- * HessianService
+ * HttpService
*/
-public interface HessianService {
+public interface HttpService {
String sayHello(String name);
-
+
String sayHello(String name, int times);
void timeOut(int millis);
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianServiceImpl.java b/dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpServiceImpl.java
similarity index 90%
copy from dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianServiceImpl.java
copy to dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpServiceImpl.java
index 855de0a..1c78b3b 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianServiceImpl.java
+++ b/dubbo-rpc/dubbo-rpc-http/src/test/java/com/alibaba/dubbo/rpc/protocol/http/HttpServiceImpl.java
@@ -14,12 +14,12 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package com.alibaba.dubbo.rpc.protocol.hessian;
+package com.alibaba.dubbo.rpc.protocol.http;
/**
- * HessianServiceImpl
+ * HttpServiceImpl
*/
-public class HessianServiceImpl implements HessianService {
+public class HttpServiceImpl implements HttpService {
private boolean called;
@@ -27,7 +27,7 @@ public class HessianServiceImpl implements HessianService {
called = true;
return "Hello, " + name;
}
-
+
public String sayHello(String name, int times) {
called = true;
StringBuilder sb = new StringBuilder();
diff --git a/dubbo-rpc/dubbo-rpc-rest/pom.xml b/dubbo-rpc/dubbo-rpc-rest/pom.xml
index 026e2c2..724ae6d 100644
--- a/dubbo-rpc/dubbo-rpc-rest/pom.xml
+++ b/dubbo-rpc/dubbo-rpc-rest/pom.xml
@@ -105,5 +105,11 @@
<artifactId>netty-all</artifactId>
</dependency>
+ <dependency>
+ <groupId>com.alibaba</groupId>
+ <artifactId>dubbo-serialization-jdk</artifactId>
+ <version>${project.parent.version}</version>
+ <scope>test</scope>
+ </dependency>
</dependencies>
</project>
\ No newline at end of file
diff --git a/dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestProtocolTest.java b/dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestProtocolTest.java
new file mode 100644
index 0000000..4764cf6
--- /dev/null
+++ b/dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestProtocolTest.java
@@ -0,0 +1,48 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.alibaba.dubbo.rpc.protol.rest;
+
+import com.alibaba.dubbo.common.URL;
+import com.alibaba.dubbo.common.extension.ExtensionLoader;
+import com.alibaba.dubbo.rpc.*;
+import junit.framework.Assert;
+import org.junit.Test;
+
+/**
+ * RestProtocolTest
+ */
+public class RestProtocolTest {
+
+ private Protocol protocol = ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
+ private ProxyFactory proxyFactory = ExtensionLoader.getExtensionLoader(ProxyFactory.class).getAdaptiveExtension();
+
+ @Test
+ public void testRestProtocol() {
+ ServiceClassHolder.getInstance().pushServiceClass(RestServiceImpl.class);
+ RestServiceImpl server = new RestServiceImpl();
+ Assert.assertFalse(server.isCalled());
+ URL url = URL.valueOf("rest://127.0.0.1:5342/rest/say1?version=1.0.0");
+ Exporter<RestService> exporter = protocol.export(proxyFactory.getInvoker(server, RestService.class, url));
+ Invoker<RestService> invoker = protocol.refer(RestService.class, url);
+ RestService client = proxyFactory.getProxy(invoker);
+ String result = client.sayHello("haha");
+ Assert.assertTrue(server.isCalled());
+ Assert.assertEquals("Hello, haha", result);
+ invoker.destroy();
+ exporter.unexport();
+ }
+}
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java b/dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestService.java
similarity index 72%
copy from dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
copy to dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestService.java
index 8629425..30441b2 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
+++ b/dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestService.java
@@ -14,20 +14,23 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package com.alibaba.dubbo.rpc.protocol.hessian;
+package com.alibaba.dubbo.rpc.protol.rest;
+import javax.ws.rs.Consumes;
+import javax.ws.rs.POST;
+import javax.ws.rs.Path;
+import javax.ws.rs.core.MediaType;
+
/**
- * HessianService
+ * RestService
*/
-public interface HessianService {
+@Path("/rest")
+public interface RestService {
+ @POST
+ @Path("/say1")
+ @Consumes({MediaType.TEXT_PLAIN})
String sayHello(String name);
- String sayHello(String name, int times);
-
- void timeOut(int millis);
-
- String customException();
-
}
diff --git a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java b/dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestServiceImpl.java
similarity index 70%
copy from dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
copy to dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestServiceImpl.java
index 8629425..3de80d2 100644
--- a/dubbo-rpc/dubbo-rpc-hessian/src/test/java/com/alibaba/dubbo/rpc/protocol/hessian/HessianService.java
+++ b/dubbo-rpc/dubbo-rpc-rest/src/test/java/com/alibaba/dubbo/rpc/protol/rest/RestServiceImpl.java
@@ -14,20 +14,23 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package com.alibaba.dubbo.rpc.protocol.hessian;
-
+package com.alibaba.dubbo.rpc.protol.rest;
/**
- * HessianService
+ * RestServiceImpl
*/
-public interface HessianService {
- String sayHello(String name);
+public class RestServiceImpl implements RestService {
- String sayHello(String name, int times);
+ private boolean called;
- void timeOut(int millis);
+ public String sayHello(String name) {
+ called = true;
+ return "Hello, " + name;
+ }
- String customException();
+ public boolean isCalled() {
+ return called;
+ }
}
--
To stop receiving notification emails like this one, please contact
liujun@apache.org.