Permalink
Browse files

fixes #1

  • Loading branch information...
coldnebo committed Jun 14, 2012
1 parent 29cfd85 commit e520edf9cf471c0304a352f67c8c8469f5e15390
Showing with 39 additions and 6 deletions.
  1. +2 −1 .gitignore
  2. +1 −1 Gemfile
  3. +2 −2 Rakefile
  4. +15 −1 lib/condi.rb
  5. +19 −1 test/test_condi.rb
View
@@ -3,4 +3,5 @@
Gemfile.lock
doc
coverage
-pkg
+pkg
+.rvmrc
View
@@ -4,7 +4,7 @@
source :rubygems
group :test do
- #gem 'ruby-debug19'
+ #gem 'debugger'
gem 'simplecov', :require => false
gem 'mocha'
gem 'actionpack', '2.3.11'
View
@@ -3,7 +3,7 @@ require 'rake/testtask'
require 'yard'
-PKG_VERSION = '0.0.6'
+PKG_VERSION = '0.0.7'
SRC_FILES = Dir.glob('lib/**/*')
TST_FILES = Dir.glob('test/**/*')
@@ -25,7 +25,7 @@ spec = Gem::Specification.new do |s|
s.description = "Conditional UI predicates for Rails - a clean and simple approach to separate business logic from your views and models."
s.name = 'condi'
- s.date = '2011-12-14'
+ s.date = '2012-06-14'
s.summary = "Condi"
s.authors = ["Larry Kyrala"]
s.email = 'larry.kyrala@gmail.com'
View
@@ -30,10 +30,24 @@ module Condi
# @param [Proc] block {} or do...end block.
# @note A *synonym* is an alias for defining methods that return values other than true or false.
# @note You are not required to end a predicate with a question mark, however it is conventional in Ruby to do so.
+ # @note Predicates can only be called during the request context they are defined in, otherwise a RuntimeError is raised. This restriction prevents the associated closures from inadvertently leaking previous request data when the controller classes are cached (i.e. in production).
# @see the full example in the <a href="index.html">README</a>.
def predicate(method_name, &block)
self.class.instance_eval do
- define_method(method_name, &block)
+ # this is the request id at the moment the predicate is defined
+ request_id = eval("request.object_id",block.binding)
+
+ define_method(method_name) do |*args|
+ # this is the request id at the moment the predicate is called
+ check_request_id = request.object_id
+
+ # if they don't match, raise an error!
+ unless check_request_id == request_id
+ #debugger
+ raise RuntimeError, "predicate '#{method_name}' cannot be called outside of the request it was defined in (#{request_id}). please redefine the predicate in this request (#{check_request_id}).", caller(2)
+ end
+ block.call(*args)
+ end
helper_method(method_name)
end
end
View
@@ -9,7 +9,7 @@
require 'ostruct'
-#require 'ruby-debug'
+#require 'debugger'
class CondiTest < Test::Unit::TestCase
@@ -142,4 +142,22 @@ def test_synonyms
end
+ # fix for https://github.com/coldnebo/condi/issues/1
+ def test_lifespan
+ @controller_instance.request = Object.new # simulate the first request
+ @controller_instance.instance_eval do
+ predicate(:always_be_true?) { true }
+ end
+
+ assert @controller_instance.respond_to?(:always_be_true?)
+ assert @controller_instance.always_be_true? == true
+
+ @controller_instance.request = Object.new # simulate a second request
+
+ # now, if a view calls the predicate, we shouldn't allow it!
+ assert_raise RuntimeError do
+ @controller_instance.always_be_true?
+ end
+ end
+
end

0 comments on commit e520edf

Please sign in to comment.