Commit a64aff2f1c1ddc77b00211489d74fbc23c0c2fa2
1 parent
4ce034ca
Exists in
master
and in
4 other branches
Omniauth Support
Showing
20 changed files
with
194 additions
and
60 deletions
Show diff stats
Gemfile
| ... | ... | @@ -8,6 +8,10 @@ gem "mysql2" |
| 8 | 8 | |
| 9 | 9 | # Auth |
| 10 | 10 | gem "devise", "~> 2.1.0" |
| 11 | +gem 'omniauth' | |
| 12 | +gem 'omniauth-google-oauth2' | |
| 13 | +gem 'omniauth-twitter' | |
| 14 | +gem 'omniauth-github' | |
| 11 | 15 | |
| 12 | 16 | # GITLAB patched libs |
| 13 | 17 | gem "grit", :git => "https://github.com/gitlabhq/grit.git", :ref => "7f35cb98ff17d534a07e3ce6ec3d580f67402837" | ... | ... |
Gemfile.lock
| ... | ... | @@ -166,6 +166,8 @@ GEM |
| 166 | 166 | eventmachine (0.12.10) |
| 167 | 167 | execjs (1.4.0) |
| 168 | 168 | multi_json (~> 1.0) |
| 169 | + faraday (0.8.1) | |
| 170 | + multipart-post (~> 1.1) | |
| 169 | 171 | ffaker (1.14.0) |
| 170 | 172 | ffi (1.0.11) |
| 171 | 173 | foreman (0.47.0) |
| ... | ... | @@ -191,6 +193,7 @@ GEM |
| 191 | 193 | httparty (0.8.3) |
| 192 | 194 | multi_json (~> 1.0) |
| 193 | 195 | multi_xml |
| 196 | + httpauth (0.1) | |
| 194 | 197 | i18n (0.6.0) |
| 195 | 198 | journey (1.0.4) |
| 196 | 199 | jquery-rails (2.0.2) |
| ... | ... | @@ -200,6 +203,8 @@ GEM |
| 200 | 203 | jquery-rails |
| 201 | 204 | railties (>= 3.1.0) |
| 202 | 205 | json (1.7.4) |
| 206 | + jwt (0.1.5) | |
| 207 | + multi_json (>= 1.0) | |
| 203 | 208 | kaminari (0.13.0) |
| 204 | 209 | actionpack (>= 3.0.0) |
| 205 | 210 | activesupport (>= 3.0.0) |
| ... | ... | @@ -223,12 +228,35 @@ GEM |
| 223 | 228 | sprockets (~> 2.0) |
| 224 | 229 | multi_json (1.3.6) |
| 225 | 230 | multi_xml (0.5.1) |
| 231 | + multipart-post (1.1.5) | |
| 226 | 232 | mysql2 (0.3.11) |
| 227 | 233 | net-ldap (0.2.2) |
| 228 | 234 | nokogiri (1.5.3) |
| 235 | + oauth (0.4.6) | |
| 236 | + oauth2 (0.8.0) | |
| 237 | + faraday (~> 0.8) | |
| 238 | + httpauth (~> 0.1) | |
| 239 | + jwt (~> 0.1.4) | |
| 240 | + multi_json (~> 1.0) | |
| 241 | + rack (~> 1.2) | |
| 229 | 242 | omniauth (1.1.0) |
| 230 | 243 | hashie (~> 1.2) |
| 231 | 244 | rack |
| 245 | + omniauth-github (1.0.1) | |
| 246 | + omniauth (~> 1.0) | |
| 247 | + omniauth-oauth2 (~> 1.0) | |
| 248 | + omniauth-google-oauth2 (0.1.13) | |
| 249 | + omniauth (~> 1.0) | |
| 250 | + omniauth-oauth2 | |
| 251 | + omniauth-oauth (1.0.1) | |
| 252 | + oauth | |
| 253 | + omniauth (~> 1.0) | |
| 254 | + omniauth-oauth2 (1.1.0) | |
| 255 | + oauth2 (~> 0.8.0) | |
| 256 | + omniauth (~> 1.0) | |
| 257 | + omniauth-twitter (0.0.12) | |
| 258 | + multi_json (~> 1.3) | |
| 259 | + omniauth-oauth (~> 1.0) | |
| 232 | 260 | orm_adapter (0.3.0) |
| 233 | 261 | polyglot (0.3.3) |
| 234 | 262 | posix-spawn (0.3.6) |
| ... | ... | @@ -411,7 +439,11 @@ DEPENDENCIES |
| 411 | 439 | minitest (>= 2.10) |
| 412 | 440 | modernizr (= 2.5.3) |
| 413 | 441 | mysql2 |
| 442 | + omniauth | |
| 443 | + omniauth-github | |
| 444 | + omniauth-google-oauth2 | |
| 414 | 445 | omniauth-ldap! |
| 446 | + omniauth-twitter | |
| 415 | 447 | pry |
| 416 | 448 | pygments.rb! |
| 417 | 449 | rack-mini-profiler | ... | ... |
app/assets/stylesheets/main.scss
| ... | ... | @@ -3,8 +3,8 @@ |
| 3 | 3 | |
| 4 | 4 | /** GITLAB colors **/ |
| 5 | 5 | $text_color:#222; |
| 6 | -$lite_text_color: #666; | |
| 7 | -$link_color:#2A79A3; | |
| 6 | +$lite_text_color: #666; | |
| 7 | +$link_color:#2A79A3; | |
| 8 | 8 | $active_link_color:#2FA0BB; |
| 9 | 9 | $active_bg_color:#79C3E0; |
| 10 | 10 | $active_bd_color: #2FA0BB; |
| ... | ... | @@ -31,7 +31,7 @@ $hover: #FDF5D9; |
| 31 | 31 | box-shadow: 0 0 3px #ddd; |
| 32 | 32 | } |
| 33 | 33 | |
| 34 | -@mixin solid_shade { | |
| 34 | +@mixin solid_shade { | |
| 35 | 35 | -moz-box-shadow: 0 0 0 3px #eee; |
| 36 | 36 | -webkit-box-shadow: 0 0 0 3px #eee; |
| 37 | 37 | box-shadow: 0 0 0 3px #eee; |
| ... | ... | @@ -73,21 +73,21 @@ $hover: #FDF5D9; |
| 73 | 73 | |
| 74 | 74 | |
| 75 | 75 | /** |
| 76 | - * Header of application. | |
| 76 | + * Header of application. | |
| 77 | 77 | * Contain application logo, search panel, profile icon |
| 78 | 78 | */ |
| 79 | 79 | @import "sections/header.scss"; |
| 80 | 80 | |
| 81 | 81 | /** |
| 82 | - * Navigation menu of application. | |
| 82 | + * Navigation menu of application. | |
| 83 | 83 | * Panel with links to pages depends on project, profile or admin area |
| 84 | 84 | */ |
| 85 | 85 | @import "sections/nav.scss"; |
| 86 | 86 | |
| 87 | 87 | /** |
| 88 | - * This file represent some UI that can be changed | |
| 89 | - * during web app restyle or theme select. | |
| 90 | - * | |
| 88 | + * This file represent some UI that can be changed | |
| 89 | + * during web app restyle or theme select. | |
| 90 | + * | |
| 91 | 91 | * Next items should be placed there |
| 92 | 92 | * - link, button colors |
| 93 | 93 | * - header restyles |
| ... | ... | @@ -118,11 +118,11 @@ $hover: #FDF5D9; |
| 118 | 118 | * Most of application styles placed here. |
| 119 | 119 | * This file represent common UI that should not be changed between themes |
| 120 | 120 | * or project restyling like form width or user avatar class or commit title |
| 121 | - * | |
| 121 | + * | |
| 122 | 122 | * TODO: clean it |
| 123 | 123 | */ |
| 124 | 124 | @import "common.scss"; |
| 125 | - | |
| 125 | +@import "auth_methods.scss"; | |
| 126 | 126 | |
| 127 | 127 | /** |
| 128 | 128 | * Styles related to specific part of app |
| ... | ... | @@ -140,17 +140,17 @@ $hover: #FDF5D9; |
| 140 | 140 | @import "ref_select.scss"; |
| 141 | 141 | |
| 142 | 142 | /** |
| 143 | - * Code (files list) styles. Browsing project files there | |
| 143 | + * Code (files list) styles. Browsing project files there | |
| 144 | 144 | */ |
| 145 | 145 | @import "sections/tree.scss"; |
| 146 | 146 | |
| 147 | 147 | /** |
| 148 | - * This file represent notes(comments) styles | |
| 148 | + * This file represent notes(comments) styles | |
| 149 | 149 | */ |
| 150 | 150 | @import "sections/notes.scss"; |
| 151 | 151 | |
| 152 | 152 | /** |
| 153 | - * Devise styles | |
| 153 | + * Devise styles | |
| 154 | 154 | */ |
| 155 | 155 | @import "sections/login.scss"; |
| 156 | 156 | ... | ... |
app/controllers/omniauth_callbacks_controller.rb
| ... | ... | @@ -9,7 +9,7 @@ class OmniauthCallbacksController < Devise::OmniauthCallbacksController |
| 9 | 9 | error ||= env["omniauth.error.type"].to_s |
| 10 | 10 | error.to_s.humanize if error |
| 11 | 11 | end |
| 12 | - | |
| 12 | + | |
| 13 | 13 | def ldap |
| 14 | 14 | # We only find ourselves here if the authentication to LDAP was successful. |
| 15 | 15 | info = request.env["omniauth.auth"]["info"] |
| ... | ... | @@ -20,4 +20,34 @@ class OmniauthCallbacksController < Devise::OmniauthCallbacksController |
| 20 | 20 | sign_in_and_redirect @user |
| 21 | 21 | end |
| 22 | 22 | |
| 23 | + Settings.omniauth_providers.each do |provider| | |
| 24 | + define_method provider['name'] do | |
| 25 | + handle_omniauth | |
| 26 | + end | |
| 27 | + end | |
| 28 | + | |
| 29 | + private | |
| 30 | + | |
| 31 | + def handle_omniauth | |
| 32 | + oauth = request.env['omniauth.auth'] | |
| 33 | + provider, uid = oauth['provider'], oauth['uid'] | |
| 34 | + | |
| 35 | + if current_user | |
| 36 | + # Change a logged-in user's authentication method: | |
| 37 | + current_user.uid = uid | |
| 38 | + current_user.provider = provider | |
| 39 | + current_user.save | |
| 40 | + redirect_to profile_path | |
| 41 | + else | |
| 42 | + @user = User.find_by_provider_and_uid(provider, uid) | |
| 43 | + | |
| 44 | + if @user | |
| 45 | + sign_in_and_redirect @user | |
| 46 | + else | |
| 47 | + flash[:notice] = "There's no such user!" | |
| 48 | + redirect_to new_user_session_path | |
| 49 | + end | |
| 50 | + end | |
| 51 | + end | |
| 52 | + | |
| 23 | 53 | end | ... | ... |
app/helpers/application_helper.rb
| ... | ... | @@ -75,16 +75,16 @@ module ApplicationHelper |
| 75 | 75 | end |
| 76 | 76 | |
| 77 | 77 | def show_last_push_widget?(event) |
| 78 | - event && | |
| 78 | + event && | |
| 79 | 79 | event.last_push_to_non_root? && |
| 80 | 80 | !event.rm_ref? && |
| 81 | - event.project && | |
| 81 | + event.project && | |
| 82 | 82 | event.project.merge_requests_enabled |
| 83 | 83 | end |
| 84 | 84 | |
| 85 | 85 | def tab_class(tab_key) |
| 86 | 86 | active = case tab_key |
| 87 | - | |
| 87 | + | |
| 88 | 88 | # Project Area |
| 89 | 89 | when :wall; wall_tab? |
| 90 | 90 | when :wiki; controller.controller_name == "wikis" |
| ... | ... | @@ -123,4 +123,9 @@ module ApplicationHelper |
| 123 | 123 | def hexdigest(string) |
| 124 | 124 | Digest::SHA1.hexdigest string |
| 125 | 125 | end |
| 126 | + | |
| 127 | + def authbutton(provider, size = 64) | |
| 128 | + image_tag("authbuttons/#{provider.to_s.split('_').first}_#{size}.png", | |
| 129 | + alt: "Sign in with #{provider.to_s.titleize}" ) | |
| 130 | + end | |
| 126 | 131 | end | ... | ... |
app/views/devise/sessions/new.html.erb
| ... | ... | @@ -14,10 +14,15 @@ |
| 14 | 14 | <div class="right"> <%= render :partial => "devise/shared/links" %></div> |
| 15 | 15 | |
| 16 | 16 | <%- if devise_mapping.omniauthable? %> |
| 17 | - <%- resource_class.omniauth_providers.each do |provider| %> | |
| 18 | - <hr/> | |
| 19 | - <%= link_to "Sign in with #{provider.to_s.titleize}", omniauth_authorize_path(resource_name, provider), :class => "btn primary" %><br /> | |
| 20 | - <% end -%> | |
| 17 | + <hr/> | |
| 18 | + <div class="auth_methods"> | |
| 19 | + <ul> | |
| 20 | + <%- resource_class.omniauth_providers.each do |provider| %> | |
| 21 | + <li><%= link_to authbutton(provider), | |
| 22 | + omniauth_authorize_path(resource_name, provider) %></li> | |
| 23 | + <% end -%> | |
| 24 | + </ul> | |
| 25 | + </div> | |
| 21 | 26 | <% end -%> |
| 22 | 27 | |
| 23 | 28 | <% end %> | ... | ... |
app/views/layouts/profile.html.haml
app/views/profile/password.html.haml
| 1 | 1 | %h3.page_title Password |
| 2 | 2 | %hr |
| 3 | + | |
| 3 | 4 | = form_for @user, url: profile_password_path, method: :put do |f| |
| 4 | - .data | |
| 5 | - %p.slead After successful password update you will be redirected to login page where you should login with new password | |
| 6 | - -if @user.errors.any? | |
| 7 | - .alert-message.block-message.error | |
| 8 | - %ul | |
| 9 | - - @user.errors.full_messages.each do |msg| | |
| 10 | - %li= msg | |
| 5 | + .row | |
| 6 | + .span7 | |
| 7 | + .data | |
| 8 | + %p.slead After successful password update you will be redirected to login page where you should login with new password | |
| 9 | + -if @user.errors.any? | |
| 10 | + .alert-message.block-message.error | |
| 11 | + %ul | |
| 12 | + - @user.errors.full_messages.each do |msg| | |
| 13 | + %li= msg | |
| 14 | + | |
| 15 | + .clearfix | |
| 16 | + = f.label :password | |
| 17 | + .input= f.password_field :password | |
| 18 | + .clearfix | |
| 19 | + = f.label :password_confirmation | |
| 20 | + .input= f.password_field :password_confirmation | |
| 11 | 21 | |
| 12 | - .clearfix | |
| 13 | - = f.label :password | |
| 14 | - .input= f.password_field :password | |
| 15 | - .clearfix | |
| 16 | - = f.label :password_confirmation | |
| 17 | - .input= f.password_field :password_confirmation | |
| 22 | + - if Settings.omniauth.enabled | |
| 23 | + .span5.right | |
| 24 | + .auth_methods.alert.alert-info | |
| 25 | + %strong Tip: Use one of the following sites to login | |
| 26 | + %ul | |
| 27 | + - User.omniauth_providers.each do |provider| | |
| 28 | + %li= link_to authbutton(provider), | | |
| 29 | + omniauth_authorize_path(User, provider) | | |
| 18 | 30 | .actions |
| 19 | 31 | = f.submit 'Save', class: "btn primary" | ... | ... |
app/views/profile/show.html.haml
| ... | ... | @@ -49,6 +49,13 @@ |
| 49 | 49 | %strong Tip: |
| 50 | 50 | You can change your avatar at gravatar.com |
| 51 | 51 | |
| 52 | + - if Settings.omniauth.enabled && @user.provider? | |
| 53 | + %h4 | |
| 54 | + Omniauth Providers: | |
| 55 | + = link_to "Change", profile_password_path, class: "btn small right" | |
| 56 | + You can login through #{@user.provider.titleize}! | |
| 57 | + = authbutton(@user.provider, 32) | |
| 58 | + | |
| 52 | 59 | %h4 |
| 53 | 60 | Personal projects: |
| 54 | 61 | %small.right | ... | ... |
config/gitlab.yml.example
| 1 | -# # # # # # # # # # # # # # # # # # | |
| 1 | +# # # # # # # # # # # # # # # # # # | |
| 2 | 2 | # Gitlab application config file # |
| 3 | 3 | # # # # # # # # # # # # # # # # # # |
| 4 | 4 | |
| ... | ... | @@ -19,14 +19,14 @@ email: |
| 19 | 19 | |
| 20 | 20 | # Application specific settings |
| 21 | 21 | # Like default project limit for user etc |
| 22 | -app: | |
| 23 | - default_projects_limit: 10 | |
| 22 | +app: | |
| 23 | + default_projects_limit: 10 | |
| 24 | 24 | # backup_path: "/vol/backups" # default: Rails.root + backups/ |
| 25 | 25 | # backup_keep_time: 604800 # default: 0 (forever) (in seconds) |
| 26 | 26 | |
| 27 | 27 | |
| 28 | -# | |
| 29 | -# 2. Advanced settings: | |
| 28 | +# | |
| 29 | +# 2. Advanced settings: | |
| 30 | 30 | # ========================== |
| 31 | 31 | |
| 32 | 32 | # Git Hosting configuration |
| ... | ... | @@ -49,3 +49,15 @@ git: |
| 49 | 49 | git_max_size: 5242880 # 5.megabytes |
| 50 | 50 | # Git timeout to read commit, in seconds |
| 51 | 51 | git_timeout: 10 |
| 52 | + | |
| 53 | +# Omniauth configuration | |
| 54 | +# omniauth: | |
| 55 | +# enabled: true | |
| 56 | +# providers: | |
| 57 | +# - { name: 'google_oauth2', app_id: 'YOUR APP ID', | |
| 58 | +# app_secret: 'YOUR APP SECRET', | |
| 59 | +# args: { access_type: 'offline', approval_prompt: '' } } | |
| 60 | +# - { name: 'twitter', app_id: 'YOUR APP ID', | |
| 61 | +# app_secret: 'YOUR APP SECRET'} | |
| 62 | +# - { name: 'github', app_id: 'YOUR APP ID', | |
| 63 | +# app_secret: 'YOUR APP SECRET' } | ... | ... |
config/initializers/1_settings.rb
| ... | ... | @@ -6,7 +6,7 @@ class Settings < Settingslogic |
| 6 | 6 | self.web['protocol'] ||= web.https ? "https" : "http" |
| 7 | 7 | end |
| 8 | 8 | |
| 9 | - def web_host | |
| 9 | + def web_host | |
| 10 | 10 | self.web['host'] ||= 'localhost' |
| 11 | 11 | end |
| 12 | 12 | |
| ... | ... | @@ -14,11 +14,11 @@ class Settings < Settingslogic |
| 14 | 14 | self.email['from'] ||= ("notify@" + web_host) |
| 15 | 15 | end |
| 16 | 16 | |
| 17 | - def url | |
| 17 | + def url | |
| 18 | 18 | self['url'] ||= build_url |
| 19 | - end | |
| 19 | + end | |
| 20 | 20 | |
| 21 | - def web_port | |
| 21 | + def web_port | |
| 22 | 22 | if web.https |
| 23 | 23 | web['port'] = 443 |
| 24 | 24 | else |
| ... | ... | @@ -36,7 +36,7 @@ class Settings < Settingslogic |
| 36 | 36 | raw_url << web_host |
| 37 | 37 | |
| 38 | 38 | if web_custom_port? |
| 39 | - raw_url << ":#{web_port}" | |
| 39 | + raw_url << ":#{web_port}" | |
| 40 | 40 | end |
| 41 | 41 | |
| 42 | 42 | raw_url |
| ... | ... | @@ -111,5 +111,14 @@ class Settings < Settingslogic |
| 111 | 111 | def backup_keep_time |
| 112 | 112 | app['backup_keep_time'] || 0 |
| 113 | 113 | end |
| 114 | + | |
| 115 | + def omniauth_enabled? | |
| 116 | + omniauth['enabled'] || false | |
| 117 | + end | |
| 118 | + | |
| 119 | + def omniauth_providers | |
| 120 | + omniauth['providers'] || [] | |
| 121 | + end | |
| 122 | + | |
| 114 | 123 | end |
| 115 | 124 | end | ... | ... |
db/migrate/20120803152018_add_provider_and_uid_to_users.rb
0 → 100644
db/schema.rb
| ... | ... | @@ -11,7 +11,7 @@ |
| 11 | 11 | # |
| 12 | 12 | # It's strongly recommended to check this file into your version control system. |
| 13 | 13 | |
| 14 | -ActiveRecord::Schema.define(:version => 20120712080407) do | |
| 14 | +ActiveRecord::Schema.define(:version => 20120803152018) do | |
| 15 | 15 | |
| 16 | 16 | create_table "events", :force => true do |t| |
| 17 | 17 | t.string "target_type" |
| ... | ... | @@ -146,31 +146,33 @@ ActiveRecord::Schema.define(:version => 20120712080407) do |
| 146 | 146 | end |
| 147 | 147 | |
| 148 | 148 | create_table "users", :force => true do |t| |
| 149 | - t.string "email", :default => "", :null => false | |
| 150 | - t.string "encrypted_password", :limit => 128, :default => "", :null => false | |
| 149 | + t.string "email", :default => "", :null => false | |
| 150 | + t.string "encrypted_password", :default => "", :null => false | |
| 151 | 151 | t.string "reset_password_token" |
| 152 | 152 | t.datetime "reset_password_sent_at" |
| 153 | 153 | t.datetime "remember_created_at" |
| 154 | - t.integer "sign_in_count", :default => 0 | |
| 154 | + t.integer "sign_in_count", :default => 0 | |
| 155 | 155 | t.datetime "current_sign_in_at" |
| 156 | 156 | t.datetime "last_sign_in_at" |
| 157 | 157 | t.string "current_sign_in_ip" |
| 158 | 158 | t.string "last_sign_in_ip" |
| 159 | - t.datetime "created_at", :null => false | |
| 160 | - t.datetime "updated_at", :null => false | |
| 159 | + t.datetime "created_at", :null => false | |
| 160 | + t.datetime "updated_at", :null => false | |
| 161 | 161 | t.string "name" |
| 162 | - t.boolean "admin", :default => false, :null => false | |
| 163 | - t.integer "projects_limit", :default => 10 | |
| 164 | - t.string "skype", :default => "", :null => false | |
| 165 | - t.string "linkedin", :default => "", :null => false | |
| 166 | - t.string "twitter", :default => "", :null => false | |
| 162 | + t.boolean "admin", :default => false, :null => false | |
| 163 | + t.integer "projects_limit", :default => 10 | |
| 164 | + t.string "skype", :default => "", :null => false | |
| 165 | + t.string "linkedin", :default => "", :null => false | |
| 166 | + t.string "twitter", :default => "", :null => false | |
| 167 | 167 | t.string "authentication_token" |
| 168 | - t.boolean "dark_scheme", :default => false, :null => false | |
| 169 | - t.integer "theme_id", :default => 1, :null => false | |
| 168 | + t.boolean "dark_scheme", :default => false, :null => false | |
| 169 | + t.integer "theme_id", :default => 1, :null => false | |
| 170 | 170 | t.string "bio" |
| 171 | - t.boolean "blocked", :default => false, :null => false | |
| 172 | - t.integer "failed_attempts", :default => 0 | |
| 171 | + t.boolean "blocked", :default => false, :null => false | |
| 172 | + t.integer "failed_attempts", :default => 0 | |
| 173 | 173 | t.datetime "locked_at" |
| 174 | + t.string "provider" | |
| 175 | + t.string "uid" | |
| 174 | 176 | end |
| 175 | 177 | |
| 176 | 178 | add_index "users", ["email"], :name => "index_users_on_email", :unique => true | ... | ... |
1.89 KB
4.34 KB
1.58 KB
3.37 KB
1.41 KB
3.3 KB