authentication-zero 2.9.2 → 2.9.3

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.
Files changed (24) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile.lock +1 -1
  3. data/lib/authentication_zero/version.rb +1 -1
  4. data/lib/generators/authentication/authentication_generator.rb +14 -67
  5. data/lib/generators/authentication/templates/controllers/api/application_controller.rb.tt +26 -0
  6. data/lib/generators/authentication/templates/controllers/html/application_controller.rb.tt +24 -0
  7. data/lib/generators/authentication/templates/models/model.rb.tt +2 -2
  8. data/lib/generators/authentication/templates/test_unit/application_system_test_case.rb.tt +15 -0
  9. data/lib/generators/authentication/templates/test_unit/controllers/api/identity/email_verifications_controller_test.rb.tt +0 -4
  10. data/lib/generators/authentication/templates/test_unit/controllers/api/identity/emails_controller_test.rb.tt +0 -4
  11. data/lib/generators/authentication/templates/test_unit/controllers/api/passwords_controller_test.rb.tt +0 -4
  12. data/lib/generators/authentication/templates/test_unit/controllers/api/sessions/sudos_controller_test.rb.tt +0 -4
  13. data/lib/generators/authentication/templates/test_unit/controllers/api/sessions_controller_test.rb.tt +0 -4
  14. data/lib/generators/authentication/templates/test_unit/controllers/html/identity/email_verifications_controller_test.rb.tt +0 -4
  15. data/lib/generators/authentication/templates/test_unit/controllers/html/identity/emails_controller_test.rb.tt +0 -4
  16. data/lib/generators/authentication/templates/test_unit/controllers/html/passwords_controller_test.rb.tt +0 -4
  17. data/lib/generators/authentication/templates/test_unit/controllers/html/sessions/sudos_controller_test.rb.tt +0 -4
  18. data/lib/generators/authentication/templates/test_unit/controllers/html/sessions_controller_test.rb.tt +0 -4
  19. data/lib/generators/authentication/templates/test_unit/system/identity/emails_test.rb.tt +0 -10
  20. data/lib/generators/authentication/templates/test_unit/system/passwords_test.rb.tt +0 -10
  21. data/lib/generators/authentication/templates/test_unit/system/sessions/sudos_test.rb.tt +0 -10
  22. data/lib/generators/authentication/templates/test_unit/system/sessions_test.rb.tt +0 -10
  23. data/lib/generators/authentication/templates/test_unit/test_helper.rb.tt +22 -0
  24. metadata +5 -1
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 1eb8eb320cf8198e9afebf59fd2365b2683e3b52840d8d455876a11b208e243c
4
- data.tar.gz: 3bc190759683e6e647a597bdb57e09e69243901a3390c401e09eac72ada96726
3
+ metadata.gz: d8173a1510dfbe78180ce29cbb83b5f79b84b0ed4ecacf0569344905c28f2a01
4
+ data.tar.gz: 9d89bc1c96a4b59b7c7bf2437bd038036e747f4e78c0a7d5a81f1c0ae4c86f28
5
5
  SHA512:
6
- metadata.gz: 0c2996c6cf6779c22442f7155025bb99a470f26a0dc23218aea96f413fd5ae85a1ffdebd796922b77a09f60a833c4a0bb72bc9e964f5c0695066cf4074c3f4e9
7
- data.tar.gz: 8cbf3eb8525e08fc10a5c00a88e1a82d928a107c969e7b6f4e65789d0db1d79b3a19369331f914b5baf439230a6b0e246287f6875f1f4ab7d57c4f470e96c0a0
6
+ metadata.gz: 34a5ed73cbd7f5e35cd9a1e16ae0e4880a677ffa94f3892c0c6292abb436b3fded01c4664dd5e77d5b8025718b60ea8507bdbd968243d94ef191980615b02ea4
7
+ data.tar.gz: 2afb2c4fbc2bef0c7e06fab12cf783f04c6bc811d7150ed58f4a73f430c23925f4e790c6e3477729e04f2ade59b80dd30220667952d7b41cc98a4106fc4e064e
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- authentication-zero (2.9.2)
4
+ authentication-zero (2.9.3)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
@@ -1,3 +1,3 @@
1
1
  module AuthenticationZero
2
- VERSION = "2.9.2"
2
+ VERSION = "2.9.3"
3
3
  end
@@ -32,12 +32,12 @@ class AuthenticationGenerator < Rails::Generators::NamedBase
32
32
  end
33
33
 
34
34
  def create_configuration_files
35
- copy_file "config/redis/shared.yml", "config/redis/shared.yml" if options.lockable?
36
- copy_file "config/initializers/omniauth.rb", "config/initializers/omniauth.rb" if omniauthable?
35
+ copy_file "config/redis/shared.yml", "config/redis/shared.yml" if options.lockable?
36
+ copy_file "config/initializers/omniauth.rb", "config/initializers/omniauth.rb" if omniauthable?
37
37
  end
38
38
 
39
39
  def add_environment_configurations
40
- ratelimit_code = <<~CODE
40
+ ratelimit_code = <<~CODE
41
41
  # Rate limit general requests by IP address in a rate of 1000 requests per hour
42
42
  config.middleware.use(Rack::Ratelimit, name: "General", rate: [1000, 1.hour], redis: Redis.new, logger: Rails.logger) { |env| ActionDispatch::Request.new(env).ip }
43
43
  CODE
@@ -63,64 +63,9 @@ class AuthenticationGenerator < Rails::Generators::NamedBase
63
63
  template "test_unit/fixtures.yml", "test/fixtures/#{fixture_file_name}.yml"
64
64
  end
65
65
 
66
- def add_application_controller_methods
67
- api_code = <<~CODE
68
- include ActionController::HttpAuthentication::Token::ControllerMethods
69
-
70
- before_action :set_current_request_details
71
- before_action :authenticate
72
-
73
- def require_sudo
74
- if Current.session.sudo_at < 30.minutes.ago
75
- render json: { error: "Enter your password to continue" }, status: :forbidden
76
- end
77
- end
78
-
79
- private
80
- def authenticate
81
- if session = authenticate_with_http_token { |token, _| Session.find_signed(token) }
82
- Current.session = session
83
- else
84
- request_http_token_authentication
85
- end
86
- end
87
-
88
- def set_current_request_details
89
- Current.user_agent = request.user_agent
90
- Current.ip_address = request.ip
91
- end
92
- CODE
93
-
94
- html_code = <<~CODE
95
- before_action :set_current_request_details
96
- before_action :authenticate
97
-
98
- def require_sudo
99
- if Current.session.sudo_at < 30.minutes.ago
100
- redirect_to new_sessions_sudo_path(proceed_to_url: request.url)
101
- end
102
- end
103
-
104
- private
105
- def authenticate
106
- if session = Session.find_by_id(cookies.signed[:session_token])
107
- Current.session = session
108
- else
109
- redirect_to sign_in_path
110
- end
111
- end
112
-
113
- def set_current_request_details
114
- Current.user_agent = request.user_agent
115
- Current.ip_address = request.ip
116
- end
117
- CODE
118
-
119
- inject_code = options.api? ? api_code : html_code
120
- inject_into_class "app/controllers/application_controller.rb", "ApplicationController", optimize_indentation(inject_code, 2), verbose: false
121
- end
122
-
123
66
  def create_controllers
67
+ template "controllers/#{format_folder}/application_controller.rb", "app/controllers/application_controller.rb", force: true
68
+
124
69
  directory "controllers/#{format_folder}/identity", "app/controllers/identity"
125
70
  template "controllers/#{format_folder}/passwords_controller.rb", "app/controllers/passwords_controller.rb"
126
71
  template "controllers/#{format_folder}/registrations_controller.rb", "app/controllers/registrations_controller.rb"
@@ -153,29 +98,31 @@ class AuthenticationGenerator < Rails::Generators::NamedBase
153
98
  def add_routes
154
99
  if omniauthable?
155
100
  route "post '/auth/:provider/callback', to: 'sessions/omniauth#create'"
156
- route "get '/auth/:provider/callback', to: 'sessions/omniauth#create'"
157
- route "get '/auth/failure', to: 'sessions/omniauth#failure'"
101
+ route "get '/auth/:provider/callback', to: 'sessions/omniauth#create'"
102
+ route "get '/auth/failure', to: 'sessions/omniauth#failure'"
158
103
  end
159
104
 
160
105
  if options.trackable?
161
106
  route "resources :events, only: :index", namespace: :authentications
162
107
  end
163
108
 
164
- route "resource :password_reset, only: [:new, :edit, :create, :update]", namespace: :identity
109
+ route "resource :password_reset, only: [:new, :edit, :create, :update]", namespace: :identity
165
110
  route "resource :email_verification, only: [:edit, :create]", namespace: :identity
166
- route "resource :email, only: [:edit, :update]", namespace: :identity
111
+ route "resource :email, only: [:edit, :update]", namespace: :identity
167
112
  route "resource :sudo, only: [:new, :create]", namespace: :sessions
113
+ route "resource :password, only: [:edit, :update]"
168
114
  route "resources :sessions, only: [:index, :show, :destroy]"
169
- route "resource :password, only: [:edit, :update]"
170
115
  route "post 'sign_up', to: 'registrations#create'"
171
- route "get 'sign_up', to: 'registrations#new'" unless options.api?
116
+ route "get 'sign_up', to: 'registrations#new'" unless options.api?
172
117
  route "post 'sign_in', to: 'sessions#create'"
173
- route "get 'sign_in', to: 'sessions#new'" unless options.api?
118
+ route "get 'sign_in', to: 'sessions#new'" unless options.api?
174
119
  end
175
120
 
176
121
  def create_test_files
177
122
  directory "test_unit/controllers/#{format_folder}", "test/controllers"
178
123
  directory "test_unit/system", "test/system" unless options.api?
124
+ template "test_unit/test_helper.rb", "test/test_helper.rb", force: true
125
+ template "test_unit/application_system_test_case.rb", "test/application_system_test_case.rb", force: true unless options.api?
179
126
  end
180
127
 
181
128
  private
@@ -0,0 +1,26 @@
1
+ class ApplicationController < ActionController::API
2
+ include ActionController::HttpAuthentication::Token::ControllerMethods
3
+
4
+ before_action :set_current_request_details
5
+ before_action :authenticate
6
+
7
+ def require_sudo
8
+ if Current.session.sudo_at < 30.minutes.ago
9
+ render json: { error: "Enter your password to continue" }, status: :forbidden
10
+ end
11
+ end
12
+
13
+ private
14
+ def authenticate
15
+ if session = authenticate_with_http_token { |token, _| Session.find_signed(token) }
16
+ Current.session = session
17
+ else
18
+ request_http_token_authentication
19
+ end
20
+ end
21
+
22
+ def set_current_request_details
23
+ Current.user_agent = request.user_agent
24
+ Current.ip_address = request.ip
25
+ end
26
+ end
@@ -0,0 +1,24 @@
1
+ class ApplicationController < ActionController::Base
2
+ before_action :set_current_request_details
3
+ before_action :authenticate
4
+
5
+ def require_sudo
6
+ if Current.session.sudo_at < 30.minutes.ago
7
+ redirect_to new_sessions_sudo_path(proceed_to_url: request.url)
8
+ end
9
+ end
10
+
11
+ private
12
+ def authenticate
13
+ if session = Session.find_by_id(cookies.signed[:session_token])
14
+ Current.session = session
15
+ else
16
+ redirect_to sign_in_path
17
+ end
18
+ end
19
+
20
+ def set_current_request_details
21
+ Current.user_agent = request.user_agent
22
+ Current.ip_address = request.ip
23
+ end
24
+ end
@@ -9,8 +9,8 @@ class <%= class_name %> < ApplicationRecord
9
9
  validates :email, presence: true, uniqueness: true
10
10
  validates_format_of :email, with: /\A[^@\s]+@[^@\s]+\z/
11
11
 
12
- validates_length_of :password, minimum: 12, allow_blank: true
13
- validates_format_of :password, with: /(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])/, allow_blank: true, message: "might easily be guessed"
12
+ validates_length_of :password, minimum: 12, allow_nil: true
13
+ validates_format_of :password, with: /(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])/, allow_nil: true, message: "might easily be guessed"
14
14
  <% if options.pwned? -%>
15
15
  validates :password, not_pwned: { message: "might easily be guessed" }
16
16
  <% end -%>
@@ -0,0 +1,15 @@
1
+ require "test_helper"
2
+
3
+ class ApplicationSystemTestCase < ActionDispatch::SystemTestCase
4
+ driven_by :selenium, using: :chrome, screen_size: [1400, 1400]
5
+
6
+ def sign_in_as(<%= singular_table_name %>)
7
+ visit sign_in_url
8
+ fill_in :email, with: <%= singular_table_name %>.email
9
+ fill_in :password, with: "Secret1*3*5*"
10
+ click_on "Sign in"
11
+
12
+ assert_current_path root_url
13
+ return <%= singular_table_name %>
14
+ end
15
+ end
@@ -37,8 +37,4 @@ class Identity::EmailVerificationsControllerTest < ActionDispatch::IntegrationTe
37
37
  assert_response :bad_request
38
38
  assert_equal "That email verification link is invalid", response.parsed_body["error"]
39
39
  end
40
-
41
- def sign_in_as(<%= singular_table_name %>)
42
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); [<%= singular_table_name %>, response.headers["X-Session-Token"]]
43
- end
44
40
  end
@@ -18,8 +18,4 @@ class Identity::EmailsControllerTest < ActionDispatch::IntegrationTest
18
18
  assert_response :forbidden
19
19
  assert_equal "Enter your password to continue", response.parsed_body["error"]
20
20
  end
21
-
22
- def sign_in_as(<%= singular_table_name %>)
23
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); [<%= singular_table_name %>, response.headers["X-Session-Token"]]
24
- end
25
21
  end
@@ -16,8 +16,4 @@ class PasswordsControllerTest < ActionDispatch::IntegrationTest
16
16
  assert_response :bad_request
17
17
  assert_equal "The current password you entered is incorrect", response.parsed_body["error"]
18
18
  end
19
-
20
- def sign_in_as(<%= singular_table_name %>)
21
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); [<%= singular_table_name %>, response.headers["X-Session-Token"]]
22
- end
23
19
  end
@@ -17,8 +17,4 @@ class Sessions::SudosControllerTest < ActionDispatch::IntegrationTest
17
17
  assert_response :bad_request
18
18
  assert_equal "The password you entered is incorrect", response.parsed_body["error"]
19
19
  end
20
-
21
- def sign_in_as(<%= singular_table_name %>)
22
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); [<%= singular_table_name %>, response.headers["X-Session-Token"]]
23
- end
24
20
  end
@@ -31,8 +31,4 @@ class SessionsControllerTest < ActionDispatch::IntegrationTest
31
31
  delete session_url(@<%= singular_table_name %>.sessions.last), headers: { "Authorization" => "Bearer #{@token}" }
32
32
  assert_response :no_content
33
33
  end
34
-
35
- def sign_in_as(<%= singular_table_name %>)
36
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); [<%= singular_table_name %>, response.headers["X-Session-Token"]]
37
- end
38
34
  end
@@ -37,8 +37,4 @@ class Identity::EmailVerificationsControllerTest < ActionDispatch::IntegrationTe
37
37
  assert_redirected_to edit_identity_email_url
38
38
  assert_equal "That email verification link is invalid", flash[:alert]
39
39
  end
40
-
41
- def sign_in_as(<%= singular_table_name %>)
42
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); <%= singular_table_name %>
43
- end
44
40
  end
@@ -28,8 +28,4 @@ class Identity::EmailsControllerTest < ActionDispatch::IntegrationTest
28
28
  patch identity_email_url, params: { email: "new_email@hey.com" }
29
29
  assert_redirected_to new_sessions_sudo_url(proceed_to_url: identity_email_url)
30
30
  end
31
-
32
- def sign_in_as(<%= singular_table_name %>)
33
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); <%= singular_table_name %>
34
- end
35
31
  end
@@ -21,8 +21,4 @@ class PasswordsControllerTest < ActionDispatch::IntegrationTest
21
21
  assert_redirected_to edit_password_url
22
22
  assert_equal "The current password you entered is incorrect", flash[:alert]
23
23
  end
24
-
25
- def sign_in_as(<%= singular_table_name %>)
26
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); <%= singular_table_name %>
27
- end
28
24
  end
@@ -19,8 +19,4 @@ class Sessions::SudosControllerTest < ActionDispatch::IntegrationTest
19
19
  post sessions_sudo_url, params: { password: "SecretWrong1*3", proceed_to_url: edit_password_url }
20
20
  assert_redirected_to new_sessions_sudo_url(proceed_to_url: edit_password_url)
21
21
  end
22
-
23
- def sign_in_as(<%= singular_table_name %>)
24
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); [<%= singular_table_name %>, response.headers["X-Session-Token"]]
25
- end
26
22
  end
@@ -45,8 +45,4 @@ class SessionsControllerTest < ActionDispatch::IntegrationTest
45
45
  follow_redirect!
46
46
  assert_redirected_to sign_in_url
47
47
  end
48
-
49
- def sign_in_as(<%= singular_table_name %>)
50
- post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); <%= singular_table_name %>
51
- end
52
48
  end
@@ -22,14 +22,4 @@ class Identity::EmailsTest < ApplicationSystemTestCase
22
22
 
23
23
  assert_text "We sent a verification email to your email address"
24
24
  end
25
-
26
- def sign_in_as(<%= singular_table_name %>)
27
- visit sign_in_url
28
- fill_in :email, with: <%= singular_table_name %>.email
29
- fill_in :password, with: "Secret1*3*5*"
30
- click_on "Sign in"
31
-
32
- assert_current_path root_url
33
- return <%= singular_table_name %>
34
- end
35
25
  end
@@ -15,14 +15,4 @@ class PasswordsTest < ApplicationSystemTestCase
15
15
 
16
16
  assert_text "Your password has been changed"
17
17
  end
18
-
19
- def sign_in_as(<%= singular_table_name %>)
20
- visit sign_in_url
21
- fill_in :email, with: <%= singular_table_name %>.email
22
- fill_in :password, with: "Secret1*3*5*"
23
- click_on "Sign in"
24
-
25
- assert_current_path root_url
26
- return <%= singular_table_name %>
27
- end
28
18
  end
@@ -12,14 +12,4 @@ class Sessions::SudosTest < ApplicationSystemTestCase
12
12
 
13
13
  assert_selector "h1", text: "Change your password"
14
14
  end
15
-
16
- def sign_in_as(<%= singular_table_name %>)
17
- visit sign_in_url
18
- fill_in :email, with: <%= singular_table_name %>.email
19
- fill_in :password, with: "Secret1*3*5*"
20
- click_on "Sign in"
21
-
22
- assert_current_path root_url
23
- return <%= singular_table_name %>
24
- end
25
15
  end
@@ -27,14 +27,4 @@ class SessionsTest < ApplicationSystemTestCase
27
27
  click_on "Log out"
28
28
  assert_text "That session has been logged out"
29
29
  end
30
-
31
- def sign_in_as(<%= singular_table_name %>)
32
- visit sign_in_url
33
- fill_in :email, with: <%= singular_table_name %>.email
34
- fill_in :password, with: "Secret1*3*5*"
35
- click_on "Sign in"
36
-
37
- assert_current_path root_url
38
- return <%= singular_table_name %>
39
- end
40
30
  end
@@ -0,0 +1,22 @@
1
+ ENV["RAILS_ENV"] ||= "test"
2
+ require_relative "../config/environment"
3
+ require "rails/test_help"
4
+
5
+ class ActiveSupport::TestCase
6
+ # Run tests in parallel with specified workers
7
+ parallelize(workers: :number_of_processors)
8
+
9
+ # Setup all fixtures in test/fixtures/*.yml for all tests in alphabetical order.
10
+ fixtures :all
11
+
12
+ # Add more helper methods to be used by all tests here...
13
+ <% if options.api? -%>
14
+ def sign_in_as(<%= singular_table_name %>)
15
+ post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); [<%= singular_table_name %>, response.headers["X-Session-Token"]]
16
+ end
17
+ <% else -%>
18
+ def sign_in_as(<%= singular_table_name %>)
19
+ post(sign_in_url, params: { email: <%= singular_table_name %>.email, password: "Secret1*3*5*" }); <%= singular_table_name %>
20
+ end
21
+ <% end -%>
22
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: authentication-zero
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.9.2
4
+ version: 2.9.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nixon
@@ -35,6 +35,7 @@ files:
35
35
  - lib/generators/authentication/authentication_generator.rb
36
36
  - lib/generators/authentication/templates/config/initializers/omniauth.rb
37
37
  - lib/generators/authentication/templates/config/redis/shared.yml
38
+ - lib/generators/authentication/templates/controllers/api/application_controller.rb.tt
38
39
  - lib/generators/authentication/templates/controllers/api/authentications/events_controller.rb.tt
39
40
  - lib/generators/authentication/templates/controllers/api/identity/email_verifications_controller.rb.tt
40
41
  - lib/generators/authentication/templates/controllers/api/identity/emails_controller.rb.tt
@@ -43,6 +44,7 @@ files:
43
44
  - lib/generators/authentication/templates/controllers/api/registrations_controller.rb.tt
44
45
  - lib/generators/authentication/templates/controllers/api/sessions/sudos_controller.rb.tt
45
46
  - lib/generators/authentication/templates/controllers/api/sessions_controller.rb.tt
47
+ - lib/generators/authentication/templates/controllers/html/application_controller.rb.tt
46
48
  - lib/generators/authentication/templates/controllers/html/authentications/events_controller.rb.tt
47
49
  - lib/generators/authentication/templates/controllers/html/identity/email_verifications_controller.rb.tt
48
50
  - lib/generators/authentication/templates/controllers/html/identity/emails_controller.rb.tt
@@ -77,6 +79,7 @@ files:
77
79
  - lib/generators/authentication/templates/models/locking.rb.tt
78
80
  - lib/generators/authentication/templates/models/model.rb.tt
79
81
  - lib/generators/authentication/templates/models/session.rb.tt
82
+ - lib/generators/authentication/templates/test_unit/application_system_test_case.rb.tt
80
83
  - lib/generators/authentication/templates/test_unit/controllers/api/identity/email_verifications_controller_test.rb.tt
81
84
  - lib/generators/authentication/templates/test_unit/controllers/api/identity/emails_controller_test.rb.tt
82
85
  - lib/generators/authentication/templates/test_unit/controllers/api/identity/password_resets_controller_test.rb.tt
@@ -98,6 +101,7 @@ files:
98
101
  - lib/generators/authentication/templates/test_unit/system/registrations_test.rb.tt
99
102
  - lib/generators/authentication/templates/test_unit/system/sessions/sudos_test.rb.tt
100
103
  - lib/generators/authentication/templates/test_unit/system/sessions_test.rb.tt
104
+ - lib/generators/authentication/templates/test_unit/test_helper.rb.tt
101
105
  homepage: https://github.com/lazaronixon/authentication-zero
102
106
  licenses:
103
107
  - MIT