Showing posts with label proxy. Show all posts
Showing posts with label proxy. Show all posts

Monday, July 30, 2007

Spring HTTP Remoting - How ?

preface:
Spring give us few ways to communicate between client and server.
One of these ways is by using http remoting.
Http remoting is a way to invoke remote methods on server.
Spring http remoting uses Http protocol in order to achive that goal.

When do we need it?
When we want our server to expose services to clients.
say we want to expose service who gives us collection of some application users.

How we do it?
Server will expose service using simple independent interface:
public interface userService{
public Collection getAllUsers();
}

As you can see the interface can be independent, and no need to extend from nothing.

Then, we will implement this interface:
public class UserServiceImpl implements UserService{
public Collection getAllUsers() {
//do implementation...
}
}

Client - need to have only the interface in its class path.
Serevr - need to have both interface and implementing class in its classpath.

So, client is unknow with the implementation, only with the interface - like we wish for.

In order to make it work, we will use Spring HTTP Remoting.
Spring Http remoting uses the standard Java serialization mechanism to expose services through HTTP.

Exposing server service:
first, we will create simple bean using spring. the bean will be the service implementation:
< id="userService" class="example.UserServiceImpl">

then, we will expose the service with name "/UserService">
< name="">/UserService"
class="org.springframework.remoting.httpinvoker.HttpInvokerServiceExporter">
< name="service" ref="userService">
< name="serviceInterface" value="example.UserService">
< /bean >

Configuration of web.xml (only once for all services):
< /servlet &gt
< servlet-name &gt remoting < / servlet-name &gt
< servlet-class &gt org.springframework.web.servlet.DispatcherServlet < / servlet-class &gt
< /servlet >

<>
remoting < / servlet-name >
/remoting/* < /url-pattern >
< /servlet-mapping >


Linking the service at the client side:
< id="">userServiceProxy"
class="org.springframework.remoting.httpinvoker.HttpInvokerProxyFactoryBean" >
< name="serviceUrl" value="">/UserService"/ >
< name="serviceInterface" value="">UserService"/ >
< /bean >

Then, in order to invoke service:
UserService service = (UserService) appContext.getBean("userServiceProxy");
Collection allUsers = service.getAllUsers();


And.. thats it. service will be invoked on server and client will get the results.

So, how it works ?


  1. The userServiceProxy bean that we created is a proxy.
  2. When method is being called, the proxy takes the method and its arguments and creates org.springframework.remoting.support.RemoteInvocation object. this object holds the information about the method invoked, like method name and which arguments given to method (and more).
  3. The RemoteInvocation object is serialiezed and pushed into an http request to url we declared in "serviceUrl" property of proxy ("http://host:8080/remoting/UserService").
  4. When request reachs server, the url is mapped by us in web.xml and will be dispatch to a spring servlet.
  5. The RemoteInvocation object is deserialized, and by using reflaction the method is being executed - on server.
  6. Then org.springframework.remoting.support.RemoteInvocationResult object will be created. this object will hold the result of execution or the exception if accured.
  7. The RemoteInvocationResult object will serialized and phushed into an HTTP response.
  8. Client will get the response, and will deserialize RemoteInvocationResult object.
  9. If the RemoteInvocationResult object holds an exception - it will be thrown, else the value of method will be returned.

So as you can see, using Spring http is very easy to use and to understand. spring give us a way to make remote invocation transparent for us, and we can use services as they were on our client.

This mechanism can be extended and give us more abilities, like adding attributes on request and so on... i hope i will find the time to represent these abilities in the near futher.

Monday, July 23, 2007

Java Dynamic Proxy, simple yet powerfull!

What is Proxy?

Proxy is a well know design pattern.
Proxy is an object how encapsulate another object .

Say we have some interface, and some implementations. the implementations are real subject implementations. each implementation doing concrete operation. lets say that we want to add some behavior to all implementations, without touching each implementation code. for example, we would like to write to log before and after each operation invocation. the simplest way is to use one abstract class for all implementation to extend from, and by using some template methods we can achieve this goal. but, using abstract class has its limitations:

  • if we have an object how implements two interfaces, and we want to extends some behavior for both interfaces - we cannot do that using two different abstract class.
  • each implementation should extends the abstract class,so the implementations are now "dirty" and if one of the implementations is a third party code - we cannot do that.

so, whats is the solution ?

Proxy !

We can create some new object called MyProxy.

MyProxy will implement the interface and hold a private member of interface type (called target object). the implementation of proxy will be to delegate each method to invoke the targets methods implementation, so this proxy can hold all know implementation of interface, and invoke concrete implementations.

Now, we can add behaviors like log writing, just before and after we delegate the method to target implementation.

As you can understand now, we don't have any limitations we had using abstract classes, and we are free to add any behavior we like.


What is dynamic Proxy?
Dynamic proxy is a proxy we create at runtime. no need to write a proxy object how implements the interface. we can create implementation of some interface at runtime, and encapsulate from user that he is not using his concrete implementation, and add a behaviors as we wish.

How can we do it ?
Using JDK dynamic proxy.

The object java.lang.reflect.Proxy is a dynamic proxy how can create for us proxies for a given interfaces at runtime.

first we will need to implement java.lang.reflect.InvocationHandler interface:

public MyHandler extends java.lang.reflect.InvocationHandler{

T target;

public myHandler (T target){

this.target = target.

}

Object invoke(Object proxy, Method method,Object[] args) {

//do before

method.invoke(target,args);

//do after

}

}

Now we can create proxy for any interface that we wish to add this behavior. say we want to create proxy for Foo interface encapsulating FooImpl:

Foo implementation = new FooImpl();

Foo f = (Foo) Proxy.newProxyInstance(Foo.class.getClassLoader(), new Class[] Foo.class } , new MyHandler(implementation));

now when we execute f.someMethod() will will execute FooImpl implementation with extra behavior.

This is a simple example of using proxies to achieve extended behaviors. Proxy can be use for a lot of other use cases like security check points, lazy loading of data, and many more.

So, use it, but do not over use it!