From 416076610e7b1674669ad33bae604155f55a3d02 Mon Sep 17 00:00:00 2001 From: Grzegorz Bizon Date: Tue, 17 Jul 2018 14:50:04 +0200 Subject: [PATCH] Implement scaffold of authentication activity metrics --- config/initializers/warden.rb | 12 +++++ lib/gitlab/auth/activity.rb | 69 +++++++++++++++++++++++++++ spec/lib/gitlab/auth/activity_spec.rb | 11 +++++ 3 files changed, 92 insertions(+) create mode 100644 lib/gitlab/auth/activity.rb create mode 100644 spec/lib/gitlab/auth/activity_spec.rb diff --git a/config/initializers/warden.rb b/config/initializers/warden.rb index 8cc36820d3c..c75a76a3118 100644 --- a/config/initializers/warden.rb +++ b/config/initializers/warden.rb @@ -5,17 +5,29 @@ Rails.application.configure do |config| Warden::Manager.before_failure(scope: :user) do |env, opts| Gitlab::Auth::BlockedUserTracker.log_if_user_blocked(env) + + Gitlab::Auth::Activity.new(opts).user_authentication_failed! end Warden::Manager.after_authentication(scope: :user) do |user, auth, opts| ActiveSession.cleanup(user) + + Gitlab::Auth::Activity.new(opts).user_authenticated! end Warden::Manager.after_set_user(scope: :user, only: :fetch) do |user, auth, opts| ActiveSession.set(user, auth.request) + + Gitlab::Auth::Activity.new(opts).user_session_fetched! + end + + Warden::Manager.after_set_user(scope: :user, only: :set_user) do |user, auth, opts| + Gitlab::Auth::Activity.new(opts).user_set_manually! end Warden::Manager.before_logout(scope: :user) do |user, auth, opts| ActiveSession.destroy(user || auth.user, auth.request.session.id) + + Gitlab::Auth::Activity.new(opts).user_logout! end end diff --git a/lib/gitlab/auth/activity.rb b/lib/gitlab/auth/activity.rb new file mode 100644 index 00000000000..c0254ca81cd --- /dev/null +++ b/lib/gitlab/auth/activity.rb @@ -0,0 +1,69 @@ +module Gitlab + module Auth + ## + # Metrics and logging for user authentication activity. + # + class Activity + extend Gitlab::Utils::StrongMemoize + + COUNTERS = { + user_authenticated: 'Counter of total successful authentication events', + user_unauthenticated: 'Counter of total authentication failures', + user_not_found: 'Counter of total failed log-ins when user is unknown', + user_password_invalid: 'Counter of failed log-ins with invalid password', + user_session_fetched: 'Counter of total sessions fetched', + user_session_override: 'Counter of manual log-ins and sessions overrides', + user_signed_out: 'Counter of total user sign out events' + }.freeze + + def initialize(opts) + @opts = opts + end + + def user_authentication_failed! + self.class.user_unauthenticated_counter.increment + + case @opts[:message] + when :not_found_in_database + self.class.user_not_found_counter.increment + when :invalid + self.class.user_password_invalid_counter.increment + end + end + + def user_authenticated! + self.class.user_authenticated_counter.increment + end + + def user_session_fetched! + self.class.user_session_fetched_counter.increment + end + + def user_set_manually! + self.class.user_session_override_counter.increment + end + + def user_logout! + self.class.user_signed_out_counter.increment + end + + class StubCounter + def initialize(metric) + Rails.logger.warn("METRIC #{metric}") + end + + def increment + end + end + + COUNTERS.each_pair do |metric, description| + define_singleton_method("#{metric}_counter") do + strong_memoize(metric) do + StubCounter.new(metric) + # Gitlab::Metrics.counter("gitlab_auth_#{metric}_total", description) + end + end + end + end + end +end diff --git a/spec/lib/gitlab/auth/activity_spec.rb b/spec/lib/gitlab/auth/activity_spec.rb new file mode 100644 index 00000000000..311c29010b3 --- /dev/null +++ b/spec/lib/gitlab/auth/activity_spec.rb @@ -0,0 +1,11 @@ +require 'spec_helper' + +describe Gitlab::Auth::Activity do + describe 'counters' do + it 'has all static counters defined' do + described_class::COUNTERS.each_key do |metric| + expect(described_class).to respond_to("#{metric}_counter") + end + end + end +end