What is the difference between Java RMI and JMS? - java

When designing an distributed application in Java there seem to be a few technologies that address the same kind of problem. I have briefly read about Java Remote Method Invocation and Java Message Service, but it is hard to really see the difference. Java RMI seems to be more tightly coupled than JMS because JMS uses asynchronous communication, but otherwise I don't see any big differences.
What is the difference between them?
Is one of them newer than the other one?
Which one is more common/popular in enterprises?
What advantages do they have over each other?
When is one preferred over the other?
Do they differ much in how difficult they are to implement?
I also think that Web Services and CORBA address the same problem.

You already know about method calls. What if the object that you want to invoke the method on is on a different computer? You use RMI to send the call from one computer (client) to the other (server). The client will wait (or "block") until the result comes back from the server. This is called synchronous operation.
JMS is different: it lets one computer send a message to another - like email. The first one doesn't have to wait for a response: it can keep doing whatever work it wants. There may not even be a response. The two computer systems don't necessarily work exactly in step, so this is called asynchronous.
Another way of thinking about the difference: RMI is like making a phone call, and JMS is like sending a text message.
RMI is a little older than JMS, but that's not really relevant. The two concepts are much much older than java.
There's not much difference in the complexity. I think that you should try doing a tutorial on each one. RMI and JMS
If you're starting a project from scratch, and you're not sure which one to use, then probably the synchronous/asynchronous issue is the best decision factor. If you're working on an existing system, it's probably best not to introduce too many new technologies. So if they're already using one, then I'd suggest it's probably best to stick with that one.

You cannot really compare the two, its apples and oranges.
RMI is a form of Remote Procedure Call (RPC). It is a lightweight, Java specific API that expects the caller and receiver to be available at the time of communication.
JMS is a reliable messaging API. JMS providers exist for various messaging systems. Messages can be passed even if one of the parties is not available if the provider implements that. The two I am familiar with are TIBCO and IBM MQ.
RMI doesn't deal with guaranteed delivery or asynchronous responses, JMS may, depending on the provider.
JMS allows loose coupling in the sense of availability.
"Web Services" allows loose coupling in the sense of protocol and data but doesn't specify much in the way of reliable messaging, though some implementations do include this (Windows Communication Foundation) and some don't.
EDITED: Revised per comments. When I wrote this answer in 2010 my experience was actually with only one JMS provider and I didn't actually know there was no default JMS provider.

Related

How can I connect an android with a local server?

sorry if my english isn't perfect.
I'm trying to make an app and I need to exchange information between more devices.
I thought that could be a solution connect the devices on a server but I really don't have the idea where start.
What language I need to study to make this? There is a better solution?
This highly depends on what you are trying to achieve in the first place. It would be helpful if you could tell what you are trying to do, but I will still outline some general aspects:
You need to decide, what information is going to be exchanged and how this should happen
What information: Figure out, what exactly needs to be sent and received. Generic text messages? Images? Byte Streams?
How should this be done: Generally spoken, there are two approaches of getting information as a client: Polling and subscribing.
Polling: This approach means to periodically check an endpoint for new data. For example, HTTP uses this way: A web browser or any other client (REST-Client for example) periodically requests information from a HTTP-Server, using a connection just for this single request.
Subscribing / Sync / Notification: In some way or another, the client tells the server that it is interested in the information and wants to get notified when there is something new. The connection is initiated at the beginning and held open for further usage. The benefit of this approach is that changes are received immediately, but on the other hand a permanent connection needs to be maintained.
Things to study
At the beginning, get a good understanding of the TCP/IP Protocol, how Sockets work, how common Protocols do their job (e.g. HTTP, WebSockets)
Take a look at specific Protocols working on top of the basic ones
Tip: REST: Most common WebServices Protocol, providing a common way to exchange stateless data. Uses Polling.
WebSockets: Socket connection using Web Browsers. Commonly used to update information without needing to poll.
There is no specific language to learn for connections. It's more about understanding what the difficulties are and what ways have been invented to address this. Once you get to this point and know what you want to do, it's possible in every language.
Recommendation: As you seem to use Java/Android, I would try to use REST. A really great client-side library for REST on Android is Retrofit. For the server side use what fits for you .. common Java way would be to use Jersey, but you are free to choose from a lot of choices. If using Jersey is too hard for the beginning, maybe take a look at the JS/NodeJS world, those guys invented Express, which allows you to create a REST service out of just a database, wihtout having to code a lot.
First you need to decide if you want to go for an Android or an iOS application. There are other various mobile operating systems as well, but these are widely used . If you want to go for android which is most widely used in my opinion, then you need to learn Java. If you want to go for iOS application, then you need to learn swift or objectiveC. These languages provide the API to connect with various types of services such as Facebook, Firebase and Amazon etc. If you want to connect to some other local server who’s IP is known to you, then you can use socket programming to send messages.
There could be many ways you can implement this. One way will be using Web services. Of course REST might be a better option, if you follow this approach. You can implement Your service(server side code) with any language. I will recommend you use java since you are already using android.
Aside from this You might need to go through the basics of REST, its specifications and
some reference implementations for language of your preference.

Does it make sense to use messaging queues in a non-distributed application

So I'm planning on writing an application that would lend itself well to a producer/consumer pattern. I was thinking of building out my own producer/consumer framework but then thought about message queues something I use extensively at work. I'm not a 100% sure that a messaging queue would be the right approach considering that the multiple modules of the application I am writing need to run on a single server as its a client/controller of sorts for that particular host.
What are the pros and cons of using messaging queues for a non-distributed application? Has anyone used it in this way before?
Thanks, let me know if you need more information.
By "message queues" do you mean an external message server? My below answer assumes that is what you were aking about. If you are just asking about the more general architectural approach of having modules communicate partially, or in full, via in-memory-messages instead of method calls--yes sometimes this can be very nice. Classes like guava's EvenBus facilitate a design like this nicely: https://code.google.com/p/guava-libraries/wiki/EventBusExplained
On the one hand I generally try to discourage people from using JMS message queues when a simple queue data structure would suffice. Sometimes I feel that JMS is an inter-process communication tool that has one-to-many (topics) and one-to-one communication channels which happen to be named queues. Yes their access pattern is similar to that of a queue, but the more important characteristic, it seems to me, is their point-to-point messaging capability. So an unfortunate name that I think sometimes causes people to use a jackhammer (JMS) when all they need is a screwdriver (java.lang.Queue).
On the other hand there are exceptions to any rule. I can't recommend, off hand, a java.lang.Queue implementation that is thread-safe and persistent during server restart (an often needed feature when people are considering JMS). I'm sure there are some. Find a few and compare them to JMS. Weigh business needs, time constraints, possible future design/requirements, etc. I have implemented one myself before and it turned out quite nice (and was faster than sending messages over the network to a remote JMS server)-- but only you can say if this is right for your situation.
I suppose you could always defer the decision by having the modules of your app communicate through a messaging-like interface of your own which uses java.lang.Queues internally for now, but JMS later if you find that you need it. Though be careful here too-- adding unnecessary abstraction early is sometimes a burden that turns out not to be worth it.

What's the easiest and most efficient way to combine UDP and RPCs in java?

I'm currently considering using java in one of my projects(for reasons unrelated to networking). At the moment I'm using C++ and a custom protocol built on top of UDP. My problem here is that while the added efficiency is nice for sending large amounts of realtime-data, I'd rather have something along the lines of RPCs for pure "logic actions" such as login. RPC's in C++ are hard to do though, since standard C++ itself has no notion of serialization.
In another answer, I found Java's RMI, which seems to be similar to RPCs, but I couldn't find how efficient/responsive it is, nor whether it could be plugged into my existing UDP socket, since I don't want to have two ports open on my server program.
Alternatively, since I think Java has serialization, I could implement RPC's myself, depending on how straightforward deserializing an arbitrary stream of objects in java is. Still, if this would require me to spend days on learning the intrinsics of java, this wouldn't be an option for me.
If you're interested in RPC, there is always XML-RPC and JSON-RPC, both of which have free/open-source C++ implementations. Unfortunately, most of my development has been in Java, so I can't speak to how usable or effective they are, but it might be something to look into since it sounds like you have already done some work in C++ and are comfortable with it. They also have Java implementations, so you might even be able to support both Java and C++ applications with XML-RPC or JSON-RPC, if you want to go down that route.
The only downside is that it looks like most of these use HTTP connections. One of the things you wanted to do was to reuse the existing connection. Now, I haven't looked at all of the implementations, but the two that I looked at might not meet that requirement. Worst case is that perhaps you can get some ideas. Best case if that there might be another implementation out there somewhere that does what you need and you now have a starting point to find it.
The use of RPCs as an abstraction do not preclude the use of UDP as the transport layer: RMI is an RPC abstraction that generally used TCP under the hood (last time I looked).
I'd suggest just coding up a Java layer to talk your UDP protocol: you can use any one of many libraries to do it and you don't have to discard all your existing work. If you want to wrap an RPC layer around your protocol no reason why you can't do that: create a login method that sends the login UDP packet and receives the appropriate response and returns it.
If it's a remotely serious project, you should probably take a look at Netty.
It's a great library for developing networked systems, has a lot of proven production usage and is well suited for things like TCP or UDP client-server communication. I wouldn't go reinventing this wheel unless you really have to :-)
As a bonus they have some good examples and documentation too.

Java - Framework to "APIzize" any class and make it available on TCP?

I have an application where both the backend and the frontend are built in Java. The backend provides some functionalities like accessing the DB, etc. While the frontend built in Struts calls those functions.
I'm looking for a way to make any Java class easily callable on TCP, ideally in my mind this could be done by extending a specific class, let's say:
public class MyClass extends ThisIsAnAPI
making in this way all the public functions callable on a network protocol.
With such a framework the frontend could be easily implemented in other languages, like Ruby (On Rails), by making network requests to the backend APIs written in Java and exposed on TCP.
Any tips?
If you are likely to go to a JavaScript/Ajax UI then I would take the time to expose the backend as RESTful services. Using JAX/RS this is a matter of a few lines of a code and some annotations and an interface.
If you are staying pure Java, it's pretty trivial these days to turn a POJO into a remotely callable EJB: just a couple of annotations.
It may sound like overkill, but in terms of effort and cost (given a free app server such as WebSphere CE or JBoss) it's not that big a deal. However if you don't go for EJBs then you need to look at two big issues:
Security. You've got some TCP-callable services. How sensitive are those services? Do they need authentication and authorisation? You can all too easily open up sensitive databases to the whole company or even the internet.
Resilience and Scaling. How will you manage failure scenarios? EJBs exposed via RMI/IIOP can be clusterd and hence you can scale and deal with errors. If you start with a technology capable of doing that, even if you don't need the functionality right now, you are well placed for the future.
I would start with RMI which is designed to do this. You create an interface which the client uses and the server implements.
Try Hessian, which is a low-level TCP protocol also having bindings for several other platforms, so you will get C#/C++/Flash/... for free. I think it is a bit easier to work with compared to RMI.
If you need more portability for the future, consider exposing POJOs via SOAP/REST (most WS stacks have this ability, only few extra annotations are needed if any).
You might want to take a look at JMS. It's quite high level and easy to use, but you need to run a message broker. It's a bit of a different architecture to point-to-point communication.
As several persons have mentioned RMI you can look up spring which have support for this and I have myself used successfully. http://static.springsource.org/spring/docs/2.0.x/reference/remoting.html

Which Java RMI/RPC/IPC technology should I use?

I'm developing a Java application that consists of a server and a client (possibly multiple clients in future) which may run on different hosts.
For communication between these two I currently use a custom protocol which consists of JSON messages that are sent over network sockets and that are converted back to Java Bean objects on both sides. However the more complex the application gets I notice that this method doesn't meet my standards and is too complex.
I'm looking for a well established, possibly standardized alternative.
I've looked at Remote Method Invocation (RMI) but read that the protocol is slow (big network overhead).
The technology I'm looking for should be lightweight (protocol and library wise), robust, maybe support compression (big plus if it does!), maybe support encryption, well document and well established (e.g. an Apache project). It should be as easy as calling a method on a remote object with RMI but without its disadvantages.
What can you recommend?
Avro is an Apache project that is designed for cross-language RPC (see Thrift for its spiritual predecessor). It is fairly new (less than two years old), so it isn't as well-established as RMI, for example. You should still give it a chance, though; large projects like Cassandra are moving to Avro. Avro is also a sub-project under Hadoop and has been receiving healthy support from that community.
It designed to be fast and support multiple languages, so you will probably need to introduce another step during compilation in which you translate an Avro IDL file into Java, although it isn't strictly necessary. The rest is typical RPC.
One nice thing about Avro is that its transport layers are independent of how data is represented. For example, it comes with various "transceivers" (their base communication class) for raw sockets, HTTP, and even local intra-process calls. HTTPS and SASL transceivers can provide security.
For representing data, there are encoders and decoders of various types, although the default BinaryEncoder generally suffices since Hadoop, Cassandra, etc... focus on efficiency. There is also a JsonEncoder in case you find that useful.
This really all depends on what kind of compatibility you require between client and server. CORBA is a well established and standardized way of communicating between different languages, but it requires a bit more effort to use than Java RMI. If the clients are running from some external, untrusted source, then an HTTP based protocol makes more sense. If you follow a REST approach, then it becomes easier to scale out later as you need to add more servers.
If both client and server are Java, and they are running within a trusted network, RMI meets your requirements for being "well established". Performance overhead of RMI is exaggerated, but very early versions did not pool connections.
If you're willing to toss away both "well established" and "standardized", you can use Dirmi as a substitute for RMI. It's faster, easier, has more features, and it doesn't have the firewall problems RMI has. Like RMI, it supports TLS (encryption), but neither supports built-in compression.
Whatever you choose, beware of lock-in. Try to design your server such that the remote access layer is a thin layer over the core code. This allows you to easily support multiple protocols, perhaps at the same time.
Mybe CORBA?
Would you consider HTTP/REST?
If so, you can leverage something like a Tomcat/Spring, and still support all the requirements you listed ( robust, lightweight, well documented, well established )
The RPC based protocols are simply antiquated.
Seriously, unless you're doing a web app that already requires the web baggage, you really do want RMI or, even better, CORBA. I recommend JacORB (www.jacorb.org).
Ignore general claims of slow/fast and perform your own performance tests.
Keep in mind that a software project is successful because it performs the useful function for which it was designed and intended, not because it uses the latest cool buzzword tech.
Good luck.
Apache MINA library for client-server communication and EJB3 will suit best

Categories

Resources