authtrail 0.2.2 → 0.4.1
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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +20 -0
- data/LICENSE.txt +1 -1
- data/README.md +72 -16
- data/app/jobs/auth_trail/geocode_job.rb +3 -0
- data/lib/auth_trail/manager.rb +18 -23
- data/lib/auth_trail/version.rb +1 -1
- data/lib/authtrail.rb +1 -2
- data/lib/generators/authtrail/install_generator.rb +31 -1
- data/lib/generators/authtrail/templates/initializer.rb.tt +14 -0
- data/lib/generators/authtrail/templates/login_activities_migration.rb.tt +2 -5
- data/lib/generators/authtrail/templates/{login_activity_model.rb.tt → model.rb.tt} +0 -0
- data/lib/generators/authtrail/templates/model_lockbox.rb.tt +14 -0
- metadata +12 -122
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 22c5cb73374854a16a8581aad0618cf66033a7346784b16213ed58bb74d56b6b
|
4
|
+
data.tar.gz: 6666d786ba53acf7169c39e02eefcfdc7ae4211f26482bb47f142ca31d22885c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 6c429f790573ad4814b6c92eeff96cfc03b9b283046c5e1c23c425346674071792607c2f1c2f762ab588acaeb70badab8dafccaea38cc92c0c6944f63b7079fa
|
7
|
+
data.tar.gz: 9bfd5a70268d39c89f9792b3f3b6435935b55c11f201d690991053067e456b214463f912adce3dc879cb39f515322139a9cb690d7ca89ee98debb1640150d32d
|
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,23 @@
|
|
1
|
+
## 0.4.1 (2021-08-14)
|
2
|
+
|
3
|
+
- Improved error message when `geocoder` gem not installed
|
4
|
+
|
5
|
+
## 0.4.0 (2021-08-13)
|
6
|
+
|
7
|
+
- Disabled geocoding by default
|
8
|
+
- Made the `geocoder` gem an optional dependency
|
9
|
+
- Added `country_code` to geocoding
|
10
|
+
|
11
|
+
## 0.3.1 (2021-03-03)
|
12
|
+
|
13
|
+
- Added `--lockbox` option to install generator
|
14
|
+
|
15
|
+
## 0.3.0 (2021-03-01)
|
16
|
+
|
17
|
+
- Disabled geocoding by default for new installations
|
18
|
+
- Raise an exception instead of logging when auditing fails
|
19
|
+
- Removed support for Rails < 5.2 and Ruby < 2.6
|
20
|
+
|
1
21
|
## 0.2.2 (2020-11-21)
|
2
22
|
|
3
23
|
- Added `transform_method` option
|
data/LICENSE.txt
CHANGED
data/README.md
CHANGED
@@ -2,6 +2,8 @@
|
|
2
2
|
|
3
3
|
Track Devise login activity
|
4
4
|
|
5
|
+
**AuthTrail 0.4.0 was recently released** - see [how to upgrade](#upgrading)
|
6
|
+
|
5
7
|
:tangerine: Battle-tested at [Instacart](https://www.instacart.com/opensource)
|
6
8
|
|
7
9
|
[](https://github.com/ankane/authtrail/actions)
|
@@ -14,13 +16,22 @@ Add this line to your application’s Gemfile:
|
|
14
16
|
gem 'authtrail'
|
15
17
|
```
|
16
18
|
|
17
|
-
|
19
|
+
To encrypt email and IP addresses, install [Lockbox](https://github.com/ankane/lockbox) and [Blind Index](https://github.com/ankane/blind_index) and run:
|
20
|
+
|
21
|
+
```sh
|
22
|
+
rails generate authtrail:install --lockbox
|
23
|
+
rails db:migrate
|
24
|
+
```
|
25
|
+
|
26
|
+
If you prefer not to encrypt data, run:
|
18
27
|
|
19
28
|
```sh
|
20
29
|
rails generate authtrail:install
|
21
30
|
rails db:migrate
|
22
31
|
```
|
23
32
|
|
33
|
+
To enable geocoding, see the [Geocoding section](#geocoding).
|
34
|
+
|
24
35
|
## How It Works
|
25
36
|
|
26
37
|
A `LoginActivity` record is created every time a user tries to login. You can then use this information to detect suspicious behavior. Data includes:
|
@@ -47,7 +58,7 @@ AuthTrail.exclude_method = lambda do |data|
|
|
47
58
|
end
|
48
59
|
```
|
49
60
|
|
50
|
-
Add or modify data
|
61
|
+
Add or modify data - also add new fields to the `login_activities` table if needed
|
51
62
|
|
52
63
|
```ruby
|
53
64
|
AuthTrail.transform_method = lambda do |data, request|
|
@@ -95,50 +106,83 @@ The `LoginActivity` model uses a [polymorphic association](https://guides.rubyon
|
|
95
106
|
|
96
107
|
## Geocoding
|
97
108
|
|
98
|
-
|
109
|
+
AuthTrail uses [Geocoder](https://github.com/alexreisner/geocoder) for geocoding. We recommend configuring [local geocoding](#local-geocoding) or [load balancer geocoding](#load-balancer-geocoding) so IP addresses are not sent to a 3rd party service. If you do use a 3rd party service and adhere to GDPR, be sure to add it to your subprocessor list.
|
110
|
+
|
111
|
+
To enable geocoding, add this line to your application’s Gemfile:
|
99
112
|
|
100
113
|
```ruby
|
101
|
-
|
114
|
+
gem 'geocoder'
|
102
115
|
```
|
103
116
|
|
104
|
-
|
117
|
+
And update `config/initializers/authtrail.rb`:
|
105
118
|
|
106
119
|
```ruby
|
107
|
-
AuthTrail.
|
120
|
+
AuthTrail.geocode = true
|
108
121
|
```
|
109
122
|
|
110
|
-
|
123
|
+
Geocoding is performed in a background job so it doesn’t slow down web requests. Set the job queue with:
|
111
124
|
|
112
|
-
|
125
|
+
```ruby
|
126
|
+
AuthTrail.job_queue = :low_priority
|
127
|
+
```
|
113
128
|
|
114
|
-
|
129
|
+
### Local Geocoding
|
130
|
+
|
131
|
+
For privacy and performance, we recommend geocoding locally. Add this line to your application’s Gemfile:
|
115
132
|
|
116
133
|
```ruby
|
117
134
|
gem 'maxminddb'
|
118
135
|
```
|
119
136
|
|
120
|
-
|
137
|
+
For city-level geocoding, download the [GeoLite2 City database](https://dev.maxmind.com/geoip/geoip2/geolite2/) and create `config/initializers/geocoder.rb` with:
|
121
138
|
|
122
139
|
```ruby
|
123
140
|
Geocoder.configure(
|
124
141
|
ip_lookup: :geoip2,
|
125
142
|
geoip2: {
|
126
|
-
file:
|
143
|
+
file: "path/to/GeoLite2-City.mmdb"
|
144
|
+
}
|
145
|
+
)
|
146
|
+
```
|
147
|
+
|
148
|
+
For country-level geocoding, install the `geoip-database` package. It’s preinstalled on Heroku. For Ubuntu, use:
|
149
|
+
|
150
|
+
```sh
|
151
|
+
sudo apt-get install geoip-database
|
152
|
+
```
|
153
|
+
|
154
|
+
And create `config/initializers/geocoder.rb` with:
|
155
|
+
|
156
|
+
```ruby
|
157
|
+
Geocoder.configure(
|
158
|
+
ip_lookup: :maxmind_local,
|
159
|
+
maxmind_local: {
|
160
|
+
file: "/usr/share/GeoIP/GeoIP.dat",
|
161
|
+
package: :country
|
127
162
|
}
|
128
163
|
)
|
129
164
|
```
|
130
165
|
|
131
|
-
|
166
|
+
### Load Balancer Geocoding
|
167
|
+
|
168
|
+
Some load balancers can add geocoding information to request headers.
|
132
169
|
|
133
|
-
|
170
|
+
- [nginx](https://nginx.org/en/docs/http/ngx_http_geoip_module.html)
|
171
|
+
- [Google Cloud](https://cloud.google.com/load-balancing/docs/custom-headers)
|
172
|
+
- [Cloudflare](https://support.cloudflare.com/hc/en-us/articles/200168236-Configuring-Cloudflare-IP-Geolocation)
|
134
173
|
|
135
174
|
```ruby
|
136
|
-
|
137
|
-
|
138
|
-
|
175
|
+
AuthTrail.geocode = false
|
176
|
+
|
177
|
+
AuthTrail.transform_method = lambda do |data, request|
|
178
|
+
data[:country] = request.headers["<country-header>"]
|
179
|
+
data[:region] = request.headers["<region-header>"]
|
180
|
+
data[:city] = request.headers["<city-header>"]
|
139
181
|
end
|
140
182
|
```
|
141
183
|
|
184
|
+
Check out [this example](https://github.com/ankane/authtrail/issues/40)
|
185
|
+
|
142
186
|
## Other Notes
|
143
187
|
|
144
188
|
We recommend using this in addition to Devise’s `Lockable` module and [Rack::Attack](https://github.com/kickstarter/rack-attack).
|
@@ -147,6 +191,18 @@ Check out [Hardening Devise](https://ankane.org/hardening-devise) and [Secure Ra
|
|
147
191
|
|
148
192
|
## Upgrading
|
149
193
|
|
194
|
+
### 0.4.0
|
195
|
+
|
196
|
+
There are two notable changes to geocoding:
|
197
|
+
|
198
|
+
1. Geocoding is now disabled by default (this was already the case for new installations with 0.3.0+). Check out the instructions for [how to enable it](#geocoding) (you may need to create `config/initializers/authtrail.rb`).
|
199
|
+
|
200
|
+
2. The `geocoder` gem is now an optional dependency. To use geocoding, add it to your Gemfile:
|
201
|
+
|
202
|
+
```ruby
|
203
|
+
gem 'geocoder'
|
204
|
+
```
|
205
|
+
|
150
206
|
### 0.2.0
|
151
207
|
|
152
208
|
To store latitude and longitude, create a migration with:
|
@@ -8,6 +8,8 @@ module AuthTrail
|
|
8
8
|
result =
|
9
9
|
begin
|
10
10
|
Geocoder.search(login_activity.ip).first
|
11
|
+
rescue NameError
|
12
|
+
raise "Add the geocoder gem to your Gemfile to use geocoding"
|
11
13
|
rescue => e
|
12
14
|
Rails.logger.info "Geocode failed: #{e.message}"
|
13
15
|
nil
|
@@ -18,6 +20,7 @@ module AuthTrail
|
|
18
20
|
city: result.try(:city),
|
19
21
|
region: result.try(:state),
|
20
22
|
country: result.try(:country),
|
23
|
+
country_code: result.try(:country_code),
|
21
24
|
latitude: result.try(:latitude),
|
22
25
|
longitude: result.try(:longitude)
|
23
26
|
}
|
data/lib/auth_trail/manager.rb
CHANGED
@@ -2,34 +2,29 @@ module AuthTrail
|
|
2
2
|
module Manager
|
3
3
|
class << self
|
4
4
|
def after_set_user(user, auth, opts)
|
5
|
-
|
6
|
-
AuthTrail.safely do
|
7
|
-
request = ActionDispatch::Request.new(auth.env)
|
5
|
+
request = ActionDispatch::Request.new(auth.env)
|
8
6
|
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
end
|
7
|
+
AuthTrail.track(
|
8
|
+
strategy: detect_strategy(auth),
|
9
|
+
scope: opts[:scope].to_s,
|
10
|
+
identity: AuthTrail.identity_method.call(request, opts, user),
|
11
|
+
success: true,
|
12
|
+
request: request,
|
13
|
+
user: user
|
14
|
+
)
|
18
15
|
end
|
19
16
|
|
20
17
|
def before_failure(env, opts)
|
21
|
-
|
22
|
-
request = ActionDispatch::Request.new(env)
|
18
|
+
request = ActionDispatch::Request.new(env)
|
23
19
|
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
end
|
20
|
+
AuthTrail.track(
|
21
|
+
strategy: detect_strategy(env["warden"]),
|
22
|
+
scope: opts[:scope].to_s,
|
23
|
+
identity: AuthTrail.identity_method.call(request, opts, nil),
|
24
|
+
success: false,
|
25
|
+
request: request,
|
26
|
+
failure_reason: opts[:message].to_s
|
27
|
+
)
|
33
28
|
end
|
34
29
|
|
35
30
|
private
|
data/lib/auth_trail/version.rb
CHANGED
data/lib/authtrail.rb
CHANGED
@@ -1,5 +1,4 @@
|
|
1
1
|
# dependencies
|
2
|
-
require "geocoder"
|
3
2
|
require "warden"
|
4
3
|
|
5
4
|
# modules
|
@@ -11,7 +10,7 @@ module AuthTrail
|
|
11
10
|
class << self
|
12
11
|
attr_accessor :exclude_method, :geocode, :track_method, :identity_method, :job_queue, :transform_method
|
13
12
|
end
|
14
|
-
self.geocode =
|
13
|
+
self.geocode = false
|
15
14
|
self.identity_method = lambda do |request, opts, user|
|
16
15
|
if user
|
17
16
|
user.try(:email)
|
@@ -6,17 +6,47 @@ module Authtrail
|
|
6
6
|
include ActiveRecord::Generators::Migration
|
7
7
|
source_root File.join(__dir__, "templates")
|
8
8
|
|
9
|
+
class_option :lockbox, type: :boolean
|
10
|
+
|
9
11
|
def copy_migration
|
10
12
|
migration_template "login_activities_migration.rb", "db/migrate/create_login_activities.rb", migration_version: migration_version
|
11
13
|
end
|
12
14
|
|
15
|
+
def copy_templates
|
16
|
+
template "initializer.rb", "config/initializers/authtrail.rb"
|
17
|
+
end
|
18
|
+
|
13
19
|
def generate_model
|
14
|
-
|
20
|
+
if lockbox?
|
21
|
+
template "model_lockbox.rb", "app/models/login_activity.rb"
|
22
|
+
else
|
23
|
+
template "model.rb", "app/models/login_activity.rb"
|
24
|
+
end
|
15
25
|
end
|
16
26
|
|
17
27
|
def migration_version
|
18
28
|
"[#{ActiveRecord::VERSION::MAJOR}.#{ActiveRecord::VERSION::MINOR}]"
|
19
29
|
end
|
30
|
+
|
31
|
+
def identity_column
|
32
|
+
if lockbox?
|
33
|
+
"t.text :identity_ciphertext\n t.string :identity_bidx, index: true"
|
34
|
+
else
|
35
|
+
"t.string :identity, index: true"
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
def ip_column
|
40
|
+
if lockbox?
|
41
|
+
"t.text :ip_ciphertext\n t.string :ip_bidx, index: true"
|
42
|
+
else
|
43
|
+
"t.string :ip, index: true"
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
def lockbox?
|
48
|
+
options[:lockbox]
|
49
|
+
end
|
20
50
|
end
|
21
51
|
end
|
22
52
|
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
# set to true for geocoding (and add the geocoder gem to your Gemfile)
|
2
|
+
# we recommend configuring local geocoding as well
|
3
|
+
# see https://github.com/ankane/authtrail#geocoding
|
4
|
+
AuthTrail.geocode = false
|
5
|
+
|
6
|
+
# add or modify data
|
7
|
+
# AuthTrail.transform_method = lambda do |data, request|
|
8
|
+
# data[:request_id] = request.request_id
|
9
|
+
# end
|
10
|
+
|
11
|
+
# exclude certain attempts from tracking
|
12
|
+
# AuthTrail.exclude_method = lambda do |data|
|
13
|
+
# data[:identity] == "capybara@example.org"
|
14
|
+
# end
|
@@ -3,12 +3,12 @@ class <%= migration_class_name %> < ActiveRecord::Migration<%= migration_version
|
|
3
3
|
create_table :login_activities do |t|
|
4
4
|
t.string :scope
|
5
5
|
t.string :strategy
|
6
|
-
|
6
|
+
<%= identity_column %>
|
7
7
|
t.boolean :success
|
8
8
|
t.string :failure_reason
|
9
9
|
t.references :user, polymorphic: true
|
10
10
|
t.string :context
|
11
|
-
|
11
|
+
<%= ip_column %>
|
12
12
|
t.text :user_agent
|
13
13
|
t.text :referrer
|
14
14
|
t.string :city
|
@@ -18,8 +18,5 @@ class <%= migration_class_name %> < ActiveRecord::Migration<%= migration_version
|
|
18
18
|
t.float :longitude
|
19
19
|
t.datetime :created_at
|
20
20
|
end
|
21
|
-
|
22
|
-
add_index :login_activities, :identity
|
23
|
-
add_index :login_activities, :ip
|
24
21
|
end
|
25
22
|
end
|
File without changes
|
@@ -0,0 +1,14 @@
|
|
1
|
+
class LoginActivity < ApplicationRecord
|
2
|
+
belongs_to :user, polymorphic: true, optional: true
|
3
|
+
|
4
|
+
encrypts :identity, :ip
|
5
|
+
blind_index :identity, :ip
|
6
|
+
|
7
|
+
before_save :reduce_precision
|
8
|
+
|
9
|
+
# reduce precision to city level to protect IP
|
10
|
+
def reduce_precision
|
11
|
+
self.latitude = latitude&.round(1) if try(:latitude_changed?)
|
12
|
+
self.longitude = longitude&.round(1) if try(:longitude_changed?)
|
13
|
+
end
|
14
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: authtrail
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.4.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Andrew Kane
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2021-08-14 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: railties
|
@@ -16,28 +16,28 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - ">="
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: '5'
|
19
|
+
version: '5.2'
|
20
20
|
type: :runtime
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
24
|
- - ">="
|
25
25
|
- !ruby/object:Gem::Version
|
26
|
-
version: '5'
|
26
|
+
version: '5.2'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: activerecord
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
31
|
- - ">="
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: '5'
|
33
|
+
version: '5.2'
|
34
34
|
type: :runtime
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
38
|
- - ">="
|
39
39
|
- !ruby/object:Gem::Version
|
40
|
-
version: '5'
|
40
|
+
version: '5.2'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: warden
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -52,120 +52,8 @@ dependencies:
|
|
52
52
|
- - ">="
|
53
53
|
- !ruby/object:Gem::Version
|
54
54
|
version: '0'
|
55
|
-
- !ruby/object:Gem::Dependency
|
56
|
-
name: geocoder
|
57
|
-
requirement: !ruby/object:Gem::Requirement
|
58
|
-
requirements:
|
59
|
-
- - ">="
|
60
|
-
- !ruby/object:Gem::Version
|
61
|
-
version: '0'
|
62
|
-
type: :runtime
|
63
|
-
prerelease: false
|
64
|
-
version_requirements: !ruby/object:Gem::Requirement
|
65
|
-
requirements:
|
66
|
-
- - ">="
|
67
|
-
- !ruby/object:Gem::Version
|
68
|
-
version: '0'
|
69
|
-
- !ruby/object:Gem::Dependency
|
70
|
-
name: bundler
|
71
|
-
requirement: !ruby/object:Gem::Requirement
|
72
|
-
requirements:
|
73
|
-
- - ">="
|
74
|
-
- !ruby/object:Gem::Version
|
75
|
-
version: '0'
|
76
|
-
type: :development
|
77
|
-
prerelease: false
|
78
|
-
version_requirements: !ruby/object:Gem::Requirement
|
79
|
-
requirements:
|
80
|
-
- - ">="
|
81
|
-
- !ruby/object:Gem::Version
|
82
|
-
version: '0'
|
83
|
-
- !ruby/object:Gem::Dependency
|
84
|
-
name: rake
|
85
|
-
requirement: !ruby/object:Gem::Requirement
|
86
|
-
requirements:
|
87
|
-
- - ">="
|
88
|
-
- !ruby/object:Gem::Version
|
89
|
-
version: '0'
|
90
|
-
type: :development
|
91
|
-
prerelease: false
|
92
|
-
version_requirements: !ruby/object:Gem::Requirement
|
93
|
-
requirements:
|
94
|
-
- - ">="
|
95
|
-
- !ruby/object:Gem::Version
|
96
|
-
version: '0'
|
97
|
-
- !ruby/object:Gem::Dependency
|
98
|
-
name: minitest
|
99
|
-
requirement: !ruby/object:Gem::Requirement
|
100
|
-
requirements:
|
101
|
-
- - ">="
|
102
|
-
- !ruby/object:Gem::Version
|
103
|
-
version: '5'
|
104
|
-
type: :development
|
105
|
-
prerelease: false
|
106
|
-
version_requirements: !ruby/object:Gem::Requirement
|
107
|
-
requirements:
|
108
|
-
- - ">="
|
109
|
-
- !ruby/object:Gem::Version
|
110
|
-
version: '5'
|
111
|
-
- !ruby/object:Gem::Dependency
|
112
|
-
name: combustion
|
113
|
-
requirement: !ruby/object:Gem::Requirement
|
114
|
-
requirements:
|
115
|
-
- - ">="
|
116
|
-
- !ruby/object:Gem::Version
|
117
|
-
version: '0'
|
118
|
-
type: :development
|
119
|
-
prerelease: false
|
120
|
-
version_requirements: !ruby/object:Gem::Requirement
|
121
|
-
requirements:
|
122
|
-
- - ">="
|
123
|
-
- !ruby/object:Gem::Version
|
124
|
-
version: '0'
|
125
|
-
- !ruby/object:Gem::Dependency
|
126
|
-
name: rails
|
127
|
-
requirement: !ruby/object:Gem::Requirement
|
128
|
-
requirements:
|
129
|
-
- - ">="
|
130
|
-
- !ruby/object:Gem::Version
|
131
|
-
version: '0'
|
132
|
-
type: :development
|
133
|
-
prerelease: false
|
134
|
-
version_requirements: !ruby/object:Gem::Requirement
|
135
|
-
requirements:
|
136
|
-
- - ">="
|
137
|
-
- !ruby/object:Gem::Version
|
138
|
-
version: '0'
|
139
|
-
- !ruby/object:Gem::Dependency
|
140
|
-
name: sqlite3
|
141
|
-
requirement: !ruby/object:Gem::Requirement
|
142
|
-
requirements:
|
143
|
-
- - ">="
|
144
|
-
- !ruby/object:Gem::Version
|
145
|
-
version: '0'
|
146
|
-
type: :development
|
147
|
-
prerelease: false
|
148
|
-
version_requirements: !ruby/object:Gem::Requirement
|
149
|
-
requirements:
|
150
|
-
- - ">="
|
151
|
-
- !ruby/object:Gem::Version
|
152
|
-
version: '0'
|
153
|
-
- !ruby/object:Gem::Dependency
|
154
|
-
name: devise
|
155
|
-
requirement: !ruby/object:Gem::Requirement
|
156
|
-
requirements:
|
157
|
-
- - ">="
|
158
|
-
- !ruby/object:Gem::Version
|
159
|
-
version: '0'
|
160
|
-
type: :development
|
161
|
-
prerelease: false
|
162
|
-
version_requirements: !ruby/object:Gem::Requirement
|
163
|
-
requirements:
|
164
|
-
- - ">="
|
165
|
-
- !ruby/object:Gem::Version
|
166
|
-
version: '0'
|
167
55
|
description:
|
168
|
-
email: andrew@
|
56
|
+
email: andrew@ankane.org
|
169
57
|
executables: []
|
170
58
|
extensions: []
|
171
59
|
extra_rdoc_files: []
|
@@ -179,8 +67,10 @@ files:
|
|
179
67
|
- lib/auth_trail/version.rb
|
180
68
|
- lib/authtrail.rb
|
181
69
|
- lib/generators/authtrail/install_generator.rb
|
70
|
+
- lib/generators/authtrail/templates/initializer.rb.tt
|
182
71
|
- lib/generators/authtrail/templates/login_activities_migration.rb.tt
|
183
|
-
- lib/generators/authtrail/templates/
|
72
|
+
- lib/generators/authtrail/templates/model.rb.tt
|
73
|
+
- lib/generators/authtrail/templates/model_lockbox.rb.tt
|
184
74
|
homepage: https://github.com/ankane/authtrail
|
185
75
|
licenses:
|
186
76
|
- MIT
|
@@ -193,14 +83,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
193
83
|
requirements:
|
194
84
|
- - ">="
|
195
85
|
- !ruby/object:Gem::Version
|
196
|
-
version: '2.
|
86
|
+
version: '2.6'
|
197
87
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
198
88
|
requirements:
|
199
89
|
- - ">="
|
200
90
|
- !ruby/object:Gem::Version
|
201
91
|
version: '0'
|
202
92
|
requirements: []
|
203
|
-
rubygems_version: 3.
|
93
|
+
rubygems_version: 3.2.22
|
204
94
|
signing_key:
|
205
95
|
specification_version: 4
|
206
96
|
summary: Track Devise login activity
|