@@ -1,6 +1,11 @@
 require File.expand_path('../boot', __FILE__)

-require 'rails/all'
+# Pick the frameworks you want:
+require 'active_record/railtie'
+require 'action_controller/railtie'
+require 'action_mailer/railtie'
+require 'sprockets/railtie'
+# require "rails/test_unit/railtie"

 # If you have a Gemfile, require the default gems, the ones in the
 # current environment and also include :assets gems if in development

require File.expand_path('../boot', __FILE__)

require 'rails/all'

# If you have a Gemfile, require the default gems, the ones in the
# current environment and also include :assets gems if in development
# or test environments.
Bundler.require(:default, Rails.env)

module Workshops
  class Application < Rails::Application
    # Settings in config/environments/* take precedence over those specified here.
    # Application configuration should go into files in config/initializers
    # -- all .rb files in that directory are automatically loaded.

    # Custom directories with classes and modules you want to be autoloadable.
    # config.autoload_paths += %W(#{config.root}/extras)
    config.autoload_paths += [
      "#{config.root}/lib",
      "#{config.root}/app/serializers",
      "#{config.root}/app/jobs",
      "#{config.root}/app/modules"
    ]

    config.paths['app/views'] << "#{config.root}/app/modules/teams/views"

    # Set Time.zone default to the specified zone and make Active Record auto-convert to this zone.
    # Run "rake -D time" for a list of tasks for finding time zone names. Default is UTC.
    # config.time_zone = 'Central Time (US & Canada)'

    # The default locale is :en and all translations from config/locales/*.rb,yml are auto loaded.
    # config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}').to_s]
    # config.i18n.default_locale = :de
    config.i18n.enforce_available_locales = true
  end
end

BLACKLIST_TOPICS = ["this week in open source", "thoughtbot", "hoptoad", "airbrake"]

Prefer double-quoted strings unless you need single quotes to avoid extra backslashes for escaping.


@@ -35,12 +35,29 @@ describe AuthHashService, '#find_or_create_user_from_auth_hash' do
   end

   context "when a new account is created" do
-    it "notififes analytics of account_created" do
-      tracker = stub_analytics_tracker
+    context "and successfully saves" do
+      it "notififes analytics of account_created" do
+        tracker = stub_analytics_tracker

-      AuthHashService.new(auth_hash).find_or_create_user_from_auth_hash
+        AuthHashService.new(auth_hash).
+          find_or_create_user_from_auth_hash
+
+        expect(tracker).to have_received(:track_account_created)
+      end
+    end
+
+    context "and fails to save" do
+      it "does not notify analytics of account_created" do
+        tracker = stub_analytics_tracker
+        invalid_auth_hash = auth_hash.merge(
+          "info" => { "name" => nil, "nickname" => nil },
+        )
+
+        AuthHashService.new(invalid_auth_hash).
+          find_or_create_user_from_auth_hash

-      expect(tracker).to have_received(:track_account_created)
+        expect(tracker).not_to have_received(:track_account_created)
+      end
     end
   end

require "rails_helper"

describe AuthHashService, '#find_or_create_user_from_auth_hash' do
  it 'creates a user using nickname as a name when name is blank in auth_hash' do
    hash = auth_hash('info' => {'name' => nil,
                                'email' => 'user@example.com',
                                'nickname' => 'thoughtbot'})
    user = AuthHashService.new(hash).find_or_create_user_from_auth_hash

    expect(user).to be_persisted
    expect(user.name).to eq 'thoughtbot'
    expect(user.github_username).to eq 'thoughtbot'
  end

  it 'creates a new user when no matching user' do
    stub_team_member false

    user = AuthHashService.new(auth_hash).find_or_create_user_from_auth_hash

    expect(user).to be_persisted
    expect(user.name).to eq 'Test User'
    expect(user.email).to eq 'user@example.com'
    expect(user.github_username).to eq 'thoughtbot'
    expect(user.auth_provider).to eq 'github'
    expect(user.auth_uid).to eq 1
    expect(user).not_to be_admin
  end

  it 'creates a new admin when no matching user from our organization' do
    stub_team_member true

    user = AuthHashService.new(auth_hash).find_or_create_user_from_auth_hash

    expect(user).to be_admin
  end

  context "when a new account is created" do
    it "notififes analytics of account_created" do
      tracker = stub_analytics_tracker

      AuthHashService.new(auth_hash).find_or_create_user_from_auth_hash

      expect(tracker).to have_received(:track_account_created)
    end
  end

  context 'with an existing user' do
    it "finds the user by email" do
      existing_user = create(:user, email: auth_hash["info"]["email"])

      expect(existing_user).to eq AuthHashService.new(auth_hash).
        find_or_create_user_from_auth_hash
      expect(existing_user.reload.auth_provider).to eq auth_hash["provider"]
      expect(existing_user.auth_uid).to eq auth_hash["uid"]
    end

    it "finds the user by github username" do
      github_username = "a_github_username"
      existing_user = create(:user, github_username: github_username)
      options = { "info" => { "nickname" => github_username } }

      expect(existing_user).to eq AuthHashService.new(auth_hash(options)).
        find_or_create_user_from_auth_hash
      expect(existing_user.reload.auth_provider).to eq auth_hash["provider"]
      expect(existing_user.auth_uid).to eq auth_hash["uid"]
    end

    it "finds the user by auth_provider and auth_uid" do
      existing_user = create(:user, auth_provider: 'github', auth_uid: 1)

      expect(existing_user).to eq AuthHashService.new(auth_hash).
        find_or_create_user_from_auth_hash
    end

    it "does not track account_created" do
      tracker = stub_analytics_tracker
      create_user_with_github_auth

      AuthHashService.new(auth_hash).find_or_create_user_from_auth_hash

      expect(tracker).not_to have_received(:track_account_created)
    end
  end

  def stub_team_member(return_value)
    client = double("github_client")
    allow(client).to receive(:team_member?).
      with(AuthHashService::THOUGHTBOT_GITHUB_TEAM_ID, 'thoughtbot').
      and_return(return_value)
    allow(Octokit::Client).to receive(:new).
      with(access_token: GITHUB_ACCESS_TOKEN).
      and_return(client)
  end

  def auth_hash(options = {})
    {
      'provider' => 'github',
      'uid' => 1,
      'info' => {
        'email' => 'user@example.com',
        'name' => 'Test User',
        'nickname' => 'thoughtbot',
      }
    }.merge(options)
  end

  def stub_analytics_tracker
    double("Analytics").tap do |tracker|
      allow(tracker).to receive(:track_account_created)
      allow(tracker).to receive(:track_updated)
      allow(Analytics).to receive(:new).and_return(tracker)
    end
  end

  def create_user_with_github_auth
    create(:user, auth_provider: "github", auth_uid: auth_hash["uid"])
  end
end

Metrics/LineLength: Line is too long. [81/80]