cops 0.2.0.6
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +20 -0
- data/README.rdoc +113 -0
- data/Rakefile +95 -0
- data/VERSION +1 -0
- data/app/controllers/blue_light_special/confirmations_controller.rb +76 -0
- data/app/controllers/blue_light_special/impersonations_controller.rb +44 -0
- data/app/controllers/blue_light_special/passwords_controller.rb +93 -0
- data/app/controllers/blue_light_special/sessions_controller.rb +76 -0
- data/app/controllers/blue_light_special/users_controller.rb +85 -0
- data/app/models/blue_light_special_mailer.rb +28 -0
- data/app/models/deliver_change_password_job.rb +19 -0
- data/app/models/deliver_welcome_job.rb +17 -0
- data/app/models/generic_mailer.rb +31 -0
- data/app/models/impersonation.rb +26 -0
- data/app/models/mimi_mailer.rb +30 -0
- data/app/views/generic_mailer/change_password.html.erb +9 -0
- data/app/views/generic_mailer/confirmation.html.erb +5 -0
- data/app/views/generic_mailer/welcome.html.erb +1 -0
- data/app/views/impersonations/index.html.erb +5 -0
- data/app/views/passwords/edit.html.erb +23 -0
- data/app/views/passwords/new.html.erb +15 -0
- data/app/views/sessions/new.html.erb +48 -0
- data/app/views/users/_form.html.erb +21 -0
- data/app/views/users/edit.html.erb +6 -0
- data/app/views/users/new.html.erb +6 -0
- data/app/views/users/show.html.erb +8 -0
- data/generators/blue_light_special/USAGE +1 -0
- data/generators/blue_light_special/blue_light_special_generator.rb +78 -0
- data/generators/blue_light_special/lib/insert_commands.rb +33 -0
- data/generators/blue_light_special/lib/rake_commands.rb +22 -0
- data/generators/blue_light_special/templates/README +20 -0
- data/generators/blue_light_special/templates/application.html.erb +50 -0
- data/generators/blue_light_special/templates/blue_light_special.rb +25 -0
- data/generators/blue_light_special/templates/blue_light_special.yml +45 -0
- data/generators/blue_light_special/templates/factories.rb +23 -0
- data/generators/blue_light_special/templates/migrations/create_users.rb +24 -0
- data/generators/blue_light_special/templates/migrations/update_users.rb +44 -0
- data/generators/blue_light_special/templates/style.css +31 -0
- data/generators/blue_light_special/templates/user.rb +3 -0
- data/generators/blue_light_special/templates/xd_receiver.html +10 -0
- data/generators/blue_light_special/templates/xd_receiver_ssl.html +10 -0
- data/generators/blue_light_special_admin/USAGE +1 -0
- data/generators/blue_light_special_admin/blue_light_special_admin_generator.rb +30 -0
- data/generators/blue_light_special_admin/lib/insert_commands.rb +33 -0
- data/generators/blue_light_special_admin/templates/README +16 -0
- data/generators/blue_light_special_admin/templates/app/controllers/admin/admin_controller.rb +14 -0
- data/generators/blue_light_special_admin/templates/app/controllers/admin/users_controller.rb +52 -0
- data/generators/blue_light_special_admin/templates/app/views/admin/users/_form.html.erb +25 -0
- data/generators/blue_light_special_admin/templates/app/views/admin/users/edit.html.erb +6 -0
- data/generators/blue_light_special_admin/templates/app/views/admin/users/index.html.erb +7 -0
- data/generators/blue_light_special_admin/templates/app/views/admin/users/new.html.erb +6 -0
- data/generators/blue_light_special_admin/templates/app/views/admin/users/show.html.erb +10 -0
- data/generators/blue_light_special_admin/templates/test/integration/admin/users_test.rb +201 -0
- data/generators/blue_light_special_tests/USAGE +1 -0
- data/generators/blue_light_special_tests/blue_light_special_tests_generator.rb +21 -0
- data/generators/blue_light_special_tests/templates/README +58 -0
- data/generators/blue_light_special_tests/templates/test/integration/edit_profile_test.rb +35 -0
- data/generators/blue_light_special_tests/templates/test/integration/facebook_test.rb +61 -0
- data/generators/blue_light_special_tests/templates/test/integration/impersonation_test.rb +39 -0
- data/generators/blue_light_special_tests/templates/test/integration/password_reset_test.rb +128 -0
- data/generators/blue_light_special_tests/templates/test/integration/sign_in_test.rb +66 -0
- data/generators/blue_light_special_tests/templates/test/integration/sign_out_test.rb +28 -0
- data/generators/blue_light_special_tests/templates/test/integration/sign_up_test.rb +47 -0
- data/lib/blue_light_special/authentication.rb +138 -0
- data/lib/blue_light_special/configuration.rb +34 -0
- data/lib/blue_light_special/extensions/errors.rb +6 -0
- data/lib/blue_light_special/extensions/rescue.rb +5 -0
- data/lib/blue_light_special/routes.rb +62 -0
- data/lib/blue_light_special/user.rb +279 -0
- data/lib/blue_light_special.rb +7 -0
- data/rails/init.rb +4 -0
- data/shoulda_macros/blue_light_special.rb +244 -0
- data/test/controllers/passwords_controller_test.rb +184 -0
- data/test/controllers/sessions_controller_test.rb +129 -0
- data/test/controllers/users_controller_test.rb +57 -0
- data/test/models/blue_light_special_mailer_test.rb +52 -0
- data/test/models/impersonation_test.rb +25 -0
- data/test/models/user_test.rb +213 -0
- data/test/rails_root/app/controllers/accounts_controller.rb +10 -0
- data/test/rails_root/app/controllers/application_controller.rb +6 -0
- data/test/rails_root/app/helpers/application_helper.rb +5 -0
- data/test/rails_root/app/helpers/confirmations_helper.rb +2 -0
- data/test/rails_root/app/helpers/passwords_helper.rb +2 -0
- data/test/rails_root/config/boot.rb +110 -0
- data/test/rails_root/config/environment.rb +22 -0
- data/test/rails_root/config/environments/development.rb +19 -0
- data/test/rails_root/config/environments/production.rb +1 -0
- data/test/rails_root/config/environments/test.rb +37 -0
- data/test/rails_root/config/initializers/inflections.rb +10 -0
- data/test/rails_root/config/initializers/mime_types.rb +5 -0
- data/test/rails_root/config/initializers/requires.rb +13 -0
- data/test/rails_root/config/initializers/time_formats.rb +4 -0
- data/test/rails_root/config/routes.rb +9 -0
- data/test/rails_root/public/dispatch.rb +10 -0
- data/test/rails_root/script/create_project.rb +52 -0
- data/test/rails_root/test/functional/accounts_controller_test.rb +23 -0
- data/test/test_helper.rb +21 -0
- metadata +212 -0
data/LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2009 Envy Labs LLC
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.rdoc
ADDED
@@ -0,0 +1,113 @@
|
|
1
|
+
= Blue Light Special
|
2
|
+
|
3
|
+
Blue Light Special is a derivative from Thoughtbot's
|
4
|
+
{Clearance}[http://github.com/thoughtbot/clearance] gem. It's a highly
|
5
|
+
opinionated starting point for many of our projects at Envy Labs.
|
6
|
+
|
7
|
+
In addition to the basic email and password authentication provided by
|
8
|
+
Clearance, a default Blue Light Special installation includes:
|
9
|
+
|
10
|
+
* optional support for authenticating with Facebook Connect, using {mini_fb}[http://github.com/appoxy/mini_fb]
|
11
|
+
|
12
|
+
* a simple role system with built-in support for admin users
|
13
|
+
|
14
|
+
* the ability for an admin to impersonate any other user
|
15
|
+
|
16
|
+
* use of {MadMimi}[http://madmimi.com/r/b8599b9343f82e3bc30984ca4f3fea3f] for sending notification emails
|
17
|
+
|
18
|
+
* {delayed_job}[http://github.com/tobi/delayed_job] for sending emails in the background
|
19
|
+
|
20
|
+
* a basic application layout and stylesheet
|
21
|
+
|
22
|
+
== Setup
|
23
|
+
|
24
|
+
After installing the Blue Light Special gem, require it in your Rails app and run
|
25
|
+
the blue_light_special generator.
|
26
|
+
|
27
|
+
In your config/environment.rb:
|
28
|
+
|
29
|
+
config.gem 'blue_light_special'
|
30
|
+
|
31
|
+
Run the generators and migrate your database:
|
32
|
+
|
33
|
+
script/generate blue_light_special
|
34
|
+
script/generate delayed_job
|
35
|
+
rake db:migrate
|
36
|
+
|
37
|
+
You'll also want to take a look at Blue Light Special's configuration options
|
38
|
+
in config/blue_light_special.yml.
|
39
|
+
|
40
|
+
== Tests
|
41
|
+
|
42
|
+
Blue Light Special can optionally generate integration tests that cover all
|
43
|
+
of its basic features. These tests require {shoulda}[http://github.com/thoughtbot/shoulda],
|
44
|
+
{factory_girl}[http://github.com/thoughtbot/factory_girl], {webrat}[http://github.com/brynary/webrat],
|
45
|
+
and {fakeweb}[http://github.com/chrisk/fakeweb]. To install the tests:
|
46
|
+
|
47
|
+
script/generate blue_light_special_tests
|
48
|
+
|
49
|
+
After the generator runs, you'll see instructions for updating
|
50
|
+
test/test_helper.rb to include some helper methods that the tests require.
|
51
|
+
You can also use these helper methods in your own integration tests whenever
|
52
|
+
you need to sign a user in or out.
|
53
|
+
|
54
|
+
== Administration Interface
|
55
|
+
|
56
|
+
The final Blue Light Special generator builds a very simple administration
|
57
|
+
interface for your app. This allows admins to manage and impersonate users,
|
58
|
+
and it can be used as a starting point for building a more elaborate admin
|
59
|
+
interface. If you'd like to generate the admin interface, run:
|
60
|
+
|
61
|
+
script/generate blue_light_special_admin
|
62
|
+
|
63
|
+
This will generate your user admin controller and its integration test.
|
64
|
+
|
65
|
+
== Mad Mimi
|
66
|
+
|
67
|
+
If you'd like an overview of Mad Mimi, check out the third part of
|
68
|
+
{this screencast}[http://railslab.newrelic.com/2009/10/23/episode-21-on-the-edge-part-3].
|
69
|
+
In order to get Blue Light Special working with Mad Mimi, you'll need to sign
|
70
|
+
up for an account at {madmimi.com}[http://madmimi.com/r/b8599b9343f82e3bc30984ca4f3fea3f].
|
71
|
+
|
72
|
+
Your Mad Mimi account needs API access, so be sure to enable that during the signup
|
73
|
+
process. The support people at Mad Mimi will manually authorize your account for
|
74
|
+
API access. This usually happens within a few hours after you've signed up. Until
|
75
|
+
your account is authorized, you'll see HTTP errors when your Rails app attempts to
|
76
|
+
send email.
|
77
|
+
|
78
|
+
After you've signed up and your API access has been approved, all you'll need to do is
|
79
|
+
put your Mad Mimi username and API key in config/blue_light_special.yml.
|
80
|
+
|
81
|
+
== Facebook Connect
|
82
|
+
|
83
|
+
To set up Facebook Connect, go to the {Facebook developer page}[http://facebook.com/developers]
|
84
|
+
and create a new Facebook app. Since you're only using this app for Facebook Connect,
|
85
|
+
you can leave most of the fields blank. Be sure to give your app a name, and then
|
86
|
+
head over to the Connect settings and set the Connect URL to point at your Rails app.
|
87
|
+
In the Advanced section, you'll need to set Email Domain to the domain from which you'll
|
88
|
+
be sending email messages.
|
89
|
+
|
90
|
+
After you've finished setting up your Facebook app, grab its API key and secret key
|
91
|
+
and put them in config/blue_light_special.yml.
|
92
|
+
|
93
|
+
== To Build the Gem ==
|
94
|
+
gem build cops.gemspec
|
95
|
+
|
96
|
+
sudo gem install cops.gem
|
97
|
+
|
98
|
+
gem yank cops -v 0.2.0.1
|
99
|
+
|
100
|
+
== Differences from Blue Light Special ==
|
101
|
+
1. MimiMailer was made optional. In some cases, like deploying on heroku, you won't want to use MimiMailer templates, but instead regular mailer templates. Cops does not use MimiMailer unless you've setup your login info for that service.
|
102
|
+
2. DelayedJob is now optional. You can turn off the use of delayed job, again in the case of deploying to Heroku for example where you do not want to pay the extra fees of using a background worker. In this case emails will be sent immediately and not queued.
|
103
|
+
3. The welcome email is not only suppressed if the email is already confirmed, but is also not sent if the user connects via Facebook. Since Facebook returns the email already, which presumably Facebook has already confirmed, Cops marks the user as already confirmed.
|
104
|
+
4. Cops adds back into BlueLightSpecial, the email confirmation from Clearance. This is only used for non-facebook connect users
|
105
|
+
5. Added flash notice on creation of user
|
106
|
+
6. Using redirect_back_or in all cases so app using Cops gem has an option of where to send the user
|
107
|
+
7. Added a facebook_logout method that facebook can call via its Post-Remove Callback, to remove user from app
|
108
|
+
8. Changed to user can still log in even though they haven't confirmed their email (they just aren't active)
|
109
|
+
9. The change password function was using the confirmation token instead of the password reset token in several spots
|
110
|
+
|
111
|
+
== Copyright
|
112
|
+
|
113
|
+
Copyright (c) 2010 Envy Labs LLC. See LICENSE for details.
|
data/Rakefile
ADDED
@@ -0,0 +1,95 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'rake'
|
3
|
+
require 'rake/testtask'
|
4
|
+
|
5
|
+
begin
|
6
|
+
require 'jeweler'
|
7
|
+
Jeweler::Tasks.new do |gem|
|
8
|
+
gem.name = "blue_light_special"
|
9
|
+
gem.summary = %Q{Rails authentication by email and password}
|
10
|
+
gem.description = %Q{Rails authentication by email and password with integrated dependencies to MadMimi. Also provides administrative user impersonation.}
|
11
|
+
gem.email = "nate@envylabs.com"
|
12
|
+
gem.homepage = "http://github.com/envylabs/blue_light_special"
|
13
|
+
gem.authors = ["Nathaniel Bibler", "Mark Kendall", "Caike Souza"]
|
14
|
+
gem.files = FileList["[A-Z]*", "{app,config,generators,lib,shoulda_macros,rails}/**/*"]
|
15
|
+
|
16
|
+
gem.add_dependency "mini_fb", '=0.2.2'
|
17
|
+
gem.add_dependency "delayed_job", '=1.8.4'
|
18
|
+
gem.add_dependency "mad_mimi_mailer", '=0.0.7'
|
19
|
+
|
20
|
+
gem.add_development_dependency "shoulda", ">= 0"
|
21
|
+
end
|
22
|
+
Jeweler::GemcutterTasks.new
|
23
|
+
rescue LoadError
|
24
|
+
puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
|
25
|
+
end
|
26
|
+
|
27
|
+
namespace :test do
|
28
|
+
Rake::TestTask.new(:basic => ["check_dependencies",
|
29
|
+
"generator:cleanup",
|
30
|
+
"generator:blue_light_special",
|
31
|
+
"generator:blue_light_special_tests",
|
32
|
+
"generator:blue_light_special_admin"]) do |task|
|
33
|
+
task.libs << "lib"
|
34
|
+
task.libs << "test"
|
35
|
+
task.pattern = "test/{controllers,models}/*_test.rb"
|
36
|
+
task.verbose = false
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
generators = %w(blue_light_special blue_light_special_tests blue_light_special_admin)
|
41
|
+
|
42
|
+
namespace :generator do
|
43
|
+
desc "Cleans up the test app before running the generator"
|
44
|
+
task :cleanup do
|
45
|
+
FileList["test/rails_root/db/**/*"].each do |each|
|
46
|
+
FileUtils.rm_rf(each)
|
47
|
+
end
|
48
|
+
|
49
|
+
FileUtils.rm_rf("test/rails_root/vendor/plugins/blue_light_special")
|
50
|
+
FileUtils.mkdir_p("test/rails_root/vendor/plugins")
|
51
|
+
blue_light_special_root = File.expand_path(File.dirname(__FILE__))
|
52
|
+
system("ln -s \"#{blue_light_special_root}\" test/rails_root/vendor/plugins/blue_light_special")
|
53
|
+
end
|
54
|
+
|
55
|
+
desc "Run the blue_light_special generator"
|
56
|
+
task :blue_light_special do
|
57
|
+
system "cd test/rails_root && ./script/generate blue_light_special -f && ./script/generate delayed_job && rake gems:unpack && rake db:migrate db:test:prepare"
|
58
|
+
end
|
59
|
+
|
60
|
+
desc "Run the blue_light_special tests generator"
|
61
|
+
task :blue_light_special_tests do
|
62
|
+
system "cd test/rails_root && ./script/generate blue_light_special_tests -f"
|
63
|
+
end
|
64
|
+
|
65
|
+
desc "Run the blue_light_special admin generator"
|
66
|
+
task :blue_light_special_admin do
|
67
|
+
system "cd test/rails_root && ./script/generate blue_light_special_admin -f"
|
68
|
+
end
|
69
|
+
|
70
|
+
end
|
71
|
+
|
72
|
+
begin
|
73
|
+
require 'rcov/rcovtask'
|
74
|
+
Rcov::RcovTask.new do |test|
|
75
|
+
test.libs << 'test'
|
76
|
+
test.pattern = 'test/**/test_*.rb'
|
77
|
+
test.verbose = true
|
78
|
+
end
|
79
|
+
rescue LoadError
|
80
|
+
task :rcov do
|
81
|
+
abort "RCov is not available. In order to run rcov, you must: sudo gem install spicycode-rcov"
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
task :default => ['test:basic']
|
86
|
+
|
87
|
+
require 'rake/rdoctask'
|
88
|
+
Rake::RDocTask.new do |rdoc|
|
89
|
+
version = File.exist?('VERSION') ? File.read('VERSION') : ""
|
90
|
+
|
91
|
+
rdoc.rdoc_dir = 'rdoc'
|
92
|
+
rdoc.title = "BlueLightSpecial #{version}"
|
93
|
+
rdoc.rdoc_files.include('README*')
|
94
|
+
rdoc.rdoc_files.include('lib/**/*.rb')
|
95
|
+
end
|
data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
0.2.0
|
@@ -0,0 +1,76 @@
|
|
1
|
+
class BlueLightSpecial::ConfirmationsController < ApplicationController
|
2
|
+
unloadable
|
3
|
+
|
4
|
+
skip_before_filter :authenticate, :only => [:new, :create]
|
5
|
+
before_filter :redirect_signed_in_confirmed_user, :only => [:new, :create]
|
6
|
+
before_filter :redirect_signed_out_confirmed_user, :only => [:new, :create]
|
7
|
+
before_filter :forbid_missing_token, :only => [:new, :create]
|
8
|
+
before_filter :forbid_non_existent_user, :only => [:new, :create]
|
9
|
+
|
10
|
+
filter_parameter_logging :token
|
11
|
+
|
12
|
+
def new
|
13
|
+
create
|
14
|
+
end
|
15
|
+
|
16
|
+
def create
|
17
|
+
@user = ::User.find_by_id_and_confirmation_token(
|
18
|
+
params[:user_id], params[:token])
|
19
|
+
@user.confirm_email!
|
20
|
+
|
21
|
+
sign_in(@user)
|
22
|
+
flash_success_after_create
|
23
|
+
redirect_to(url_after_create)
|
24
|
+
end
|
25
|
+
|
26
|
+
private
|
27
|
+
|
28
|
+
def redirect_signed_in_confirmed_user
|
29
|
+
user = ::User.find_by_id(params[:user_id])
|
30
|
+
if user && user.email_confirmed? && current_user == user
|
31
|
+
flash_success_after_create
|
32
|
+
redirect_to(url_after_create)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
def redirect_signed_out_confirmed_user
|
37
|
+
user = ::User.find_by_id(params[:user_id])
|
38
|
+
if user && user.email_confirmed? && signed_out?
|
39
|
+
flash_already_confirmed
|
40
|
+
redirect_to(url_already_confirmed)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
def forbid_missing_token
|
45
|
+
if params[:token].blank?
|
46
|
+
raise ActionController::Forbidden, "missing token"
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
def forbid_non_existent_user
|
51
|
+
unless ::User.find_by_id_and_confirmation_token(
|
52
|
+
params[:user_id], params[:token])
|
53
|
+
raise ActionController::Forbidden, "non-existent user"
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
def flash_success_after_create
|
58
|
+
flash[:success] = translate(:confirmed_email,
|
59
|
+
:scope => [:clearance, :controllers, :confirmations],
|
60
|
+
:default => "Confirmed email and signed in.")
|
61
|
+
end
|
62
|
+
|
63
|
+
def flash_already_confirmed
|
64
|
+
flash[:success] = translate(:already_confirmed_email,
|
65
|
+
:scope => [:clearance, :controllers, :confirmations],
|
66
|
+
:default => "Already confirmed email. Please sign in.")
|
67
|
+
end
|
68
|
+
|
69
|
+
def url_after_create
|
70
|
+
'/'
|
71
|
+
end
|
72
|
+
|
73
|
+
def url_already_confirmed
|
74
|
+
sign_in_url
|
75
|
+
end
|
76
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
class BlueLightSpecial::ImpersonationsController < ApplicationController
|
2
|
+
before_filter :authenticate
|
3
|
+
before_filter :check_role, :except => :destroy
|
4
|
+
|
5
|
+
|
6
|
+
def index
|
7
|
+
@users = User.all
|
8
|
+
render :template => 'impersonations/index'
|
9
|
+
end
|
10
|
+
|
11
|
+
def create
|
12
|
+
user = User.find(params[:user_id])
|
13
|
+
if user == current_user
|
14
|
+
flash[:failure] = "Cannot impersonate yourself"
|
15
|
+
redirect_to root_url
|
16
|
+
else
|
17
|
+
session[:admin_user_id] = current_user.id
|
18
|
+
session[:impersonation_hash] = Impersonation.hash_for(current_user.id)
|
19
|
+
sign_in(user)
|
20
|
+
redirect_to root_url
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
def destroy
|
25
|
+
if Impersonation.valid_hash?(session[:admin_user_id], session[:impersonation_hash])
|
26
|
+
old_user = current_user
|
27
|
+
admin_user = User.find(session[:admin_user_id])
|
28
|
+
session[:admin_user_id] = nil
|
29
|
+
session[:impersonation_hash] = nil
|
30
|
+
sign_in(admin_user)
|
31
|
+
redirect_to impersonations_url
|
32
|
+
else
|
33
|
+
deny_access
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
|
38
|
+
private
|
39
|
+
|
40
|
+
|
41
|
+
def check_role
|
42
|
+
raise ActionController::Forbidden, "disallowed" unless current_user.admin?
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,93 @@
|
|
1
|
+
class BlueLightSpecial::PasswordsController < ApplicationController
|
2
|
+
unloadable
|
3
|
+
|
4
|
+
skip_before_filter :authenticate, :only => [:new, :create, :edit, :update]
|
5
|
+
before_filter :forbid_missing_token, :only => [:edit, :update]
|
6
|
+
before_filter :forbid_non_existent_user, :only => [:edit, :update]
|
7
|
+
filter_parameter_logging :password, :password_confirmation
|
8
|
+
|
9
|
+
def new
|
10
|
+
render :template => 'passwords/new'
|
11
|
+
end
|
12
|
+
|
13
|
+
def create
|
14
|
+
if user = ::User.find_by_email(params[:password][:email])
|
15
|
+
user.forgot_password!
|
16
|
+
if user.password_reset_token.present?
|
17
|
+
if BlueLightSpecial.configuration.use_delayed_job
|
18
|
+
Delayed::Job.enqueue DeliverChangePasswordJob.new(user)
|
19
|
+
else
|
20
|
+
BlueLightSpecialMailer.deliver_change_password(user)
|
21
|
+
end
|
22
|
+
flash_notice_after_create
|
23
|
+
redirect_to(url_after_create)
|
24
|
+
else
|
25
|
+
flash[:notice] = 'Your password was not able to be recovered. You may never have finished registration.'
|
26
|
+
render :template => 'passwords/new'
|
27
|
+
end
|
28
|
+
else
|
29
|
+
flash_failure_after_create
|
30
|
+
render :template => 'passwords/new'
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def edit
|
35
|
+
@user = ::User.find_by_id_and_password_reset_token(
|
36
|
+
params[:user_id], params[:token])
|
37
|
+
render :template => 'passwords/edit'
|
38
|
+
end
|
39
|
+
|
40
|
+
def update
|
41
|
+
@user = ::User.find_by_id_and_password_reset_token(
|
42
|
+
params[:user_id], params[:token])
|
43
|
+
|
44
|
+
if @user.update_password(params[:user][:password],
|
45
|
+
params[:user][:password_confirmation])
|
46
|
+
sign_in(@user)
|
47
|
+
flash_success_after_update
|
48
|
+
redirect_to(url_after_update)
|
49
|
+
else
|
50
|
+
render :template => 'passwords/edit'
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
private
|
55
|
+
|
56
|
+
def forbid_missing_token
|
57
|
+
if params[:token].blank?
|
58
|
+
raise ActionController::Forbidden, "missing token"
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
def forbid_non_existent_user
|
63
|
+
unless ::User.find_by_id_and_password_reset_token(
|
64
|
+
params[:user_id], params[:token])
|
65
|
+
raise ActionController::Forbidden, "non-existent user"
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
69
|
+
def flash_notice_after_create
|
70
|
+
flash[:notice] = translate(:deliver_change_password,
|
71
|
+
:scope => [:blue_light_special, :controllers, :passwords],
|
72
|
+
:default => "You will receive an email within the next few minutes. " <<
|
73
|
+
"It contains instructions for changing your password.")
|
74
|
+
end
|
75
|
+
|
76
|
+
def flash_failure_after_create
|
77
|
+
flash.now[:failure] = translate(:unknown_email,
|
78
|
+
:scope => [:blue_light_special, :controllers, :passwords],
|
79
|
+
:default => "Unknown email.")
|
80
|
+
end
|
81
|
+
|
82
|
+
def url_after_create
|
83
|
+
sign_in_url
|
84
|
+
end
|
85
|
+
|
86
|
+
def flash_success_after_update
|
87
|
+
flash[:success] = translate(:signed_in, :default => "Signed in.")
|
88
|
+
end
|
89
|
+
|
90
|
+
def url_after_update
|
91
|
+
'/'
|
92
|
+
end
|
93
|
+
end
|
@@ -0,0 +1,76 @@
|
|
1
|
+
class BlueLightSpecial::SessionsController < ApplicationController
|
2
|
+
unloadable
|
3
|
+
|
4
|
+
skip_before_filter :authenticate, :only => [:new, :create, :destroy]
|
5
|
+
protect_from_forgery :except => :create
|
6
|
+
filter_parameter_logging :password
|
7
|
+
|
8
|
+
def new
|
9
|
+
render :template => 'sessions/new'
|
10
|
+
end
|
11
|
+
|
12
|
+
def create
|
13
|
+
@user = if params[:session]
|
14
|
+
::User.authenticate(params[:session][:email], params[:session][:password])
|
15
|
+
else
|
16
|
+
::User.find_facebook_user(cookies[BlueLightSpecial.configuration.facebook_api_key + "_session_key"],
|
17
|
+
cookies[BlueLightSpecial.configuration.facebook_api_key + "_user"])
|
18
|
+
end
|
19
|
+
|
20
|
+
if @user.nil?
|
21
|
+
flash_failure_after_create
|
22
|
+
render :template => 'sessions/new', :status => :unauthorized
|
23
|
+
else
|
24
|
+
if @user.email_confirmed?
|
25
|
+
flash_success_after_create
|
26
|
+
else
|
27
|
+
::BlueLightSpecialMailer.deliver_confirmation(@user)
|
28
|
+
flash_notice_after_create
|
29
|
+
end
|
30
|
+
sign_in(@user)
|
31
|
+
reset_session
|
32
|
+
redirect_back_or(url_after_create)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
def destroy
|
37
|
+
if BlueLightSpecial.configuration.use_facebook_connect
|
38
|
+
cookies[BlueLightSpecial.configuration.facebook_api_key + "_user"] = nil
|
39
|
+
cookies[BlueLightSpecial.configuration.facebook_api_key + "_session_key"] = nil
|
40
|
+
end
|
41
|
+
sign_out
|
42
|
+
flash_success_after_destroy
|
43
|
+
redirect_to(url_after_destroy)
|
44
|
+
end
|
45
|
+
|
46
|
+
private
|
47
|
+
|
48
|
+
def flash_failure_after_create
|
49
|
+
flash.now[:failure] = translate(:bad_email_or_password,
|
50
|
+
:scope => [:blue_light_special, :controllers, :sessions],
|
51
|
+
:default => "Bad email or password.")
|
52
|
+
end
|
53
|
+
|
54
|
+
def flash_success_after_create
|
55
|
+
flash[:success] = translate(:signed_in, :default => "Signed in.")
|
56
|
+
end
|
57
|
+
|
58
|
+
def flash_notice_after_create
|
59
|
+
flash[:notice] = translate(:unconfirmed_email,
|
60
|
+
:scope => [:blue_light_special, :controllers, :sessions],
|
61
|
+
:default => "User has not confirmed email. " <<
|
62
|
+
"Confirmation email will be resent.")
|
63
|
+
end
|
64
|
+
|
65
|
+
def url_after_create
|
66
|
+
'/'
|
67
|
+
end
|
68
|
+
|
69
|
+
def flash_success_after_destroy
|
70
|
+
flash[:success] = translate(:signed_out, :default => "Signed out.")
|
71
|
+
end
|
72
|
+
|
73
|
+
def url_after_destroy
|
74
|
+
sign_in_url
|
75
|
+
end
|
76
|
+
end
|
@@ -0,0 +1,85 @@
|
|
1
|
+
class BlueLightSpecial::UsersController < ApplicationController
|
2
|
+
unloadable
|
3
|
+
|
4
|
+
skip_before_filter :authenticate, :only => [:new, :create, :facebook_remove]
|
5
|
+
before_filter :redirect_to_root, :only => [:new, :create], :if => :signed_in?
|
6
|
+
filter_parameter_logging :password
|
7
|
+
# Before Filter on *only* the 'uninstalled' method
|
8
|
+
before_filter :verify_uninstall_signature, :only => [:facebook_remove]
|
9
|
+
|
10
|
+
def facebook_remove
|
11
|
+
@fb_uid = params[:fb_sig_user]
|
12
|
+
if @fb_uid.present?
|
13
|
+
# From here on it will be app specific -- given the facebook uid, destroy the user, like...
|
14
|
+
@user = User.find_by_facebook_uid(@fb_uid)
|
15
|
+
@user.destroy if @user
|
16
|
+
end
|
17
|
+
render :nothing => true; return
|
18
|
+
end
|
19
|
+
|
20
|
+
def show
|
21
|
+
@user = current_user
|
22
|
+
render :template => 'users/show'
|
23
|
+
end
|
24
|
+
|
25
|
+
def new
|
26
|
+
@user = ::User.new(params[:user])
|
27
|
+
render :template => 'users/new'
|
28
|
+
end
|
29
|
+
|
30
|
+
def create
|
31
|
+
@user = ::User.new params[:user]
|
32
|
+
if @user.save
|
33
|
+
sign_in(@user)
|
34
|
+
flash[:notice] = 'You have successfully signed up.'
|
35
|
+
redirect_back_or(url_after_create)
|
36
|
+
else
|
37
|
+
render :template => 'users/new'
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
def edit
|
42
|
+
@user = current_user
|
43
|
+
render :template => 'users/edit'
|
44
|
+
end
|
45
|
+
|
46
|
+
def update
|
47
|
+
@user = current_user
|
48
|
+
if @user.update_attributes(params[:user])
|
49
|
+
flash[:success] = 'Your profile has been updated.'
|
50
|
+
redirect_back_or(user_path(@user))
|
51
|
+
else
|
52
|
+
render :template => 'users/edit'
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
protected
|
57
|
+
def verify_uninstall_signature
|
58
|
+
signature = ''
|
59
|
+
keys = params.keys.sort
|
60
|
+
keys.each do |key|
|
61
|
+
next if key == 'fb_sig'
|
62
|
+
next unless key.include?('fb_sig')
|
63
|
+
key_name = key.gsub('fb_sig_', '')
|
64
|
+
signature += key_name
|
65
|
+
signature += '='
|
66
|
+
signature += params[key]
|
67
|
+
end
|
68
|
+
signature += BlueLightSpecial.configuration.facebook_secret_key
|
69
|
+
calculated_sig = Digest::MD5.hexdigest(signature)
|
70
|
+
#logger.info "\nUNINSTALL :: Signature (fb_sig param from facebook) :: #{params[:fb_sig]}"
|
71
|
+
#logger.info "\nUNINSTALL :: Signature String (pre-hash) :: #{signature}"
|
72
|
+
#logger.info "\nUNINSTALL :: MD5 Hashed Sig :: #{calculated_sig}"
|
73
|
+
if calculated_sig != params[:fb_sig]
|
74
|
+
#logger.warn "\n\nUNINSTALL :: WARNING :: expected signatures did not match\n\n" return false else
|
75
|
+
#logger.warn "\n\nUNINSTALL :: SUCCESS!! Signatures matched.\n"
|
76
|
+
end
|
77
|
+
return true
|
78
|
+
end
|
79
|
+
|
80
|
+
private
|
81
|
+
|
82
|
+
def url_after_create
|
83
|
+
root_url
|
84
|
+
end
|
85
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
class BlueLightSpecialMailer
|
2
|
+
|
3
|
+
def self.deliver_change_password(user)
|
4
|
+
if MadMimiMailer.api_settings.present? && MadMimiMailer.api_settings[:username].present? && MadMimiMailer.api_settings[:api_key].present?
|
5
|
+
MimiMailer.deliver_mimi_change_password(user)
|
6
|
+
else
|
7
|
+
GenericMailer.deliver_change_password(user)
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
def self.deliver_welcome(user)
|
12
|
+
if MadMimiMailer.api_settings.present? && MadMimiMailer.api_settings[:username].present? && MadMimiMailer.api_settings[:api_key].present?
|
13
|
+
MimiMailer.deliver_welcome(user)
|
14
|
+
else
|
15
|
+
GenericMailer.deliver_welcome(user)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
def self.deliver_confirmation(user)
|
20
|
+
if MadMimiMailer.api_settings.present? && MadMimiMailer.api_settings[:username].present? && MadMimiMailer.api_settings[:api_key].present?
|
21
|
+
MimiMailer.deliver_confirmation(user)
|
22
|
+
else
|
23
|
+
GenericMailer.deliver_confirmation(user)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
|
28
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
##
|
2
|
+
# Delivers the BlueLightSpecial.deliver_mimi_change_password to the requested
|
3
|
+
# User by +id+ as an asynchronous process.
|
4
|
+
#
|
5
|
+
class DeliverChangePasswordJob
|
6
|
+
|
7
|
+
attr_reader :user_id
|
8
|
+
|
9
|
+
def initialize(user_id)
|
10
|
+
@user_id = user_id.kind_of?(User) ? user_id.id : user_id
|
11
|
+
end
|
12
|
+
|
13
|
+
def perform
|
14
|
+
if user = User.find_by_id(@user_id)
|
15
|
+
BlueLightSpecialMailer.deliver_change_password(user)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
##
|
2
|
+
# Delivers the UserMailer.deliver_mimi_welcome to the requested User by +id+
|
3
|
+
# as an asynchronous process.
|
4
|
+
#
|
5
|
+
class DeliverWelcomeJob
|
6
|
+
|
7
|
+
def initialize(user_id)
|
8
|
+
@user_id = user_id
|
9
|
+
end
|
10
|
+
|
11
|
+
def perform
|
12
|
+
if user = User.find_by_id(@user_id)
|
13
|
+
BlueLightSpecialMailer.deliver_welcome(user)
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
end
|