Deployment without downtime (Unicorn)

Hi,

I wonder how is it possible to deploy the app (Rails) without first
request slowdown and basically downtime.

With MRI Ruby we can just use Unicorn that keeps serving requests until
new process is spawned.

How can we do the same with JRuby?

Cheers,
Dmytrii
http://www.ApproachE.com

Both TorqueBox and Trinidad support hot deployment, which means a new
version of your app can be booted without restarting the web server.
This means that a deploy requires fewer resources and your app can start
serving requests much quicker.
http://torquebox.org/news/2011/01/20/capistrano-and-torquebox/
https://github.com/trinidad/trinidad

But Kirk supports zero downtime deploys, which theoretically means you
won’t miss a single request:
https://github.com/strobecorp/kirk

On 20/12/2011, at 2:31 PM, Joe K. wrote:

Both TorqueBox and Trinidad support hot deployment, which means a new version of
your app can be booted without restarting the web server. This means that a
deploy requires fewer resources and your app can start serving requests much
quicker.
http://torquebox.org/news/2011/01/20/capistrano-and-torquebox/
https://github.com/trinidad/trinidad

But Kirk supports zero downtime deploys, which theoretically means you won’t
miss a single request:
https://github.com/strobecorp/kirk

That’s awesome. Good to know all those options.

I will dig deeper into details of all of the servers there.

Maybe you can also suggest how to “switch” the embedded database (neo4j)
between the 2 apps (from old to the newly deployed one)?
The DB is only accessible from a single process.

It’s a tough issue, but interesting would people have to say here :slight_smile:

On Dec 20, 2011, at 4:17 AM, Dmytrii N. wrote:

That’s awesome. Good to know all those options.

I will dig deeper into details of all of the servers there.

Maybe you can also suggest how to “switch” the embedded database (neo4j) between
the 2 apps (from old to the newly deployed one)?
The DB is only accessible from a single process.

If the limitation on neo4j is indeed per-process, there’s no issue.
Under TorqueBox, Trinidad, and I assume Kirk, the new version of the
application is running in the same process as the old version.

Depending on how you’re accessing the database, it might be useful to
separate the embedded neo4j into a separate application that runs as a
TorqueBox Service
(http://torquebox.org/documentation/current/services.html). This would
allow the rest of your application to be restarted, deployed, and
undeployed without having to stop or switch the embedded database. The
main application would access the embedded database either via messaging
or just directly calling methods on the running service class instance.

Ben

Kirk works if you don’t want to use JRuby’s 1.9 mode. Kirk doesn’t
respect
that option.

However MWarren’s fork does: https://github.com/mwarren/kirk

One system that works very well is to run two instances of your app on
each server, each under different ports. One port is your live app,
the other is the one you deploy to. This lets you test your app in
your production environment without making it live. When you want to
make it live, tell your load balancer to switch what port it’s sending
traffic to.

Been using this system for a couple years now in production and I’d
never go back to ‘live’ deploys.

Chris

If the limitation on neo4j is indeed per-process, there’s no issue. Under
TorqueBox, Trinidad, and I assume Kirk, the new version of the application is
running in the same process as the old version.

Depending on how you’re accessing the database, it might be useful to separate
the embedded neo4j into a separate application that runs as a TorqueBox Service
(http://torquebox.org/documentation/current/services.html). This would allow the
rest of your application to be restarted, deployed, and undeployed without having
to stop or switch the embedded database. The main application would access the
embedded database either via messaging or just directly calling methods on the
running service class instance.

Thanks Ben for the explanation.

How does hot deploy works generally? Is it using some Java
infrastructure?
What happens if an old thread/app still uses the resources that new app
does? When is it going to die off?

On 21/12/2011, at 8:17, snacktime [email protected] wrote:

One system that works very well is to run two instances of your app on
each server, each under different ports. One port is your live app,
the other is the one you deploy to. This lets you test your app in
your production environment without making it live. When you want to
make it live, tell your load balancer to switch what port it’s sending
traffic to.

Unfortunately this won’t work for me because of the embedded database.

On 21/12/2011, at 1:52, Robert R. [email protected] wrote:

Kirk works if you don’t want to use JRuby’s 1.9 mode. Kirk doesn’t respect that
option.

However MWarren’s fork does: https://github.com/mwarren/kirk

I do need 1.9 support :frowning:
I wonder why the MWarren’s fork isn’t merged into the upstream.

On Dec 20, 2011, at 4:33 PM, Dmytrii N. wrote:

If the limitation on neo4j is indeed per-process, there’s no issue. Under
TorqueBox, Trinidad, and I assume Kirk, the new version of the application is
running in the same process as the old version.

Depending on how you’re accessing the database, it might be useful to separate
the embedded neo4j into a separate application that runs as a TorqueBox Service
(http://torquebox.org/documentation/current/services.html). This would allow the
rest of your application to be restarted, deployed, and undeployed without having
to stop or switch the embedded database. The main application would access the
embedded database either via messaging or just directly calling methods on the
running service class instance.

Thanks Ben for the explanation.

How does hot deploy works generally? Is it using some Java infrastructure?
What happens if an old thread/app still uses the resources that new app does?
When is it going to die off?

I can’t speak for Trinidad or Kirk - only TorqueBox. Hot deploy used in
this sense just means that you can redeploy your application without
restarting the server. What happens in TorqueBox when we redeploy an
application is we destroy all the JRuby runtimes for the running
application and create new ones for the updated application with the new
code.

Specifically in TorqueBox, we have the service concept for the use-case
where you need lifecycle control (notification of start/stop) of some
long-running process or resource usage. This is why I recommended a
service for controlling access to your embedded database. If that
service is part of your Ruby application, when the application is
deployed its start method will be called and when the application is
undeployed its stop method will be called, allowing you to do any
necessary cleanup with open resources.

Outside of TorqueBox, you’ll need to find some other way to close any
open resource handles when your application gets shut down to get
replaced by the new version. Ruby’s at_exit hooks can be used for this -
JRuby calls them when stopping a runtime.

Ben

This forum is not affiliated to the Ruby language, Ruby on Rails framework, nor any Ruby applications discussed here.

| Privacy Policy | Terms of Service | Remote Ruby Jobs