Skip to content

Commit

Permalink
Use Sinatra::base.register, factor out param store
Browse files Browse the repository at this point in the history
  • Loading branch information
skade committed Jan 11, 2012
1 parent 29e4349 commit 655d02b
Show file tree
Hide file tree
Showing 4 changed files with 108 additions and 105 deletions.
71 changes: 3 additions & 68 deletions lib/gon-sinatra.rb
@@ -1,77 +1,12 @@
require 'sinatra'
require 'gon/sinatra/store'
require 'gon/sinatra/helpers'
require 'gon/sinatra/rabl'

module Gon
module Sinatra
class << self
def all_variables
@request_env[:gon]
end

def clear
@request_env[:gon] = {}
end

def request_env=(environment)
@request_env = environment
@request_env[:gon] ||= {}
end

def request_env
if defined?(@request_env)
return @request_env
end
end

def request
@request_id if defined? @request_id
end

def request=(request_id)
@request_id = request_id
end

def method_missing(m, *args, &block)
if ( m.to_s =~ /=$/ )
if public_methods.include? m.to_s[0..-2].to_sym
raise "You can't use Gon public methods for storing data"
end
set_variable(m.to_s.delete('='), args[0])
else
get_variable(m.to_s)
end
end

def get_variable(name)
@request_env[:gon][name]
end

def set_variable(name, value)
@request_env[:gon][name] = value
end

def rabl(view_path, options = {})
unless options[:instance]
raise ArgumentError.new("You should pass :instance in options: :instance => self")
end

rabl_data = Gon::Sinatra::Rabl.parse_rabl(view_path, options[:instance])

if options[:as]
set_variable(options[:as].to_s, rabl_data)
elsif rabl_data.is_a? Hash
rabl_data.each do |key, value|
set_variable(key, value)
end
else
set_variable('rabl', rabl_data)
end
end

def jbuilder(view_path, options = {})
raise NoMethodError.new("Not available for sinatra")
end
def self.registered(base)
base.helpers(Gon::Sinatra::GonHelpers, Gon::Sinatra::Helpers)
end
end
end
15 changes: 5 additions & 10 deletions lib/gon/sinatra/helpers.rb
Expand Up @@ -4,8 +4,8 @@ module Gon
module Sinatra
module Helpers
def include_gon(options = {})
if Gon::Sinatra.request_env && Gon::Sinatra.all_variables.present?
data = Gon::Sinatra.all_variables
if gon.all_variables.present?
data = gon.all_variables
namespace = options[:namespace] || 'gon'
script = "<script>window." + namespace + " = {};"
unless options[:camel_case]
Expand All @@ -27,14 +27,9 @@ def include_gon(options = {})

module GonHelpers
def gon
if !Gon::Sinatra.request_env || Gon::Sinatra.request != request.object_id
Gon::Sinatra.request = request.object_id
Gon::Sinatra.request_env = request.env
end
Gon::Sinatra
env["gon"] ||= Gon::Sinatra::Store.new({})
@gon = env["gon"]
end
end
end
end

Sinatra::Base.helpers Gon::Sinatra::GonHelpers, Gon::Sinatra::Helpers
end
65 changes: 65 additions & 0 deletions lib/gon/sinatra/store.rb
@@ -0,0 +1,65 @@

module Gon
module Sinatra
class Store
attr_accessor :request

def initialize(variables)
@env = variables
end

def all_variables
@env
end

def clear
@env.clear
end

def method_missing(m, *args, &block)
if ( m.to_s =~ /=$/ )
if public_methods.include? m.to_s[0..-2].to_sym
raise "You can't use Gon public methods for storing data"
end
set_variable(m.to_s.delete('='), args[0])
else
get_variable(m.to_s)
end
end

def get_variable(name)
@env[name]
end
alias :get :get_variable

def set_variable(name, value)
@env[name] = value
end
alias :set :set_variable

def rabl(view_path, options = {})
raise Exception.new("You must require rabl to use the rabl method") unless defined? Rabl

unless options[:instance]
raise ArgumentError.new("You should pass :instance in options: :instance => self")
end

rabl_data = Gon::Sinatra::Rabl.parse_rabl(view_path, options[:instance])

if options[:as]
set_variable(options[:as].to_s, rabl_data)
elsif rabl_data.is_a? Hash
rabl_data.each do |key, value|
set_variable(key, value)
end
else
set_variable('rabl', rabl_data)
end
end

def jbuilder(view_path, options = {})
raise NoMethodError.new("Not available for sinatra")
end
end
end
end
62 changes: 35 additions & 27 deletions spec/gon/gon_spec.rb
@@ -1,60 +1,68 @@
# gon_spec_rb
require 'gon-sinatra'

class App < Sinatra::Base
register Gon::Sinatra
end

describe Gon::Sinatra, '#all_variables' do
def app
app = App.new!
app.env = {}
app
end

before(:each) do
Gon::Sinatra.request_env = {}
@gon = Gon::Sinatra::Store.new({})
end

it 'returns all variables in hash' do
Gon::Sinatra.a = 1
Gon::Sinatra.b = 2
Gon::Sinatra.c = Gon::Sinatra.a + Gon::Sinatra.b
Gon::Sinatra.c.should == 3
Gon::Sinatra.all_variables.should == {'a' => 1, 'b' => 2, 'c' => 3}
@gon.a = 1
@gon.b = 2
@gon.c = @gon.a + @gon.b
@gon.c.should == 3
@gon.all_variables.should == {'a' => 1, 'b' => 2, 'c' => 3}
end

it 'supports all data types' do
Gon::Sinatra.clear
Gon::Sinatra.int = 1
Gon::Sinatra.float = 1.1
Gon::Sinatra.string = 'string'
Gon::Sinatra.array = [ 1, 'string' ]
Gon::Sinatra.hash_var = { :a => 1, :b => '2'}
Gon::Sinatra.hash_w_array = { :a => [ 2, 3 ] }
Gon::Sinatra.klass = Hash
@gon.clear
@gon.int = 1
@gon.float = 1.1
@gon.string = 'string'
@gon.array = [ 1, 'string' ]
@gon.hash_var = { :a => 1, :b => '2'}
@gon.hash_w_array = { :a => [ 2, 3 ] }
@gon.klass = Hash
end

it 'output as js correct' do
Gon::Sinatra.clear
Gon::Sinatra.int = 1
Sinatra::Application.instance_methods.map(&:to_s).include?('include_gon').should == true
instance = app

instance.gon.int = 1
instance.methods.map(&:to_s).include?('include_gon').should == true

# TODO: Make it work
base = Sinatra::Base.new!
base.include_gon.should == "<script>window.gon = {};" +
"gon.int=1;" +
"</script>"
instance.include_gon.should == "<script>window.gon = {};" +
"gon.int=1;" +
"</script>"
end

it 'returns exception if try to set public method as variable' do
Gon::Sinatra.clear
lambda { Gon::Sinatra.all_variables = 123 }.should raise_error
@gon.clear
lambda { @gon.all_variables = 123 }.should raise_error
end

it 'should be threadsafe' do
instance1 = Sinatra::Base.new!
instance2 = Sinatra::Base.new!
instance1 = app()
instance2 = app()

instance1.gon.test = "foo"
instance2.gon.test = "bar"
instance1.gon.test.should == "foo"
end


it 'render json from rabl template' do
Gon::Sinatra.clear
@gon.clear
@objects = [1,2]
Gon::Sinatra.rabl 'spec/test_data/sample.rabl', :instance => self
Gon::Sinatra.objects.length.should == 2
Expand Down

0 comments on commit 655d02b

Please sign in to comment.