Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

[ssl_requirement plugin] add unit tests and ssl_allowed option (for a…

…ctions that optionally support SSL)
  • Loading branch information...
commit aa2dded823f8a9b378c22ba0159971508918928a 1 parent 79ded84
Jamis Buck authored November 15, 2005
29  README
... ...
@@ -1,11 +1,9 @@
1 1
 SSL Requirement
2 2
 ===============
3 3
 
4  
-SSL requirement adds a declarative way of specifying that certain actions should
5  
-only be allowed to run under SSL, and if they're accessed without it, they should
6  
-be redirected.
7  
-
8  
-The methods are: account_url, account_host, and account_domain.
  4
+SSL requirement adds a declarative way of specifying that certain actions
  5
+should only be allowed to run under SSL, and if they're accessed without it,
  6
+they should be redirected.
9 7
 
10 8
 Example:
11 9
 
@@ -15,6 +13,7 @@ Example:
15 13
 
16 14
   class AccountController < ApplicationController
17 15
     ssl_required :signup, :payment
  16
+    ssl_allowed :index
18 17
     
19 18
     def signup
20 19
       # Non-SSL access will be redirected to SSL
@@ -23,14 +22,22 @@ Example:
23 22
     def payment
24 23
       # Non-SSL access will be redirected to SSL
25 24
     end
  25
+
  26
+    def index
  27
+      # This action will work either with or without SSL
  28
+    end
  29
+
  30
+    def other
  31
+      # SSL access will be redirected to non-SSL
  32
+    end
26 33
   end
27 34
   
28  
-You can overwrite the protected method ssl_required? to rely on other things than
29  
-just the declarative specification. Say, only premium accounts get SSL.
  35
+You can overwrite the protected method ssl_required? to rely on other things
  36
+than just the declarative specification. Say, only premium accounts get SSL.
30 37
 
31  
-P.S.: Beware when you include the SslRequirement module. At the time of inclusion,
32  
-it'll add the before_filter that validates the declarations. Some times you'll want to
33  
-run other before_filters before that. They should then be declared ahead of including
34  
-this module.
  38
+P.S.: Beware when you include the SslRequirement module. At the time of
  39
+inclusion, it'll add the before_filter that validates the declarations. Some
  40
+times you'll want to run other before_filters before that. They should then be
  41
+declared ahead of including this module.
35 42
 
36 43
 Copyright (c) 2005 David Heinemeier Hansson, released under the MIT license
10  lib/ssl_requirement.rb
@@ -29,6 +29,10 @@ module ClassMethods
29 29
     def ssl_required(*actions)
30 30
       write_inheritable_array(:ssl_required_actions, actions)
31 31
     end
  32
+
  33
+    def ssl_allowed(*actions)
  34
+      write_inheritable_array(:ssl_allowed_actions, actions)
  35
+    end
32 36
   end
33 37
   
34 38
   protected
@@ -36,9 +40,15 @@ def ssl_required(*actions)
36 40
     def ssl_required?
37 41
       (self.class.read_inheritable_attribute(:ssl_required_actions) || []).include?(action_name.to_sym)
38 42
     end
  43
+    
  44
+    def ssl_allowed?
  45
+      (self.class.read_inheritable_attribute(:ssl_allowed_actions) || []).include?(action_name.to_sym)
  46
+    end
39 47
 
40 48
   private
41 49
     def ensure_proper_protocol
  50
+      return true if ssl_allowed?
  51
+
42 52
       if ssl_required? && !request.ssl?
43 53
         redirect_to "https://" + request.host + request.request_uri
44 54
         return false
98  test/ssl_requirement_test.rb
... ...
@@ -0,0 +1,98 @@
  1
+begin
  2
+  require 'action_controller'
  3
+rescue LoadError
  4
+  if ENV['ACTIONCONTROLLER_PATH'].nil?
  5
+    abort <<MSG
  6
+Please set the ACTIONCONTROLLER_PATH environment variable to the directory
  7
+containing the action_controller.rb file.
  8
+MSG
  9
+  else
  10
+    $LOAD_PATH.unshift << ENV['ACTIONCONTROLLER_PATH']
  11
+    begin
  12
+      require 'action_controller'
  13
+    rescue LoadError
  14
+      abort "ActionController could not be found."
  15
+    end
  16
+  end
  17
+end
  18
+
  19
+require 'action_controller/test_process'
  20
+require 'test/unit'
  21
+require "#{File.dirname(__FILE__)}/../lib/ssl_requirement"
  22
+
  23
+ActionController::Base.logger = nil
  24
+ActionController::Routing::Routes.reload rescue nil
  25
+
  26
+class SslRequirementController < ActionController::Base
  27
+  include SslRequirement
  28
+  
  29
+  ssl_required :a, :b
  30
+  ssl_allowed :c
  31
+  
  32
+  def a
  33
+    render :nothing => true
  34
+  end
  35
+  
  36
+  def b
  37
+    render :nothing => true
  38
+  end
  39
+  
  40
+  def c
  41
+    render :nothing => true
  42
+  end
  43
+  
  44
+  def d
  45
+    render :nothing => true
  46
+  end
  47
+end
  48
+
  49
+class SslRequirementTest < Test::Unit::TestCase
  50
+  def setup
  51
+    @controller = SslRequirementController.new
  52
+    @request    = ActionController::TestRequest.new
  53
+    @response   = ActionController::TestResponse.new
  54
+  end
  55
+  
  56
+  def test_required_without_ssl
  57
+    assert_not_equal "on", @request.env["HTTPS"]
  58
+    get :a
  59
+    assert_response :redirect
  60
+    assert_match %r{^https://}, @response.headers['location']
  61
+    get :b
  62
+    assert_response :redirect
  63
+    assert_match %r{^https://}, @response.headers['location']
  64
+  end
  65
+  
  66
+  def test_required_with_ssl
  67
+    @request.env['HTTPS'] = "on"
  68
+    get :a
  69
+    assert_response :success
  70
+    get :b
  71
+    assert_response :success
  72
+  end
  73
+
  74
+  def test_disallowed_without_ssl
  75
+    assert_not_equal "on", @request.env["HTTPS"]
  76
+    get :d
  77
+    assert_response :success
  78
+  end
  79
+
  80
+  def test_disallowed_with_ssl
  81
+    @request.env['HTTPS'] = "on"
  82
+    get :d
  83
+    assert_response :redirect
  84
+    assert_match %r{^http://}, @response.headers['location']
  85
+  end
  86
+
  87
+  def test_allowed_without_ssl
  88
+    assert_not_equal "on", @request.env["HTTPS"]
  89
+    get :c
  90
+    assert_response :success
  91
+  end
  92
+
  93
+  def test_allowed_with_ssl
  94
+    @request.env['HTTPS'] = "on"
  95
+    get :c
  96
+    assert_response :success
  97
+  end
  98
+end

0 notes on commit aa2dded

Please sign in to comment.
Something went wrong with that request. Please try again.