Skip to content

Commit

Permalink
Geovelocity and Password change after login working with session_id
Browse files Browse the repository at this point in the history
  • Loading branch information
DeadKennedyx committed Jan 10, 2024
1 parent d68a8bc commit b67b7ae
Show file tree
Hide file tree
Showing 5 changed files with 72 additions and 15 deletions.
20 changes: 20 additions & 0 deletions lib/usual_suspect/sessions_controller_extension.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
require 'geocoder'

module UsualSuspect
module SessionsControllerExtension
extend ActiveSupport::Concern

def track_usual_suspect_login
user_ip = request.remote_ip
location = Geocoder.search(user_ip).first
session_token = generate_unique_session_token
session[:usual_suspect_session_token] = session_token

current_user.update_login(user_ip, location, session_token) if current_user
end

def generate_unique_session_token
SecureRandom.hex(10)
end
end
end
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,14 @@ class CreateUsualSuspectEvents < ActiveRecord::Migration[6.0]
t.boolean :password_change_after_login
t.boolean :geovelocity_failed
t.boolean :vpn_usage
t.string :ip_location
t.string :sign_in_ip
t.string :city
t.string :country
t.string :latitude
t.string :longitude
t.string :session_token

t.index :session_token

t.timestamps
end
Expand Down
2 changes: 2 additions & 0 deletions lib/usual_suspect/tasks/templates/usual_suspect_event.rb.erb
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,6 @@ class UsualSuspectEvent < ApplicationRecord
include UsualSuspect::Event

belongs_to :user

validates :session_token, presence: true
end
54 changes: 41 additions & 13 deletions lib/usual_suspect/user_extension.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,35 +2,63 @@ module UsualSuspect
module UserExtension
extend ActiveSupport::Concern

included do
after_update :check_for_suspicious_password_change, if: :saved_change_to_password?
end
def update_login(ip, location, session_token)
event = UsualSuspectEvent.new(user: self, session_token: session_token)

def update_login_times
event = UsualSuspectEvent.find_or_initialize_by(user: self)
event.last_sign_in_at = event.sign_in_at
event.sign_in_at = Time.current
event.assign_attributes(
sign_in_at: Time.current,
sign_in_ip: ip,
city: location.city,
country: location.country,
latitude: location.latitude,
longitude: location.longitude
)

event.save

check_geo_velocity(event)
end

private

def check_for_suspicious_password_change
event = UsualSuspectEvent.find_by(user: self)
def check_geo_velocity(current_event)
last_event = UsualSuspectEvent.where(user: self).order(:sign_in_at).second_to_last

if last_event && geo_velocity_failed?(last_event, current_event)
current_event.update(geovelocity_failed: true)
end
end

def check_for_suspicious_password_change(session_token)
event = UsualSuspectEvent.find_by(user: self, session_token: session_token)

if event && event.sign_in_at && Time.current - event.sign_in_at < suspicious_threshold
log_suspicious_activity('Password changed shortly after login')
event.update(password_change_after_login: true)
end
end

private

def geo_velocity_failed?(last_event, current_event)
distance = Geocoder::Calculations.distance_between(
[last_event.latitude, last_event.longitude],
[current_event.latitude, current_event.longitude]
)

time_difference_hours = (current_event.sign_in_at - last_event.sign_in_at) / 1.hour

velocity = distance / time_difference_hours

max_feasible_velocity = 926

velocity > max_feasible_velocity
end

def suspicious_threshold
1.minutes
5.minutes
end

def log_suspicious_activity(activity)
# Implement logging mechanism
# This could be a simple log, an entry in a database table, or an alert
Rails.logger.warn("[UsualSuspect] Activity: #{activity}")
end
end
Expand Down
2 changes: 1 addition & 1 deletion usual_suspect.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ Gem::Specification.new do |spec|
spec.require_paths = ["lib"]

# Uncomment to register a new dependency of your gem
# spec.add_dependency "example-gem", "~> 1.0"
spec.add_dependency "geocoder", "~> 1.8.2"

# For more information and examples about making a new gem, checkout our
# guide at: https://bundler.io/guides/creating_gem.html
Expand Down

0 comments on commit b67b7ae

Please sign in to comment.