Skip to content

Commit

Permalink
Adding the functional middleware
Browse files Browse the repository at this point in the history
  • Loading branch information
Jacques Crocker committed Nov 14, 2010
1 parent e065ba5 commit 58b7231
Show file tree
Hide file tree
Showing 9 changed files with 118 additions and 7 deletions.
1 change: 0 additions & 1 deletion Gemfile
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
source :rubygems

gem "rake"
gemspec
7 changes: 3 additions & 4 deletions Gemfile.lock
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,12 @@ PATH
remote: .
specs:
heroscale (0.0.1)
rack (~> 1.0)

GEM
remote: http://rubygems.org/
specs:
diff-lcs (1.1.2)
rack (1.2.1)
json (1.4.6)
rake (0.8.7)
rspec (2.1.0)
rspec-core (~> 2.1.0)
Expand All @@ -24,6 +23,6 @@ PLATFORMS

DEPENDENCIES
heroscale!
rack (~> 1.0)
rake
json
rake (~> 0.8.7)
rspec (~> 2.0)
1 change: 0 additions & 1 deletion Rakefile
Original file line number Diff line number Diff line change
Expand Up @@ -39,5 +39,4 @@ Rake::RDocTask.new do |rdoc|
rdoc.rdoc_files.include("lib/**/*.rb")
end


task :default => :spec
3 changes: 2 additions & 1 deletion heroscale.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,9 @@ Gem::Specification.new do |s|
"README.md"
]

s.add_runtime_dependency 'rack', '~> 1.0'
s.add_development_dependency "json"
s.add_development_dependency "rspec", "~> 2.0"
s.add_development_dependency 'rake', '~> 0.8.7'
end


Expand Down
2 changes: 2 additions & 0 deletions lib/heroscale.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
require 'heroscale/middleware'
require 'heroscale/railtie' if defined?(Rails::Railtie)
29 changes: 29 additions & 0 deletions lib/heroscale/middleware.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
module Heroscale

# simple Rack Middleware that adds a hook to return the heroku env info
class Middleware
def initialize(app)
@app = app
end

def call(env)
if env["PATH_INFO"] == "/heroscale/status"
queue_wait_time = env['HTTP_X_HEROKU_QUEUE_WAIT_TIME']
queue_depth = env['HTTP_X_HEROKU_QUEUE_DEPTH']
dynos_in_use = env['HTTP_X_HEROKU_DYNOS_IN_USE']

if queue_wait_time and queue_depth and dynos_in_use
# format the response on heroku
res = %|{"heroku": true, "queue_wait_time": #{queue_wait_time.to_i}, "queue_depth": #{queue_depth.to_i}, "dynos_in_use": #{dynos_in_use.to_i}}|
else
res = %|{"heroku": false}|
end

[ 200, {'Content-Type' => 'application/json'}, res]
else
@app.call(env)
end
end

end
end
Empty file added lib/heroscale/railtie.rb
Empty file.
74 changes: 74 additions & 0 deletions spec/heroscale/middleware_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
require "spec_helper"
require "heroscale"

require "json"

describe Heroscale::Middleware do

# this is our original app (that the middleware is wrapping around)
let(:orig_app) do
lambda do |env|
[ 200, {'Content-Type' => 'application/json'}, "HELLO!"]
end
end

# this is our app with the middleware attached
let(:app) do
Heroscale::Middleware.new orig_app
end

def heroku_request(opts = {})
app.call({
'PATH_INFO' => '/heroscale/status',
'HTTP_X_HEROKU_QUEUE_WAIT_TIME' => (opts[:wait] || 100),
'HTTP_X_HEROKU_QUEUE_DEPTH' => (opts[:depth] || 0),
'HTTP_X_HEROKU_DYNOS_IN_USE' => (opts[:dynos] || 1)
})
end

context "when querying on a heroku instance" do
before(:each) do
@rack_response = heroku_request(:wait => 100, :depth => 5, :dynos => 12)
@json = JSON.parse(@rack_response.last)
end

it "should return the 'heroku' field that tells that we're on heroku" do
@json["heroku"].should == true
end

it "should return the 'queue_wait_time' field that tells us the queue wait time" do
@json["queue_wait_time"].should == 100
end

it "should return the 'queue_depth' field that tells us the current queue depth" do
@json["queue_depth"].should == 5
end

it "should return the 'dynos_in_use' field that tells us the current heroku dynos in use" do
@json["dynos_in_use"].should == 12
end

end

context "when not quering the status link" do
it "should return the original app's response" do
app.call({}).last.should == "HELLO!"
app.call({"PATH_INFO" => "/"}).last.should == "HELLO!"
app.call({"PATH_INFO" => "/heroscale/"}).last.should == "HELLO!"
app.call({"PATH_INFO" => "/heroscale/status2"}).last.should == "HELLO!"
end

end

context "when query while not on a heroku instance" do
before(:each) do
@rack_response = app.call({"PATH_INFO" => "/heroscale/status"})
@json = JSON.parse(@rack_response.last)
end

it "should return the 'heroku' field telling use we're not on heroku" do
@json["heroku"].should == false
end
end

end
8 changes: 8 additions & 0 deletions spec/spec_helper.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
require 'bundler/setup'
require "rspec"

$:.unshift "lib"

Rspec.configure do |config|
config.color_enabled = true
end

0 comments on commit 58b7231

Please sign in to comment.