Last active
February 26, 2017 22:16
-
-
Save jhubert/2975dc03f1201203cd9961328a811bdd to your computer and use it in GitHub Desktop.
The before code for my article on refactoring in the real world
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Disable users who have had no activity in the last 14 days | |
class DisableInactiveUsersJob | |
include Sidekiq::Worker | |
def perform | |
now = Time.zone.now | |
target_users = users_with_no_activity_since(now - 14.days) | |
# Load the ids before we update the users or the pluck query will return nothing | |
target_user_ids = target_users.pluck(:id) | |
target_users.update_all(disabled_at: now) | |
target_user_ids.each { |user_id| track_disabling_of(user_id) } | |
end | |
private | |
def track_disabling_of(user_id) | |
Activity.track( | |
'user:disable', | |
target_type: User.name, | |
target_id: user_id | |
) | |
end | |
def users_with_no_activity_since(time) | |
# fairly complicated query for figuring out if users have had activity | |
# omitting for simplicity | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
require 'test_helper' | |
class DisableInactiveUsersJobTest < ActiveSupport::TestCase | |
test "should disable all enabled users who have not had any activity" do | |
DisableInactiveUsers.new.perform | |
User.all.each do |user| | |
assert_predicate user, :disabled? | |
assert Activity::DB.where(target: user, activity: 'user:disable').exists? | |
end | |
end | |
test "should not disable users who are already disabled" do | |
melissa = users(:melissa) | |
melissa.disable! | |
DisableInactiveUsers.new.perform | |
assert_predicate melissa, :disabled? | |
refute Activity::DB.where(target: melissa, activity: 'user:disable').exists? | |
end | |
test "should not disable a user that has had activity within 14 days" do | |
melissa = users(:melissa) | |
Activity.create(activity: 'session:create', user: melissa, created_at: 13.days.ago) | |
DisableInactiveUsers.new.perform | |
melissa.reload | |
assert_predicate melissa, :enabled? | |
refute Activity::DB.where(target: melissa, activity: 'user:disable').exists? | |
end | |
test "should disable a user that has had activity more than 14 days ago" do | |
melissa = users(:melissa) | |
Activity.create(activity: 'session:create', user: melissa, created_at: 15.days.ago) | |
DisableInactiveUsers.new.perform | |
melissa.reload | |
assert_predicate melissa, :disabled? | |
assert Activity::DB.where(target: melissa, activity: 'user:disable').exists? | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Give an active record model the ability to be enabled / disabled | |
# based on the timestamp value of a column | |
module Disableable | |
extend ActiveSupport::Concern | |
included do | |
scope :enabled, ->(time = Time.zone.now) { where("disabled_at IS NULL OR disabled_at > ?", time) } | |
scope :disabled, ->(time = Time.zone.now) { where("disabled_at < ?", time) } | |
end | |
def disable(time = Time.zone.now) | |
set_disabled_at_value(time) | |
end | |
def disable!(time = Time.zone.now) | |
update_disabled_at_value(time) | |
end | |
def enable | |
set_disabled_at_value(nil) | |
end | |
def enable! | |
update_disabled_at_value(nil) | |
end | |
def enabled?(time = Time.zone.now) | |
!disabled?(time) | |
end | |
def disabled?(time = Time.zone.now) | |
disabled_at && disabled_at <= time | |
end | |
private | |
def set_disabled_at_value(value) # rubocop:disable Style/AccessorMethodName | |
self.disabled_at = value | |
end | |
def update_disabled_at_value(value) | |
update_attribute(:disabled_at, value) | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Disable or enable a User by their id | |
class Users::DisablementsController < ApplicationController | |
before_action :load_user, only: [:create, :destroy] | |
def create | |
@user.disable! | |
track_activity('user:disable', target: @user) | |
redirect_to user_path(@user), notice: I18n.t('user.disablements.create_notice') | |
end | |
def destroy | |
@user.enable! | |
track_activity('user:enable', target: @user) | |
redirect_to user_path(@user), notice: I18n.t('user.disablements.destroy_notice') | |
end | |
private | |
def load_user | |
@user = User.find(params[:user_id]) | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
require 'test_helper' | |
class Users::DisablementsControllerTest < ActionController::TestCase | |
include AuthenticatedAsAdmin | |
test "should enable the intended user" do | |
user = users(:melissa) | |
user.disable! | |
@controller.expects(:track_activity).with('user:enable', target: user) | |
delete :destroy, user_id: user.id | |
user.reload | |
assert_predicate user, :enabled? | |
end | |
test "should disable the intended user" do | |
user = users(:melissa) | |
@controller.expects(:track_activity).with('user:disable', target: user) | |
post :create, user_id: user.id | |
user.reload | |
assert_predicate user, :disabled? | |
end | |
# ... more tests for redirection, error messages, etc... | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class User < ActiveRecord::Base | |
include Disableable | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment