Rails as a filtering reverse proxy - ruby-on-rails

I'd like to gradually transition an app from old java to a new rails app. The data flow would look like
user -> browser -> new rails -> old java
That is, the new rails app would function as a reverse proxy to the old app, and the user would never be the wiser of the original app.
As more functionality is migrated to the rails app, the java app would become used less and less.
I'm familiar with the Net::HTTP classes for requesting resources from the other app, but most examples are overly simplified, and don't facilitate the transition. A full featured gem would be able to
handle common HTTP verbs
pass and retain cookies
rewrite HTML from the old app (for instance, the old app will have
href="/something/foo.html", and the new app would have
"/newpath/bar.html")
have configurable session awareness (associate a sessionID on the
java app with the rails session, such that if you delete the rails session,
it could callback to the java app with a logout)
Performance is not a big concern.
Any pointers to such a gem? It would probably be classified as some sort of reverse proxy, man -in-the-middle, filter, etc

I would suggest not doing this in Rails itself, but rather doing it in directly in your webserver (e.g. Apache)
I have been working on a large project to migrate a Java website to Ruby, and have been using Apache mod_rewrite and mod_proxy for this purpose.
So the flow was
user -> browser -> apache -> passenger or Tomcat
Using modules within Apache itself meant that we did not need to use any of the Rails stack (and associated CPU/memory/threads). It also allowed us to meet one of your requirements to ensure that "the user would never be the wiser of the original app"
Session management is the only tricky part to this; I introduced a cookie that the Java and Rails app could both read, and used the presence of the cookie to tell Ruby or Java if the user was logged in. This way, Ruby and Java did not need to try to manage each other's sessions.
Hope some of that proves helpful?

Related

How to run multiple Rails versions for a single website / project?

I've inherited a Rails 3.2 production environment which is 'humming' away nicely.
The client now wants another major piece of work doing but I want to do it in Rails 5. The web address would be the same for both the old site and the new project. The new project would be additional functionality which would be accessed via the old site.
Any one know of a way of keeping the old site running whilst I develop and deliver the new work via Rails 5? Eventually if this all works then I get the opportunity to migrate the old site to Rails 5. However for the moment I need to serve up both Rails 3.2 and Rails 5 from the same site.
It's possible to do what you describe with a reverse proxy, e.g. nginx, configured to serve from different web servers based on different paths on the same host. This answer has some details on how to do that. We would need to know how your website is hosted in order to give more details on exactly how to do that.
However, there are other concerns that come up when you start separating your apps which you may not have considered. For example, if your website allows users to log in, do you want them to still be logged in when they visit the new site? To do so transparently will require sharing the session cookie, which this post describes a bit (you'll need to use the same secret key for both apps, or use a remote session store like Memcached). I'm not sure if it'll work properly when shared between Rails 3.2 and 5, though.
As a final note, breaking up your monolithic app into a distributed system is never a decision to take lightly. It would likely end up being less work, and less overall architectural overhead, to simply invest the time in upgrading from 3.2 -> 4.0 -> 4.2 -> 5.0.
Personally I wouldn't touch that old app and its server, especially if the client is happy. Deploying the new app to a new server or a container service like heroku is something you should consider.

How to use Nodejs and Ruby on Rails together?

I really like Ruby on Rails but I have also developed in node js. Currently I'm making a web app which has chat functionality that could have 30 people in it. For that I want to use node js.
I have never done this, I'm confused on how's traffic divided between app. How is the state shared between apps for example how would I share the user session will I have to hit the database for every request.
My first recommendation is to not split a web app between two separate server platforms. It overly complicates the project and isn't necessary at all.
That being said, if it must be done, you could use one of the platforms as the 'main' one and the other one for API endpoints stationed at localhost:some-port-number. This way, if you were in the main platform (Rails let's say), you could request data via the node.js API by redirecting it to whatever IP address (make it a local IP) that node is running on.
Again, I recommend against this. But that's one solution if it must be done.

Communication between Rails apps

I have built two rails apps that need to communicate and send files between each other. For example one rails app would send a request to view a table in the other apps' database. The other app would then render json of that table and send it back. I would also like one app to send a text file stored in its public directory to the other app's public directory.
I have never done anything like this so I don't even know where to begin. Any help would be appreciated. Thanks!
You requirement is common for almost all the web apps irrespective of rails, Communicating with each other is required by most modern web apps. But there is a small understanding that you need to get hold on,
Web sites should not directly access each others internal data (such as tables), (even if they are build by the same language (in this case Rails) by the same developer),
That is where the web-services comes in to play, So you should expose your data through web services so that not only rails application can consume that, but also any app that knows how to consume a web service will get benefit.
Coming back to your question with Rails, rails supports REST web services out of the box, So do some googling about web services, REST web services with rails
HTH
As a starting point, look at ActiveResource.
Railscast
docs
Message queuing systems such as RabbitMQ may be used to communicate things internally between different apps such as a "mailer" app and a main "hub" application.
Alternatively, you can use a shared connection to something like redis stick things onto a "queue" in one app and read them for processing from the other.
In recent Rails versions, it is rather easy to develop API only applications. In the Rails core master, there was even a special application type for these apps briefly (until it got yanked again). But it is still available as a plugin and probably one day becomes actually part of Rails core again. See http://blog.wyeworks.com/2012/4/20/rails-for-api-applications-rails-api-released for more information.
To actually develop and maintain the API of the backend service and make sure both backend and frontend have the same understanding of the resources, you can use ROAR which is great way to build great APIs.
Generally, you should fully define your backend application with an API. Trying to be clever and to skip some of the design steps will only bring you headaches in the long run...
Check out Morpheus. It lets you create RESTful services and use familiar ActiveRecord syntax in the client.

How do I manage sessions in a hybrid Ruby/GWT system?

I currently have a Ruby on Rails system, and there are plans to port it to GWT. Before we do this, the powers that be want to have a proof of concept with part of the site being written in GWT to show that GWT can use and display the current content. The flow of data in the GWT portion of the system is as follows:
Client sends an RPC call to the GWT server
Server receives RPC call, then makes an equivalent Ajax request to the Rails system
Server generates a Java object from the result of the Ajax request, passes it back to client
The issue I'm running into now is managing user session data across both systems. We only have 1 Tomcat instance, and that has its own type of sessions, and then our Ruby system uses ActiveRecordStore to store session data in the database.
The problem here is that when the Tomcat system talks with the Ruby system, if the GWT client has made a login request, the last user to log in from the GWT system has all outgoing Ajax requests being performed in the Rails system as if they're the current user since the Tomcat system looks like a single client to Rails.
Anyways, how can I make it such that if a user begins a session with the Tomcat system, the Ruby system will be aware of this and have an equivalent session so that even though the Tomcat server is a single client to it, the Rails system is aware of the fact that many different users are communicating with it from that single client.
I think the best way to solve this would be to use cookies instead of a database to store the session. Rails supports this natively, actually it's the default cookie store for some time now. The cookie itself is signed by a server secret to prevent user tampering. I think the Rails implementation uses Ruby marshaling to dump/load the data so you might have to implement it in Java, or you can implement your own cookie manager on both sides using the same idea.
It is also possible to just use the Ruby code from JRuby in your Java application.
I don't know about RoR, but in most web technologies sessions are maintained using cookies. If you preserve the cookies (for a given user) across multiple calls from your Java server to your RoR instance, you should be all good.

Should I be using Rails or Ruby for this website application? How?

I'm very new to web programming (or actually, very old to it, since the last time I messed with the web was HTML 1.1), but now need to deploy a web application quickly. It seems like every time I turn around, there's new acronyms and technologies to learn (JSON, XMLRPC, GWT, Javascript, Rails, etc).
Here's what my app must do:
Given a username and password, authenticate (easy enough, everything does that, apparently).
Allow the user to upload a large glob of data for processing.
Process that data.
Allow the user to download their processed data.
I've already got Java scripts and a database for handling the data. On one machine, I can run a series of command-line programs to process an incoming datablock and put the results back into a mysql database. That is already present and working.
I want to construct a web front-end to this task, using these existing and tested methods. I'm currently leaning to this approach:
Have two machines, a database machine and a web server. That approach allows for later scalability, if necessary, but also requires that I can't assume that the programs that I use to access the data and manipulate it are locally stored.
Use a Ruby DRb application to create a server and a client. The client would pass data to the server which would in turn call these applications.
Use some other Ruby interface to interact with the DRb for the web frontend.
Here's my problem: it looks like most Ruby applications for the web automatically try to build some kind of local database. All the Rails tutorials I've found start with making your own database and interacting with that, which is exactly what I don't want to do.
Is Rails the right technology for me, or using Ruby DRb? Is there some other technology I should be exploring?
If Rails or Ruby is the Right Thing here, what should I be looking at? I already have the Programming Ruby book, and have used that for some of the backend stuff as well as getting basic DRb stuff working.
Sounds like Rails might be a bit heavyweight for your situation. Perhaps Sinatra might be a better fit? It's an ultra-lightweight framework: a hello world app might look something like:
require 'sinatra'
get '/' do
"Hello World!"
end
Rails is fine. You can have development and test databases on your local machine and the production database on a remote machine. It doesn't have to be the web server. Get a copy of Agile Web Development with Rails. It'll teach you all you need to know.

Resources