diff --git a/Gemfile b/Gemfile index c967bd8f..d6d711d2 100644 --- a/Gemfile +++ b/Gemfile @@ -21,7 +21,9 @@ gem 'jwt' gem 'lograge' gem 'mysql2', require: false gem 'oj' +gem 'omniauth-github' gem 'omniauth-google-oauth2' +gem 'omniauth-microsoft-office365' gem 'omniauth-rails_csrf_protection' gem 'pagy' gem 'pdf-reader' diff --git a/Gemfile.lock b/Gemfile.lock index f4b7ab71..c4107333 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -328,11 +328,17 @@ GEM hashie (>= 3.4.6) rack (>= 2.2.3) rack-protection + omniauth-github (2.0.1) + omniauth (~> 2.0) + omniauth-oauth2 (~> 1.8) omniauth-google-oauth2 (1.1.1) jwt (>= 2.0) oauth2 (~> 2.0.6) omniauth (~> 2.0) omniauth-oauth2 (~> 1.8.0) + omniauth-microsoft-office365 (0.0.8) + omniauth + omniauth-oauth2 omniauth-oauth2 (1.8.0) oauth2 (>= 1.4, < 3) omniauth (~> 2.0) @@ -589,7 +595,9 @@ DEPENDENCIES lograge mysql2 oj + omniauth-github omniauth-google-oauth2 + omniauth-microsoft-office365 omniauth-rails_csrf_protection pagy pdf-reader diff --git a/app/models/user.rb b/app/models/user.rb index 92129293..e026610b 100644 --- a/app/models/user.rb +++ b/app/models/user.rb @@ -58,7 +58,10 @@ class User < ApplicationRecord has_many :email_messages, dependent: :destroy devise :two_factor_authenticatable, :recoverable, :rememberable, :validatable, :trackable - devise :registerable, :omniauthable, omniauth_providers: [:google_oauth2] if Docuseal.multitenant? + + if Docuseal.multitenant? + devise :registerable, :omniauthable, omniauth_providers: %i[google_oauth2 microsoft_office365 github] + end attribute :role, :string, default: ADMIN_ROLE attribute :uuid, :string, default: -> { SecureRandom.uuid } diff --git a/app/views/devise/registrations/show.html.erb b/app/views/devise/registrations/show.html.erb index 0b139107..23483bdf 100644 --- a/app/views/devise/registrations/show.html.erb +++ b/app/views/devise/registrations/show.html.erb @@ -16,11 +16,18 @@ <% end %> <% if devise_mapping.omniauthable? %> - <%= form_for '', url: omniauth_authorize_path(resource_name, :google_oauth2), data: { turbo: false }, method: :post do |f| %> - - <%= hidden_field_tag :state, { redir: params[:redir].to_s }.compact_blank.to_query %> - <%= f.button button_title(title: 'Sign up with Google', icon: svg_icon('brand_google', class: 'w-6 h-6')), class: 'white-button w-full mt-4' %> - <% end %> +
+ <%= form_for '', url: omniauth_authorize_path(resource_name, :google_oauth2), data: { turbo: false }, method: :post do |f| %> + + <%= hidden_field_tag :state, { redir: params[:redir].to_s }.compact_blank.to_query %> + <%= f.button button_title(title: 'Sign up with Google', icon: svg_icon('brand_google', class: 'w-6 h-6')), class: 'white-button w-full mt-4' %> + <% end %> + <%= form_for '', url: omniauth_authorize_path(resource_name, :microsoft_office365), data: { turbo: false }, method: :post do |f| %> + + <%= hidden_field_tag :state, { redir: params[:redir].to_s }.compact_blank.to_query, id: 'state_microsoft' %> + <%= f.button button_title(title: 'Sign up with Microsoft', icon: svg_icon('brand_microsoft', class: 'w-6 h-6')), class: 'white-button w-full' %> + <% end %> +
<% end %> <%= render 'devise/shared/links' %> diff --git a/app/views/devise/sessions/new.html.erb b/app/views/devise/sessions/new.html.erb index ea6d7f55..16f15385 100644 --- a/app/views/devise/sessions/new.html.erb +++ b/app/views/devise/sessions/new.html.erb @@ -20,11 +20,18 @@ <% end %> <% if devise_mapping.omniauthable? %> - <%= form_for '', url: omniauth_authorize_path(resource_name, :google_oauth2), data: { turbo: false }, method: :post do |f| %> - - <%= hidden_field_tag :state, { redir: params[:redir].to_s }.compact_blank.to_query %> - <%= f.button button_title(title: 'Sign in with Google', icon: svg_icon('brand_google', class: 'w-6 h-6')), class: 'white-button w-full mt-4' %> - <% end %> +
+ <%= form_for '', url: omniauth_authorize_path(resource_name, :google_oauth2), data: { turbo: false }, method: :post do |f| %> + + <%= hidden_field_tag :state, { redir: params[:redir].to_s }.compact_blank.to_query %> + <%= f.button button_title(title: 'Sign in with Google', icon: svg_icon('brand_google', class: 'w-6 h-6')), class: 'white-button w-full mt-4' %> + <% end %> + <%= form_for '', url: omniauth_authorize_path(resource_name, :microsoft_office365), data: { turbo: false }, method: :post do |f| %> + + <%= hidden_field_tag :state, { redir: params[:redir].to_s }.compact_blank.to_query, id: 'state_microsoft' %> + <%= f.button button_title(title: 'Sign in with Microsoft', icon: svg_icon('brand_microsoft', class: 'w-6 h-6')), class: 'white-button w-full' %> + <% end %> +
<% end %> <%= render 'devise/shared/links' %> diff --git a/app/views/icons/_brand_microsoft.html.erb b/app/views/icons/_brand_microsoft.html.erb new file mode 100644 index 00000000..cbcab3f9 --- /dev/null +++ b/app/views/icons/_brand_microsoft.html.erb @@ -0,0 +1,3 @@ + + + diff --git a/config/initializers/devise.rb b/config/initializers/devise.rb index d5ffebfb..f082a7da 100644 --- a/config/initializers/devise.rb +++ b/config/initializers/devise.rb @@ -14,6 +14,7 @@ Devise.otp_allowed_drift = 60.seconds # # Use this hook to configure devise mailer, warden hooks and so forth. # Many of these configuration options can be set straight in your model. +# rubocop:disable Metrics/BlockLength Devise.setup do |config| config.warden do |manager| manager.default_strategies(scope: :user).unshift(:two_factor_authenticatable) @@ -277,6 +278,12 @@ Devise.setup do |config| # Add a new OmniAuth provider. Check the wiki for more information on setting # up on your models and hooks. config.omniauth :google_oauth2, ENV.fetch('GOOGLE_CLIENT_ID', nil), ENV.fetch('GOOGLE_CLIENT_SECRET', nil), {} + config.omniauth :microsoft_office365, ENV.fetch('OFFICE365_CLIENT_ID', nil), + ENV.fetch('OFFICE365_CLIENT_SECRET', nil), {} + + if ENV['GITHUB_CLIENT_ID'] + config.omniauth :github, ENV.fetch('GITHUB_CLIENT_ID', nil), ENV.fetch('GITHUB_CLIENT_SECRET', nil), {} + end # ==> Warden configuration # If you want to use other strategies, that are not supported by Devise, or @@ -316,3 +323,4 @@ Devise.setup do |config| # changed. Defaults to true, so a user is signed in automatically after changing a password. # config.sign_in_after_change_password = true end +# rubocop:enable Metrics/BlockLength diff --git a/lib/users.rb b/lib/users.rb index 775e3e97..0d1bea56 100644 --- a/lib/users.rb +++ b/lib/users.rb @@ -4,12 +4,21 @@ module Users module_function def from_omniauth(oauth) - user = User.find_by(email: oauth.info.email) + user = User.find_by(email: oauth.info.email.to_s.downcase) return user if user - User.new(email: oauth.info.email, - first_name: oauth.extra.id_info.given_name, - last_name: oauth.extra.id_info.family_name) + case oauth['provider'].to_s + when 'google_oauth2' + User.new(email: oauth.info.email, + first_name: oauth.extra.id_info.given_name, + last_name: oauth.extra.id_info.family_name) + when 'microsoft_office365' + User.new(email: oauth.info.email, + first_name: oauth.info.first_name, + last_name: oauth.info.last_name) + when 'github' + User.new(email: oauth.info.email, first_name: oauth.info.name) + end end end