token_authenticate_me 0.5.3 → 0.5.4

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c1f54dbd7d8eb742f1e9c70eff54faf8e1e540e5
4
- data.tar.gz: 551e27d482158cfd41ff0edbb52d4c1e0405951d
3
+ metadata.gz: 014ea05ef85b51fefd546c3810d22ceb01c1949a
4
+ data.tar.gz: 32299428b5e1198b06350a8b3cc5c6e9ca56e291
5
5
  SHA512:
6
- metadata.gz: 58504a64583a11e34883a2f09b30913c7db1ef2a06516679f3c4b3d17f76424c328308677b4b38a0d5f5a69a27e0007793ece766c4dad174dfd5e63f527d6264
7
- data.tar.gz: 94460e4e5dcfefdd1fbc93bce5142e49c74143bc8ab9bae610b6fd35b7622ebc0e585b85ea78dad424641103fc3868e028630246078def05c3c16dc5a8863f7a
6
+ metadata.gz: 77265c9a971f4cd560dc6cf6ce3272d86c42ebba02d29714147e34f59f047ede1227ef88bb52a38beabc3a8541fcf6867fec752a415848afc160ba45e3593c5b
7
+ data.tar.gz: fe1899c608ce5be093d59417eb03beaf2431e7c3807637bb8a43897aa693ee95e1a18310fb5564655496795ee0339e95145892162ca18ea6ae5efff7f09ec248
data/README.md CHANGED
@@ -10,25 +10,31 @@ Add the gem to your Gemfile:
10
10
 
11
11
  Run `bundle install` to install it.
12
12
 
13
- To add or create a user with token authentication run:
14
- `rails generate token_authenticate_me:install <model>`
13
+ To install run the following:
14
+ `rails generate token_authenticate_me:install`
15
15
 
16
- Replace `<model>` with the class name used for users. This will create the necessary migration files, and optionally create the model file if it does not exist.
16
+ Include `TokenAuthenticateMe::Concerns::Controllers::TokenAuthenticateable` into api controllers that require authorization:
17
+ ````rb
18
+ require 'token_authenticate_me/concerns/controllers/token_authenticateable'
17
19
 
18
- **Right now this gem only supports creating the authentication model `User`, so it is recommended to call `rails generate token_authenticate_me:install user`**
20
+ class ApiController < ApplicationController
21
+ include TokenAuthenticateMe::Concerns::Controllers::TokenAuthenticateable
19
22
 
20
- Include TokenAuthenticateMe::TokenAuthentication into the application controller or any controllers that require authorization:
21
- ````rb
22
- require 'token_authenticate_me/controllers/token_authenticateable'
23
+ skip_before_filter :verify_authenticity_token # CSRF is not needed for header or param based auth
24
+
25
+ #...
26
+ end
27
+ ````
23
28
 
24
- class ApplicationController < ActionController::Base
25
- force_ssl if Rails.env.production?
29
+ Include `TokenAuthenticateMe::Concerns::Controllers::SessionAuthenticateable` into server rendered page controllers that require authorization:
30
+ ````rb
31
+ require 'token_authenticate_me/concerns/controllers/session_authenticateable'
26
32
 
33
+ class AuthenticatedController < ApplicationController
27
34
  # Prevent CSRF attacks by raising an exception.
28
- # For APIs, you may want to use :null_session instead.
29
35
  protect_from_forgery with: :exception
30
36
 
31
- include TokenAuthenticateMe::Controllers::TokenAuthenticateable
37
+ include TokenAuthenticateMe::Concerns::Controllers::SessionAuthenticateable
32
38
 
33
39
  #...
34
40
  end
@@ -44,16 +50,10 @@ end
44
50
  ````
45
51
 
46
52
  ## Authentication Model
47
- The model that is used for authentication will need to have `include TokenAuthenticateMe::Models::Authenticatable`. This will automatically happen if you use the generator.
48
-
49
- If you did not use the generator, this module expects the model to have the following attributes:
50
- * `email:string`
51
- * `password_digest:string`
52
- * `username:string`
53
- * `reset_password_token:string`
54
- * `reset_password_token_exp:datetime`
55
-
56
- This model will have a set of [validators](https://github.com/inigo-llc/token_authenticate_me/blob/master/lib/token_authenticate_me/models/authenticatable.rb#L11) added to it.
53
+ The model has 3 concerns:
54
+ * [Authenticatable](https://github.com/wildland/token_authenticate_me/blob/master/lib/token_authenticate_me/concerns/models/authenticatable.rb)
55
+ * [Invitable](https://github.com/wildland/token_authenticate_me/blob/master/lib/token_authenticate_me/concerns/models/invitable.rb)
56
+ * [Sessionable](https://github.com/wildland/token_authenticate_me/blob/master/lib/token_authenticate_me/concerns/models/sessionable.rb)
57
57
 
58
58
  *tl;dr*:
59
59
  * `email` is required, can't be blank, is unique (case insensitive), and must look like an email address.
@@ -61,10 +61,5 @@ This model will have a set of [validators](https://github.com/inigo-llc/token_au
61
61
  * `username` is required, can't be blank, is unique (case insensitive), and only allows alphanumeric values.
62
62
  * To change the `password` or `email` after the model has been persisted, you will need to provide the current password as `current_password`.
63
63
 
64
- #### TODO:
65
- - [ ] Make it so any resource name can be used for authentication (initial thought is either specify the default or pass resource name in token string?).
66
- - [ ] Allow users to specify the API namespace default.
67
- - [ ] Add a way to override/change/configure validations.
68
-
69
64
  ## Code Of Conduct
70
65
  Wildland Open Source [Code Of Conduct](https://github.com/wildland/code-of-conduct)
@@ -1,8 +1,7 @@
1
1
  module TokenAuthenticateMe
2
2
  module Api
3
3
  module V1
4
- class BaseController < TokenAuthenticateMe::ApplicationController
5
- skip_before_action :verify_authenticity_token
4
+ class BaseController < ActionController::Base
6
5
  end
7
6
  end
8
7
  end
@@ -1,10 +1,12 @@
1
- require 'token_authenticate_me/concerns/controllers/sessionable'
1
+ require 'token_authenticate_me/concerns/controllers/token_authenticateable'
2
+ require 'token_authenticate_me/concerns/controllers/token_sessionable'
2
3
 
3
4
  module TokenAuthenticateMe
4
5
  module Api
5
6
  module V1
6
7
  class SessionsController < BaseController
7
- include TokenAuthenticateMe::Concerns::Controllers::Sessionable
8
+ include TokenAuthenticateMe::Concerns::Controllers::TokenAuthenticateable
9
+ include TokenAuthenticateMe::Concerns::Controllers::TokenSessionable
8
10
  end
9
11
  end
10
12
  end
@@ -0,0 +1,24 @@
1
+ module TokenAuthenticateMe
2
+ class Authentication
3
+ def self.default_token_handler(token, _options)
4
+ session = TokenAuthenticateMe::Session.find_by_key(token)
5
+
6
+ if session && session.expiration > DateTime.now
7
+ session
8
+ else
9
+ false
10
+ end
11
+ end
12
+
13
+ attr_reader :token, :token_handler
14
+
15
+ def initialize(token:, token_handler: TokenAuthenticateMe::Authentication.method(:default_token_handler))
16
+ @token = token
17
+ @token_handler = token_handler
18
+ end
19
+
20
+ def authenticate(options = {})
21
+ token_handler.call(token, options)
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,33 @@
1
+ require 'active_support/concern'
2
+ require 'token_authenticate_me/authentication'
3
+
4
+ module TokenAuthenticateMe
5
+ module Concerns
6
+ module Controllers
7
+ module Authenticateable
8
+ extend ActiveSupport::Concern
9
+
10
+ # Standard authentication routine, override to implement different auth strategies.
11
+ def token_handler(token, options)
12
+ authentication = TokenAuthenticateMe::Authentication.new(token: token)
13
+ authentication.authenticate(options)
14
+ end
15
+
16
+ protected
17
+
18
+ # `authenticated_session` and `render_unauthorized` are specific to controllers.
19
+ # Ex:
20
+ # Could render json or http status code for unauthorized, or could redirect to a different url for server rendered pages.
21
+ # Could authenticate using headers or params, or cookie sessions depending on controller type.
22
+ def authenticate
23
+ authenticated_session || render_unauthorized
24
+ end
25
+
26
+ def current_user
27
+ return unless authenticated_session
28
+ @current_user ||= User.find_by_id(authenticated_session.user_id)
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,47 @@
1
+ require 'active_support/concern'
2
+ require 'token_authenticate_me/concerns/controllers/authenticateable'
3
+ require 'token_authenticate_me/session_authentication'
4
+
5
+ # This module provides cookie based session authentication for server rendered pages.
6
+ # If using this module, make sure CSRF is enabled to prevent CSRF attacks.
7
+
8
+ module TokenAuthenticateMe
9
+ module Concerns
10
+ module Controllers
11
+ module SessionAuthenticateable
12
+ extend ActiveSupport::Concern
13
+
14
+ include TokenAuthenticateMe::Concerns::Controllers::Authenticateable
15
+
16
+ protected
17
+
18
+ def authenticated_session
19
+ @session ||= authenticate_with_session
20
+ end
21
+
22
+ def authenticate_with_session
23
+ session_authentication = TokenAuthenticateMe::SessionAuthentication.new(controller: self)
24
+ session_authentication.authenticate
25
+ end
26
+
27
+ def return_to_url
28
+ session[:return_to]
29
+ end
30
+
31
+ def save_return_to_url
32
+ session[:return_to] = request.url
33
+ end
34
+
35
+ def redirect_to_login
36
+ redirect_to login_url
37
+ end
38
+
39
+ def render_unauthorized
40
+ save_return_to_url
41
+ flash.now[:error] = "You must be logged in to access this section"
42
+ redirect_to_login
43
+ end
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,50 @@
1
+ require 'active_support/concern'
2
+ require 'token_authenticate_me/concerns/controllers/sessionable'
3
+
4
+ module TokenAuthenticateMe
5
+ module Concerns
6
+ module Controllers
7
+ module SessionSessionable
8
+ extend ActiveSupport::Concern
9
+
10
+ include Sessionable
11
+
12
+ included do
13
+ skip_before_action :authenticate, only: [:new, :create]
14
+
15
+ def new
16
+ end
17
+
18
+ def create
19
+ if authenticate_resource
20
+ @session = create_session!(resource)
21
+ session[:key] = @session.key
22
+ if return_to_url
23
+ redirect_to_login
24
+ else
25
+ redirect_to root_url
26
+ end
27
+ else
28
+ flash.now[:error] = "Invalid username or password"
29
+ redirect_to_login
30
+ end
31
+ end
32
+
33
+ def destroy
34
+ unauthenticate_resource
35
+ redirect_to return_to_url
36
+
37
+ rescue
38
+ render_unauthorized
39
+ end
40
+
41
+ protected
42
+
43
+ def session_params
44
+ params.require(:session).permit(:username, :password)
45
+ end
46
+ end
47
+ end
48
+ end
49
+ end
50
+ end
@@ -1,5 +1,4 @@
1
1
  require 'active_support/concern'
2
-
3
2
  require 'token_authenticate_me/concerns/controllers/token_authenticateable'
4
3
 
5
4
  module TokenAuthenticateMe
@@ -8,43 +7,33 @@ module TokenAuthenticateMe
8
7
  module Sessionable
9
8
  extend ActiveSupport::Concern
10
9
 
11
- include TokenAuthenticateMe::Concerns::Controllers::TokenAuthenticateable
12
-
13
10
  included do
14
- skip_before_action :authenticate, only: [:create]
15
- after_action :cleanup_sessions, only: [:destroy]
16
-
17
- def create
18
- resource = User.where('username=? OR email=?', params[:username], params[:username]).first
19
- if resource && resource.authenticate(params[:password])
20
- @session = Session.create(user_id: resource.id)
21
- render json: @session, status: 201
22
- else
23
- render json: { message: 'Bad credentials' }, status: 401
24
- end
25
- end
11
+ after_action :cleanup_sessions, only: [:create, :destroy]
26
12
 
27
- def show
28
- @session = authenticate_token
29
- render json: @session
30
- end
13
+ protected
31
14
 
32
- def destroy
33
- authenticate_token.destroy
15
+ def unauthenticate_resource
16
+ authenticated_session.destroy!
17
+ end
34
18
 
35
- render status: 204, nothing: true
36
- rescue
37
- render_unauthorized
19
+ def create_session!(authenticated_resource)
20
+ Session.create!(user_id: authenticated_resource.id)
38
21
  end
39
22
 
40
- private
23
+ def resource
24
+ @resource ||= User.where('username=? OR email=?', session_params[:username], session_params[:username]).first
25
+ end
41
26
 
42
- def session_params
43
- params.permit(:username, :email, :password)
27
+ def authenticate_resource
28
+ if resource && resource.authenticate(session_params[:password])
29
+ resource
30
+ else
31
+ nil
32
+ end
44
33
  end
45
34
 
46
35
  def cleanup_sessions
47
- ApiSession.where('expiration < ?', DateTime.now).delete_all
36
+ Session.where('expiration < ?', DateTime.now).delete_all
48
37
  rescue
49
38
  Rails.logger.warn 'Error cleaning up old authentication sessions'
50
39
  end
@@ -1,4 +1,6 @@
1
1
  require 'active_support/concern'
2
+ require 'token_authenticate_me/concerns/controllers/authenticateable'
3
+ require 'token_authenticate_me/header_authentication'
2
4
 
3
5
  module TokenAuthenticateMe
4
6
  module Concerns
@@ -6,25 +8,22 @@ module TokenAuthenticateMe
6
8
  module TokenAuthenticateable
7
9
  extend ActiveSupport::Concern
8
10
 
11
+ include TokenAuthenticateMe::Concerns::Controllers::Authenticateable
12
+
9
13
  included do
10
- before_action :authenticate
14
+ before_action :authenticate # By default authenticate every action
11
15
  end
12
16
 
13
- protected
14
17
 
15
- def authenticate
16
- authenticate_token || render_unauthorized
17
- end
18
+ protected
18
19
 
19
- def current_user
20
- return unless authenticate_token
21
- @current_user ||= User.find_by_id(authenticate_token.user_id)
20
+ def authenticated_session
21
+ @session ||= authenticate_with_header
22
22
  end
23
23
 
24
- def authenticate_token
25
- @session ||= (
26
- authenticate_with_http_token(&method(:token_handler)) || authenticate_with_params
27
- )
24
+ def authenticate_with_header
25
+ header_authentication = TokenAuthenticateMe::HeaderAuthentication.new(controller: self)
26
+ header_authentication.authenticate
28
27
  end
29
28
 
30
29
  def authenticate_with_params
@@ -36,15 +35,6 @@ module TokenAuthenticateMe
36
35
  headers['WWW-Authenticate'] = 'Token realm="Application"'
37
36
  render json: 'Bad credentials', status: 401
38
37
  end
39
-
40
- def token_handler(token, _options)
41
- session = TokenAuthenticateMe::Session.find_by_key(token)
42
- if session && session.expiration > DateTime.now
43
- session
44
- else
45
- false
46
- end
47
- end
48
38
  end
49
39
  end
50
40
  end
@@ -0,0 +1,47 @@
1
+ require 'active_support/concern'
2
+ require 'token_authenticate_me/concerns/controllers/sessionable'
3
+
4
+ module TokenAuthenticateMe
5
+ module Concerns
6
+ module Controllers
7
+ module TokenSessionable
8
+ extend ActiveSupport::Concern
9
+
10
+ include Sessionable
11
+
12
+ included do
13
+ skip_before_action :authenticate, only: [:create]
14
+
15
+ def create
16
+ if authenticate_resource
17
+ @session = create_session!(resource)
18
+ render json: @session, status: 201
19
+ else
20
+ render json: { message: 'Bad credentials' }, status: 401
21
+ end
22
+ end
23
+
24
+ def show
25
+ @session = authenticated_session
26
+ render json: @session
27
+ end
28
+
29
+ def destroy
30
+ unauthenticate_resource
31
+
32
+ render status: 204, nothing: true
33
+ rescue
34
+ render_unauthorized
35
+ end
36
+
37
+ protected
38
+
39
+ def session_params
40
+ params.permit(:username, :password)
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
47
+
@@ -0,0 +1,20 @@
1
+ module TokenAuthenticateMe
2
+ class HeaderAuthentication
3
+ attr :controller
4
+
5
+ def initialize(controller:)
6
+ @controller = controller
7
+ end
8
+
9
+ def authenticate(options = {})
10
+ controller.authenticate_with_http_token(&method(:token_handler))
11
+ end
12
+
13
+ private
14
+
15
+ def token_handler(token, options)
16
+ token_handler = controller.token_handler(token, options)
17
+ end
18
+ end
19
+ end
20
+
@@ -0,0 +1,24 @@
1
+ module TokenAuthenticateMe
2
+ class SessionAuthentication
3
+ attr :controller
4
+
5
+ def initialize(controller:)
6
+ @controller = controller
7
+ end
8
+
9
+ def authenticate(options = {})
10
+ token = session_key
11
+ token_handler(token, options)
12
+ end
13
+
14
+ private
15
+
16
+ def token_handler(token, options)
17
+ controller.token_handler(token, options)
18
+ end
19
+
20
+ def session_key
21
+ controller.session[:key]
22
+ end
23
+ end
24
+ end
@@ -1,3 +1,3 @@
1
1
  module TokenAuthenticateMe
2
- VERSION = '0.5.3'.freeze
2
+ VERSION = '0.5.4'.freeze
3
3
  end
@@ -7,6 +7,24 @@ module TokenAuthenticateMe
7
7
 
8
8
  UUID_REGEX = /([a-f0-9]){32}/
9
9
 
10
+ module Concerns
11
+ module Controllers
12
+ autoload :Authenticatable, 'token_authenticate_me/concerns/controllers/authenticateable'
13
+ autoload :Invitable, 'token_authenticate_me/concerns/controllers/invitable'
14
+ autoload :PasswordResetable, 'token_authenticate_me/concerns/controllers/password_resetable'
15
+ autoload :SessionAuthenticateable, 'token_authenticate_me/concerns/controllers/session_authenticateable'
16
+ autoload :Sessionable, 'token_authenticate_me/concerns/controllers/sessionable'
17
+ autoload :TokenAuthenticateable, 'token_authenticate_me/concerns/controllers/token_authenticateable'
18
+ autoload :TokenSessionable, 'token_authenticate_me/concerns/controllers/token_sessionable'
19
+ end
20
+
21
+ module Models
22
+ autoload :Authenticatable, 'token_authenticate_me/concerns/models/authenticatable'
23
+ autoload :Invitable, 'token_authenticate_me/concerns/models/invitable'
24
+ autoload :Sessionable, 'token_authenticate_me/concerns/models/sessionable'
25
+ end
26
+ end
27
+
10
28
  def configure
11
29
  yield configuration
12
30
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: token_authenticate_me
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.3
4
+ version: 0.5.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sam Clopton
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2016-09-13 00:00:00.000000000 Z
12
+ date: 2016-10-11 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rails
@@ -71,12 +71,14 @@ files:
71
71
  - app/controllers/token_authenticate_me/application_controller.rb
72
72
  - app/helpers/token_authenticate_me/application_helper.rb
73
73
  - app/mailers/token_authenticate_me_mailer.rb
74
+ - app/models/token_authenticate_me/default_token_handler.rb
74
75
  - app/models/token_authenticate_me/invite.rb
75
76
  - app/models/token_authenticate_me/session.rb
76
77
  - app/models/token_authenticate_me/user.rb
77
78
  - app/views/token_authenticate_me_mailer/invalid_user_reset_password_email.html.erb
78
79
  - app/views/token_authenticate_me_mailer/invalid_user_reset_password_email.text.erb
79
80
  - app/views/token_authenticate_me_mailer/invite_user_email.html.erb
81
+ - app/views/token_authenticate_me_mailer/session/new.html.erb
80
82
  - app/views/token_authenticate_me_mailer/valid_user_reset_password_email.html.erb
81
83
  - app/views/token_authenticate_me_mailer/valid_user_reset_password_email.text.erb
82
84
  - config/routes.rb
@@ -91,16 +93,23 @@ files:
91
93
  - lib/generators/token_authenticate_me/policies/templates/user_policy.rb
92
94
  - lib/tasks/token_authenticate_me_tasks.rake
93
95
  - lib/token_authenticate_me.rb
96
+ - lib/token_authenticate_me/authentication.rb
97
+ - lib/token_authenticate_me/concerns/controllers/authenticateable.rb
94
98
  - lib/token_authenticate_me/concerns/controllers/invitable.rb
95
99
  - lib/token_authenticate_me/concerns/controllers/password_resetable.rb
100
+ - lib/token_authenticate_me/concerns/controllers/session_authenticateable.rb
101
+ - lib/token_authenticate_me/concerns/controllers/session_sessionable.rb
96
102
  - lib/token_authenticate_me/concerns/controllers/sessionable.rb
97
103
  - lib/token_authenticate_me/concerns/controllers/token_authenticateable.rb
104
+ - lib/token_authenticate_me/concerns/controllers/token_sessionable.rb
98
105
  - lib/token_authenticate_me/concerns/models/authenticatable.rb
99
106
  - lib/token_authenticate_me/concerns/models/invitable.rb
100
107
  - lib/token_authenticate_me/concerns/models/sessionable.rb
101
108
  - lib/token_authenticate_me/configuration.rb
102
109
  - lib/token_authenticate_me/engine.rb
110
+ - lib/token_authenticate_me/header_authentication.rb
103
111
  - lib/token_authenticate_me/models.rb
112
+ - lib/token_authenticate_me/session_authentication.rb
104
113
  - lib/token_authenticate_me/version.rb
105
114
  - test/dummy/README.rdoc
106
115
  - test/dummy/Rakefile