opensesame 0.0.2 → 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/README.md +9 -8
- data/app/assets/stylesheets/open_sesame/{application.css → opensesame.css} +0 -1
- data/app/assets/stylesheets/open_sesame/{welcome.css.scss → welcome.css} +50 -1
- data/app/controllers/open_sesame/application_controller.rb +1 -1
- data/app/controllers/open_sesame/sessions_controller.rb +22 -5
- data/app/helpers/open_sesame/application_helper.rb +1 -1
- data/app/views/layouts/open_sesame/application.html.erb +1 -2
- data/config/routes.rb +2 -2
- data/lib/open_sesame/configuration.rb +10 -13
- data/lib/open_sesame/engine.rb +21 -22
- data/lib/open_sesame/failure/app.rb +10 -0
- data/lib/open_sesame/failure/devise_app.rb +17 -0
- data/lib/open_sesame/github_auth.rb +9 -0
- data/lib/open_sesame/github_warden.rb +26 -0
- data/lib/open_sesame/{controller_helper.rb → helpers/controller_helper.rb} +2 -1
- data/lib/open_sesame/{view_helper.rb → helpers/view_helper.rb} +4 -3
- data/lib/open_sesame/member.rb +65 -0
- data/lib/open_sesame/version.rb +2 -1
- data/lib/open_sesame.rb +16 -4
- data/spec/dummy/app/views/home/index.html.erb +3 -1
- data/spec/dummy/config/initializers/opensesame.rb +16 -2
- data/spec/dummy/config/initializers/session_store.rb +1 -1
- data/spec/dummy/config/initializers/wrap_parameters.rb +1 -1
- data/spec/dummy/config/routes.rb +1 -1
- data/spec/dummy/db/development.sqlite3 +0 -0
- data/spec/dummy/log/development.log +135 -6
- data/spec/dummy/log/test.log +41874 -530
- data/spec/dummy/tmp/cache/assets/C09/2F0/sprockets%2F76045b33d436a11b0156b36a91560651 +0 -0
- data/spec/dummy/tmp/cache/assets/C54/300/sprockets%2Fb83307a70e6040f817087f997dc73122 +0 -0
- data/spec/dummy/tmp/cache/assets/CAA/920/sprockets%2Ff2904820584f0723f5ab256dcf1a9225 +0 -0
- data/spec/dummy/tmp/cache/assets/CC2/790/sprockets%2F020f956f67983c52c9889ac9801ca4b4 +0 -0
- data/spec/dummy/tmp/cache/assets/CD8/370/sprockets%2F357970feca3ac29060c1e3861e2c0953 +0 -0
- data/spec/dummy/tmp/cache/assets/CEC/240/sprockets%2Fdec29f626939d38247d1745e057c6ab2 +0 -0
- data/spec/dummy/tmp/cache/assets/D0C/2A0/sprockets%2F04922c120a656b333dd5fcd28c9f8f53 +0 -0
- data/spec/dummy/tmp/cache/assets/D12/EF0/sprockets%2F98d5a511dcf32074eef97c372f294a20 +0 -0
- data/spec/dummy/tmp/cache/assets/D32/A10/sprockets%2F13fe41fee1fe35b49d145bcc06610705 +0 -0
- data/spec/dummy/tmp/cache/assets/D38/DB0/sprockets%2Fe4441bec5b04f6a4ad4bf7056181558e +0 -0
- data/spec/dummy/tmp/cache/assets/D45/CE0/sprockets%2F6c1b76a50b27d5e7485d41cef59eb427 +0 -0
- data/spec/dummy/tmp/cache/assets/D4E/1B0/sprockets%2Ff7cbd26ba1d28d48de824f0e94586655 +0 -0
- data/spec/dummy/tmp/cache/assets/D5A/EA0/sprockets%2Fd771ace226fc8215a3572e0aa35bb0d6 +0 -0
- data/spec/dummy/tmp/cache/assets/D60/400/sprockets%2F1f456ac6c7c736a4407ead0832adb42c +0 -0
- data/spec/dummy/tmp/cache/assets/D72/880/sprockets%2Fe5615e8c12de3dbb5626aee43388cb39 +0 -0
- data/spec/dummy/tmp/cache/assets/DDC/400/sprockets%2Fcffd775d018f68ce5dba1ee0d951a994 +0 -0
- data/spec/dummy/tmp/cache/assets/DDD/910/sprockets%2Ff8ed9a8d47ac232db51e9c7adb8377a9 +0 -0
- data/spec/dummy/tmp/cache/assets/E04/890/sprockets%2F2f5173deea6c795b8fdde723bb4b63af +0 -0
- data/spec/dummy/tmp/cache/assets/E09/D90/sprockets%2Fd85890cff0dcafde74d69601baae198e +0 -0
- data/spec/dummy/tmp/cache/assets/E3C/B20/sprockets%2Fde9e6fc28cd2dfe38cc53fd0455b5b9e +0 -0
- data/spec/dummy/tmp/cache/sass/19921c2f5bb8eaa817ba254313d0f93dbf32f1df/opensesame.css.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/19921c2f5bb8eaa817ba254313d0f93dbf32f1df/opensesame_bootstrap.css.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_accordion.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_alerts.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_breadcrumbs.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_button-groups.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_buttons.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_carousel.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_close.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_code.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_component-animations.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_dropdowns.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_forms.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_grid.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_hero-unit.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_labels-badges.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_layouts.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_mixins.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_modals.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_navbar.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_navs.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_pager.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_pagination.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_popovers.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_progress-bars.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_reset.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_scaffolding.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_sprites.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_tables.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_thumbnails.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_tooltip.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_type.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_utilities.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_variables.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/bf8de80767f3492905bcacdfb6abfd679aef3272/_wells.scssc +0 -0
- data/spec/dummy/tmp/cache/sass/c0430781249a04c227e0b0aca38159d7478590b1/_bootstrap.scssc +0 -0
- data/spec/dummy/tmp/capybara/{capybara-201205020845417136358435.html → capybara-201208201553167621643394.html} +2 -0
- data/spec/lib/open_sesame/configuration_spec.rb +0 -40
- data/spec/lib/open_sesame/github_auth_spec.rb +30 -0
- data/spec/lib/open_sesame/github_warden_spec.rb +44 -0
- data/spec/lib/open_sesame/member_spec.rb +51 -0
- data/spec/lib/open_sesame/sessions_spec.rb +23 -8
- data/spec/lib/open_sesame_spec.rb +7 -2
- data/spec/spec_helper.rb +0 -3
- data/spec/support/capybara.rb +24 -0
- data/spec/support/request_helpers.rb +61 -0
- data/spec/support/vcr.rb +22 -0
- data/spec/vcr/member/retrieves_attributes_from_github.yml +46 -0
- data/spec/vcr/member/returns_nil_if_no_github_member_found.yml +46 -0
- data/spec/vcr/member/serialize_from_session_returns_member_from_given_member_id.yml +89 -0
- data/spec/vcr/member/serialize_into_session_returns_given_member_id_in_array.yml +46 -0
- data/spec/vcr/session/allows_auto_login.yml +132 -0
- data/spec/vcr/session/enforces_opensesame_login.yml +132 -0
- data/spec/vcr/session/skips_auto_login_if_just_logged_out.yml +175 -0
- data/spec/vcr/session/tries_auto_login_and_ends_up_on_opensesame_page_after_failure.yml +46 -0
- metadata +239 -41
- data/app/assets/javascripts/open_sesame/application.js +0 -15
- data/app/assets/stylesheets/open_sesame/opensesame_bootstrap.css.scss +0 -8
- data/lib/open_sesame/failure_app.rb +0 -14
- data/spec/dummy/tmp/capybara/capybara-201205020845084431324775.html +0 -14
- data/spec/dummy/tmp/capybara/capybara-201205020846032430049397.html +0 -14
- data/spec/dummy/tmp/capybara/capybara-201205020848165144257335.html +0 -26
- data/spec/dummy/tmp/capybara/capybara-201205020849371072293414.html +0 -26
- data/spec/dummy/tmp/capybara/capybara-201205020851069360249571.html +0 -26
data/README.md
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# OpenSesame
|
|
2
2
|
|
|
3
|
-
OpenSesame is a [Warden](https://github.com/hassox/warden) strategy for providing "walled garden" authentication for access to Rack-based applications via Omniauth. For example, your company has internal apps and/or staging enviroments for multiple projects and you want something better than HTTP basic auth.
|
|
3
|
+
OpenSesame is a [Warden](https://github.com/hassox/warden) strategy for providing "walled garden" authentication for access to Rack-based applications via Omniauth. The intent is protect the visibility of your app from the outside world. For example, your company has internal apps and/or staging enviroments for multiple projects and you want something better than HTTP basic auth.
|
|
4
4
|
|
|
5
|
-
Enter OpenSesame. To authenticate, OpenSesame currently uses Omniauth and the Github API to require that a user is both logged in to Github and a member of the
|
|
5
|
+
Enter OpenSesame. To authenticate, OpenSesame currently uses Omniauth and the Github API to require that a user is both logged in to Github and a member of the Github organization for which OpenSesame is configured.
|
|
6
6
|
|
|
7
7
|
## Usage
|
|
8
8
|
|
|
@@ -11,23 +11,24 @@ In your Gemfile:
|
|
|
11
11
|
$ gem "opensesame"
|
|
12
12
|
|
|
13
13
|
Register your application(s) with Github for OAuth access. For each application, you need a name, the site url,
|
|
14
|
-
and a callback for OAuth. The OmniAuth-Github OAuth strategy used under the hood will expect the callback at mount path + '/
|
|
14
|
+
and a callback for OAuth. The OmniAuth-Github OAuth strategy used under the hood will expect the callback at mount path + '/github/callback'. So the development version of your client application might be registered as:
|
|
15
15
|
|
|
16
16
|
Name: MyApp - local
|
|
17
17
|
URL: http://localhost:3000
|
|
18
|
-
Callback URL: http://localhost:3000/
|
|
18
|
+
Callback URL: http://localhost:3000/opensesame/github/callback
|
|
19
19
|
|
|
20
20
|
Configure OpenSesame:
|
|
21
21
|
|
|
22
22
|
```ruby
|
|
23
|
-
# Rails config/initializers/opensesame.rb
|
|
23
|
+
# Rails config/initializers/opensesame.rb
|
|
24
24
|
|
|
25
25
|
require 'opensesame'
|
|
26
26
|
|
|
27
27
|
OpenSesame.configure do |config|
|
|
28
|
-
config.
|
|
28
|
+
config.enable Rails.env.staging?
|
|
29
|
+
config.github ENV['GITHUB_APP_ID'], ENV['GITHUB_SECRET']
|
|
29
30
|
config.organization 'challengepost'
|
|
30
|
-
config.mounted_at '/
|
|
31
|
+
config.mounted_at '/opensesame'
|
|
31
32
|
end
|
|
32
33
|
```
|
|
33
34
|
|
|
@@ -36,5 +37,5 @@ Mount OpenSesame in your Rails routes.rb:
|
|
|
36
37
|
```ruby
|
|
37
38
|
# Rails config/routes.rb
|
|
38
39
|
|
|
39
|
-
mount OpenSesame::Engine => "/
|
|
40
|
+
mount OpenSesame::Engine => "/opensesame", :as => "opensesame"
|
|
40
41
|
```
|
|
@@ -49,4 +49,53 @@ pre, code { font-family: monospace, sans-serif; font-size: 1em; color:#080; }
|
|
|
49
49
|
.field input { border: 1px solid #CCC; }
|
|
50
50
|
|
|
51
51
|
#grant, #deny { padding: 5px 0px }
|
|
52
|
-
.green { color: green }
|
|
52
|
+
.green { color: green }
|
|
53
|
+
|
|
54
|
+
.btn {
|
|
55
|
+
display: inline-block;
|
|
56
|
+
padding: 4px 10px 4px;
|
|
57
|
+
margin-bottom: 0;
|
|
58
|
+
font-size: 13px;
|
|
59
|
+
line-height: 18px;
|
|
60
|
+
color: #333;
|
|
61
|
+
text-align: center;
|
|
62
|
+
text-shadow: 0 1px 1px rgba(255, 255, 255, 0.75);
|
|
63
|
+
vertical-align: middle;
|
|
64
|
+
cursor: pointer;
|
|
65
|
+
background-color: whiteSmoke;
|
|
66
|
+
background-image: -ms-linear-gradient(top, white, #E6E6E6);
|
|
67
|
+
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(white), to(#E6E6E6));
|
|
68
|
+
background-image: -webkit-linear-gradient(top, white, #E6E6E6);
|
|
69
|
+
background-image: -o-linear-gradient(top, white, #E6E6E6);
|
|
70
|
+
background-image: linear-gradient(top, white, #E6E6E6);
|
|
71
|
+
background-image: -moz-linear-gradient(top, white, #E6E6E6);
|
|
72
|
+
background-repeat: repeat-x;
|
|
73
|
+
border: 1px solid #CCC;
|
|
74
|
+
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
|
|
75
|
+
border-bottom-color: #B3B3B3;
|
|
76
|
+
-webkit-border-radius: 4px;
|
|
77
|
+
-moz-border-radius: 4px;
|
|
78
|
+
border-radius: 4px;
|
|
79
|
+
filter: progid:dximagetransform.microsoft.gradient(startColorstr='#ffffff', endColorstr='#e6e6e6', GradientType=0);
|
|
80
|
+
filter: progid:dximagetransform.microsoft.gradient(enabled=false);
|
|
81
|
+
-webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 2px rgba(0, 0, 0, 0.05);
|
|
82
|
+
-moz-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 2px rgba(0, 0, 0, 0.05);
|
|
83
|
+
box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 2px rgba(0, 0, 0, 0.05);
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
.btn-large {
|
|
87
|
+
font-size: 20px;
|
|
88
|
+
font-weight: normal;
|
|
89
|
+
padding: 14px 24px;
|
|
90
|
+
margin-right: 10px;
|
|
91
|
+
-webkit-border-radius: 6px;
|
|
92
|
+
-moz-border-radius: 6px;
|
|
93
|
+
border-radius: 6px;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
.content-header {
|
|
97
|
+
border-bottom: 1px solid #ccc;
|
|
98
|
+
margin-bottom: 1em;
|
|
99
|
+
|
|
100
|
+
}
|
|
101
|
+
.content-header h1 { font-size: 24px; }
|
|
@@ -14,14 +14,12 @@ module OpenSesame
|
|
|
14
14
|
end
|
|
15
15
|
|
|
16
16
|
def create
|
|
17
|
-
|
|
18
|
-
flash[:success] = "Welcome!"
|
|
17
|
+
login_opensesame
|
|
19
18
|
redirect_to main_app.root_url
|
|
20
19
|
end
|
|
21
20
|
|
|
22
21
|
def destroy
|
|
23
|
-
|
|
24
|
-
flash[:notice] = "Logged out!"
|
|
22
|
+
logout_opensesame
|
|
25
23
|
redirect_to main_app.root_url
|
|
26
24
|
end
|
|
27
25
|
|
|
@@ -33,19 +31,38 @@ module OpenSesame
|
|
|
33
31
|
|
|
34
32
|
def attempt_auto_authenticate
|
|
35
33
|
return unless attempt_auto_access?
|
|
36
|
-
|
|
34
|
+
|
|
37
35
|
redirect_to identity_request_path(OpenSesame.auto_access_provider)
|
|
38
36
|
end
|
|
39
37
|
|
|
40
38
|
def attempt_auto_access?
|
|
39
|
+
return false if just_logged_out?
|
|
41
40
|
return false unless OpenSesame.auto_access_provider.present?
|
|
42
41
|
attempts = session[:opensesame_auto_access_attempt].to_i
|
|
43
42
|
session[:opensesame_auto_access_attempt] = attempts + 1
|
|
44
43
|
attempts < 1
|
|
45
44
|
end
|
|
46
45
|
|
|
46
|
+
def just_logged_out?
|
|
47
|
+
!!session[:opensesame_logged_out].tap do
|
|
48
|
+
session[:opensesame_logged_out] = nil
|
|
49
|
+
end
|
|
50
|
+
end
|
|
51
|
+
|
|
47
52
|
def clear_auto_attempt!
|
|
48
53
|
session[:opensesame_auto_access_attempt] = nil
|
|
49
54
|
end
|
|
55
|
+
|
|
56
|
+
def login_opensesame
|
|
57
|
+
warden.authenticate!(:scope => :opensesame)
|
|
58
|
+
flash[:success] = "Welcome!"
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def logout_opensesame
|
|
62
|
+
warden.logout(:opensesame)
|
|
63
|
+
session[:opensesame_logged_out] = 1
|
|
64
|
+
flash[:notice] = "Logged out!"
|
|
65
|
+
end
|
|
66
|
+
|
|
50
67
|
end
|
|
51
68
|
end
|
|
@@ -2,8 +2,7 @@
|
|
|
2
2
|
<html>
|
|
3
3
|
<head>
|
|
4
4
|
<title>OpenSesame</title>
|
|
5
|
-
<%= stylesheet_link_tag "open_sesame/
|
|
6
|
-
<%= javascript_include_tag "open_sesame/application" %>
|
|
5
|
+
<%= stylesheet_link_tag "open_sesame/opensesame", :media => "all" %>
|
|
7
6
|
<%= csrf_meta_tags %>
|
|
8
7
|
</head>
|
|
9
8
|
<body>
|
data/config/routes.rb
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
OpenSesame::Engine.routes.draw do
|
|
2
2
|
root :to => "sessions#new"
|
|
3
3
|
|
|
4
|
-
match '
|
|
5
|
-
match '/
|
|
4
|
+
match '/:provider/callback', :to => 'sessions#create'
|
|
5
|
+
match '/:provider/failure', :to => 'sessions#failure'
|
|
6
6
|
match '/login', :to => 'sessions#new', :as => :sign_in
|
|
7
7
|
match '/logout', :to => 'sessions#destroy', :as => :sign_out
|
|
8
8
|
end
|
|
@@ -1,9 +1,10 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
1
2
|
module OpenSesame
|
|
2
3
|
class ConfigurationError < RuntimeError; end
|
|
3
4
|
|
|
4
5
|
class Configuration
|
|
5
|
-
CONFIGURABLE_ATTRIBUTES = [:organization_name, :mount_prefix, :github_client,
|
|
6
|
-
:enabled, :
|
|
6
|
+
CONFIGURABLE_ATTRIBUTES = [:organization_name, :mount_prefix, :github_client,
|
|
7
|
+
:enabled, :full_host, :auto_access_provider]
|
|
7
8
|
attr_accessor *CONFIGURABLE_ATTRIBUTES
|
|
8
9
|
|
|
9
10
|
def mounted_at(mount_prefix)
|
|
@@ -26,24 +27,20 @@ module OpenSesame
|
|
|
26
27
|
self.auto_access_provider = provider
|
|
27
28
|
end
|
|
28
29
|
|
|
29
|
-
def enable_if(conditional)
|
|
30
|
-
self.enabled = nil
|
|
31
|
-
self.enable_clause = lambda { conditional }
|
|
32
|
-
end
|
|
33
|
-
|
|
34
30
|
def enable!
|
|
35
|
-
self.enable_clause = nil
|
|
36
31
|
self.enabled = true
|
|
37
32
|
end
|
|
38
33
|
|
|
39
34
|
def disable!
|
|
40
|
-
self.enable_clause = nil
|
|
41
35
|
self.enabled = false
|
|
42
36
|
end
|
|
43
37
|
|
|
38
|
+
def enable(enabled)
|
|
39
|
+
self.enabled = !!enabled
|
|
40
|
+
end
|
|
41
|
+
|
|
44
42
|
def enabled?
|
|
45
|
-
|
|
46
|
-
(!self.enable_clause.nil? && self.enable_clause.call)
|
|
43
|
+
self.enabled
|
|
47
44
|
end
|
|
48
45
|
|
|
49
46
|
def configure
|
|
@@ -70,14 +67,14 @@ module OpenSesame
|
|
|
70
67
|
# config/initializers/open_sesame.rb
|
|
71
68
|
OpenSesame.configure do |config|
|
|
72
69
|
config.organization 'challengepost'
|
|
73
|
-
config.mounted_at '/
|
|
70
|
+
config.mounted_at '/opensesame'
|
|
74
71
|
config.github ENV['CAPITAN_GITHUB_KEY'], ENV['CAPITAN_GITHUB_SECRET']
|
|
75
72
|
end
|
|
76
73
|
|
|
77
74
|
When you register the app, make sure to point the callback url to
|
|
78
75
|
the engine mountpoint + /auth/github/callback. For example, if your
|
|
79
76
|
development app is on http://localhost:3000 and you're mounting
|
|
80
|
-
the OpenSesame::Engine at '/
|
|
77
|
+
the OpenSesame::Engine at '/opensesame', your github
|
|
81
78
|
callback url should be:
|
|
82
79
|
|
|
83
80
|
http://localhost:3000/auth/github/callback
|
data/lib/open_sesame/engine.rb
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
|
|
1
|
+
# encoding: utf-8
|
|
2
2
|
|
|
3
3
|
module OpenSesame
|
|
4
4
|
class Engine < ::Rails::Engine
|
|
@@ -9,41 +9,40 @@ module OpenSesame
|
|
|
9
9
|
end
|
|
10
10
|
|
|
11
11
|
ActiveSupport.on_load(:action_controller) do
|
|
12
|
-
include OpenSesame::ControllerHelper
|
|
12
|
+
include OpenSesame::Helpers::ControllerHelper
|
|
13
13
|
end
|
|
14
14
|
|
|
15
15
|
ActiveSupport.on_load(:action_view) do
|
|
16
|
-
include OpenSesame::ViewHelper
|
|
16
|
+
include OpenSesame::Helpers::ViewHelper
|
|
17
17
|
end
|
|
18
18
|
|
|
19
19
|
initializer "opensesame.middleware", :after => :load_config_initializers do |app|
|
|
20
|
-
OpenSesame.
|
|
20
|
+
if OpenSesame.enabled?
|
|
21
|
+
require 'open_sesame/github_warden'
|
|
21
22
|
|
|
22
|
-
|
|
23
|
+
app.config.assets.precompile += ['opensesame.css']
|
|
23
24
|
|
|
24
|
-
|
|
25
|
-
configure do |config|
|
|
26
|
-
config.path_prefix = '/auth'
|
|
27
|
-
config.full_host = OpenSesame.full_host if OpenSesame.full_host
|
|
28
|
-
end
|
|
25
|
+
OpenSesame.configuration.validate!
|
|
29
26
|
|
|
30
|
-
|
|
31
|
-
|
|
27
|
+
app.config.middleware.use OpenSesame::GithubAuth,
|
|
28
|
+
OpenSesame.github_client[:id],
|
|
29
|
+
OpenSesame.github_client[:secret],
|
|
30
|
+
:path_prefix => OpenSesame.mount_prefix
|
|
32
31
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
32
|
+
if defined?(Devise)
|
|
33
|
+
Devise.setup do |config|
|
|
34
|
+
config.warden do |manager|
|
|
35
|
+
manager.default_strategies(:opensesame_github, :scope => :opensesame)
|
|
36
|
+
manager.failure_app = OpenSesame::Failure::DeviseApp.new
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
else
|
|
40
|
+
app.config.middleware.use ::Warden::Manager do |manager|
|
|
36
41
|
manager.default_strategies(:opensesame_github, :scope => :opensesame)
|
|
37
|
-
manager.failure_app = OpenSesame::
|
|
42
|
+
manager.failure_app = OpenSesame::Failure::App.new
|
|
38
43
|
end
|
|
39
44
|
end
|
|
40
|
-
else
|
|
41
|
-
app.config.middleware.use Warden::Manager do |manager|
|
|
42
|
-
manager.default_strategies(:opensesame_github, :scope => :opensesame)
|
|
43
|
-
manager.failure_app = lambda { |env| OpenSesame::SessionsController.action(:new).call(env)}
|
|
44
|
-
end
|
|
45
45
|
end
|
|
46
|
-
|
|
47
46
|
end
|
|
48
47
|
end
|
|
49
48
|
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
require 'devise'
|
|
3
|
+
module OpenSesame
|
|
4
|
+
module Failure
|
|
5
|
+
class DeviseApp < ::Devise::Delegator
|
|
6
|
+
|
|
7
|
+
def call(env)
|
|
8
|
+
if (env['warden.options'] && (scope = env["warden.options"][:scope]) && scope == :opensesame)
|
|
9
|
+
OpenSesame::SessionsController.action(:new).call(env)
|
|
10
|
+
else
|
|
11
|
+
super
|
|
12
|
+
end
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
end
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
require 'warden'
|
|
3
|
+
|
|
4
|
+
module OpenSesame
|
|
5
|
+
class GithubWarden < ::Warden::Strategies::Base
|
|
6
|
+
|
|
7
|
+
def valid?
|
|
8
|
+
auth_hash && auth_hash["provider"] == "github"
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def authenticate!
|
|
12
|
+
if member = OpenSesame::Member.find(auth_hash["uid"])
|
|
13
|
+
success! member
|
|
14
|
+
else
|
|
15
|
+
fail 'Sorry, you do not have access'
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
def auth_hash
|
|
20
|
+
request.env['omniauth.auth']
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
::Warden::Strategies.add(:opensesame_github, OpenSesame::GithubWarden)
|
|
@@ -1,14 +1,15 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
1
2
|
module OpenSesame
|
|
2
|
-
module ViewHelper
|
|
3
|
+
module Helpers::ViewHelper
|
|
3
4
|
|
|
4
5
|
def login_image_link_to(provider)
|
|
5
|
-
link_to identity_request_path(provider), class
|
|
6
|
+
link_to identity_request_path(provider), :class => "btn btn-large" do
|
|
6
7
|
image_tag("open_sesame/#{provider}_64.png") + "<br/><span>#{provider}</span>".html_safe
|
|
7
8
|
end
|
|
8
9
|
end
|
|
9
10
|
|
|
10
11
|
def identity_request_path(provider)
|
|
11
|
-
[OpenSesame.mount_prefix,
|
|
12
|
+
[OpenSesame.mount_prefix, provider].join('/')
|
|
12
13
|
end
|
|
13
14
|
|
|
14
15
|
end
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
require "octokit"
|
|
3
|
+
|
|
4
|
+
module OpenSesame
|
|
5
|
+
class Member
|
|
6
|
+
|
|
7
|
+
def self.organization_name
|
|
8
|
+
OpenSesame.organization_name
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def self.find(member_id)
|
|
12
|
+
return nil unless member_id.present?
|
|
13
|
+
attributes = organization_members.detect { |member| member.id.to_s == member_id.to_s }
|
|
14
|
+
return nil unless attributes.present?
|
|
15
|
+
new(attributes)
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
def self.organization_members
|
|
19
|
+
github_api.organization_members(organization_name)
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def self.github_api
|
|
23
|
+
@github_api ||= Octokit.new
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
def self.lazy_attr_reader(*attrs)
|
|
27
|
+
attrs.each do |attribute|
|
|
28
|
+
class_eval do
|
|
29
|
+
define_method(attribute) do
|
|
30
|
+
@attributes[attribute.to_s] || @attributes[attribute] # allow string or symbol access
|
|
31
|
+
end
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
def self.serialize_into_session(member)
|
|
37
|
+
[member.id]
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
def self.serialize_from_session(*args)
|
|
41
|
+
id = args.shift
|
|
42
|
+
find(id)
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
attr_accessor :attributes
|
|
46
|
+
lazy_attr_reader :id, :login, :avatar_url, :gravatar_id, :url
|
|
47
|
+
|
|
48
|
+
def initialize(attributes = {})
|
|
49
|
+
@attributes = attributes
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def id
|
|
53
|
+
@attributes["id"]
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
def organization_name
|
|
57
|
+
self.class.organization_name
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
def ==(other)
|
|
61
|
+
super || (other.class == self.class && other.id == self.id)
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
end
|
|
65
|
+
end
|
data/lib/open_sesame/version.rb
CHANGED
data/lib/open_sesame.rb
CHANGED
|
@@ -2,11 +2,23 @@ module OpenSesame
|
|
|
2
2
|
extend self
|
|
3
3
|
|
|
4
4
|
autoload :Configuration, 'open_sesame/configuration'
|
|
5
|
-
autoload :
|
|
6
|
-
autoload :
|
|
5
|
+
autoload :GithubAuth, 'open_sesame/github_auth'
|
|
6
|
+
autoload :GithubWarden, 'open_sesame/github_warden'
|
|
7
7
|
autoload :FailureApp, 'open_sesame/failure_app'
|
|
8
|
+
autoload :Member, 'open_sesame/member'
|
|
8
9
|
|
|
9
|
-
|
|
10
|
+
module Helpers
|
|
11
|
+
autoload :ControllerHelper, 'open_sesame/helpers/controller_helper'
|
|
12
|
+
autoload :ViewHelper, 'open_sesame/helpers/view_helper'
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
module Failure
|
|
16
|
+
autoload :App, 'open_sesame/failure/app'
|
|
17
|
+
autoload :DeviseApp, 'open_sesame/failure/devise_app'
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
@to_configuration = Configuration::CONFIGURABLE_ATTRIBUTES + [:to => :configuration]
|
|
21
|
+
delegate *@to_configuration
|
|
10
22
|
delegate :enabled?, :to => :configuration
|
|
11
23
|
|
|
12
24
|
mattr_accessor :configuration
|
|
@@ -18,4 +30,4 @@ module OpenSesame
|
|
|
18
30
|
end
|
|
19
31
|
end
|
|
20
32
|
|
|
21
|
-
require "open_sesame/engine"
|
|
33
|
+
require "open_sesame/engine" if defined?(Rails)
|
|
@@ -1,7 +1,21 @@
|
|
|
1
1
|
require "opensesame"
|
|
2
2
|
|
|
3
|
+
app_id = ENV['GITHUB_APP_ID']
|
|
4
|
+
secret = ENV['GITHUB_SECRET']
|
|
5
|
+
|
|
6
|
+
if app_id.nil?
|
|
7
|
+
puts "Setting app_id to dummy string"
|
|
8
|
+
app_id = 'dummy_app_id'
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
if secret.nil?
|
|
12
|
+
puts "Setting secret to dummy string"
|
|
13
|
+
secret = 'dummy_secret'
|
|
14
|
+
end
|
|
15
|
+
|
|
3
16
|
OpenSesame.configure do |config|
|
|
17
|
+
config.enable true
|
|
4
18
|
config.organization 'challengepost'
|
|
5
|
-
config.mounted_at '/
|
|
6
|
-
config.github
|
|
19
|
+
config.mounted_at '/opensesame'
|
|
20
|
+
config.github app_id, secret
|
|
7
21
|
end
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# Be sure to restart your server when you modify this file.
|
|
2
2
|
|
|
3
|
-
Dummy::Application.config.session_store :cookie_store, key
|
|
3
|
+
Dummy::Application.config.session_store :cookie_store, :key => '_dummy_session'
|
|
4
4
|
|
|
5
5
|
# Use the database for sessions instead of the cookie-based default,
|
|
6
6
|
# which shouldn't be used to store highly confidential information
|
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
|
|
6
6
|
# Enable parameter wrapping for JSON. You can disable this by setting :format to an empty array.
|
|
7
7
|
ActiveSupport.on_load(:action_controller) do
|
|
8
|
-
wrap_parameters format
|
|
8
|
+
wrap_parameters :format => [:json]
|
|
9
9
|
end
|
|
10
10
|
|
|
11
11
|
# Disable root element in JSON by default.
|
data/spec/dummy/config/routes.rb
CHANGED
|
Binary file
|