Remove SslRequirement and associated logic
[gitorious:mainline.git] / app / controllers / sessions_controller.rb
1 # encoding: utf-8
2 #--
3 #   Copyright (C) 2012 Gitorious AS
4 #   Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies)
5 #   Copyright (C) 2007, 2008 Johan Sørensen <johan@johansorensen.com>
6 #   Copyright (C) 2008 August Lilleaas <augustlilleaas@gmail.com>
7 #   Copyright (C) 2008 Patrick Aljord <patcito@gmail.com>
8 #   Copyright (C) 2008 Tor Arne Vestbø <tavestbo@trolltech.com>
9 #   Copyright (C) 2009 Fabio Akita <fabio.akita@gmail.com>
10 #
11 #   This program is free software: you can redistribute it and/or modify
12 #   it under the terms of the GNU Affero General Public License as published by
13 #   the Free Software Foundation, either version 3 of the License, or
14 #   (at your option) any later version.
15 #
16 #   This program is distributed in the hope that it will be useful,
17 #   but WITHOUT ANY WARRANTY; without even the implied warranty of
18 #   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19 #   GNU Affero General Public License for more details.
20 #
21 #   You should have received a copy of the GNU Affero General Public License
22 #   along with this program.  If not, see <http://www.gnu.org/licenses/>.
23 #++
24
25 require "openid"
26 require "yadis"
27 require "gitorious"
28
29 # This controller handles the login/logout function of the site.
30 class SessionsController < ApplicationController
31   skip_before_filter :public_and_logged_in
32   renders_in_site_specific_context
33   layout "second_generation/application"
34   before_filter :validate_request_host, :only => :create
35
36   def new
37   end
38
39   def create
40     if using_open_id?
41       open_id_authentication(params[:openid_url])
42     else
43       password_authentication(params[:email], params[:password])
44     end
45   end
46
47   # This controller action should be protected behind a web server
48   # single sign-on authentication mechanism, like Apache's mod_auth_kerb
49   # or mod_ssl.
50   def http
51     http_authentication
52   end
53
54   def destroy
55     self.current_user.forget_me if logged_in?
56     cookies.delete :auth_token
57     clear_varnish_auth_cookie
58     reset_session
59     flash[:notice] = "You have been logged out."
60     redirect_back_or_default('/')
61   end
62
63   protected
64   def validate_request_host
65     if !Gitorious.site.can_share_cookies?(request.host)
66       Rails.logger.warn("WARNING: Invalid request host '#{request.host}'. Session cookies will not work")
67     end
68   end
69
70   # if user does not exist, it gets created and activated,
71   # else if the user already exists with same identity_url, it just logs in
72   def open_id_authentication(openid_url)
73     authenticate_with_open_id(openid_url, :required => [:nickname, :email], :optional => [:fullname]) do |result, identity_url, registration|
74       if result.successful?
75         @user = User.find_or_initialize_by_identity_url(identity_url)
76         if @user.new_record?
77
78           session[:openid_nickname] = registration['nickname']
79           session[:openid_email]    = registration['email']
80           session[:openid_fullname] = registration['fullname']
81           session[:openid_url]      = identity_url
82           flash[:notice] = "You now need to finalize your account"
83           redirect_to :controller => 'users', :action => 'openid_build' and return
84         end
85         self.current_user = @user
86         successful_login
87       else
88         failed_login result.message, 'openid'
89       end
90     end
91   rescue ActiveRecord::RecordInvalid => invalid
92     flash[:error] = %Q{This login (<strong>#{@user.login}</strong>) already exists,
93       please <a href="#{@user.identity_url}"> choose a different persona/nickname
94       or modify the current one</a>}
95     redirect_to login_path(:method => 'openid')
96   end
97
98   def password_authentication(email, password)
99     credentials = Gitorious::Authentication::Credentials.new
100     credentials.username = email
101     credentials.password = password
102     self.current_user = Gitorious::Authentication.authenticate(credentials)
103     if logged_in?
104       successful_login
105     else
106       failed_login("Email and/or password did not match, please try again.")
107     end
108   end
109
110   # Single sign-on, via a web server's authentication mechanism.
111   def http_authentication
112     credentials = Gitorious::Authentication::Credentials.new
113     credentials.env = request.env
114     self.current_user = Gitorious::Authentication.authenticate(credentials)
115     if logged_in?
116       successful_login
117     else
118       # If the web server is protecting this sessions URL, you might end up
119       # with an HTTP 401 error, in which case you won't even get this far.
120       # Still, it could happen, if you do some further application-level checks
121       # within your Gitorious::Authentication module.
122       failed_login "Gitorious could not verify your browser's credentials.", 'http'
123     end
124   end
125
126   def failed_login(message = "Authentication failed.",method="")
127     if method==""
128       flash.now[:error] = message
129       render :action => 'new'
130     else
131       redirect_to login_path(:method=>method)
132       flash[:error] = message
133     end
134   end
135
136   def successful_login
137     if params[:remember_me] == "1"
138       self.current_user.remember_me
139       cookies[:auth_token] = {
140         :value => self.current_user.remember_token ,
141         :expires => self.current_user.remember_token_expires_at,
142         :domain => ".#{Gitorious.host}",
143         :secure => Gitorious.site.ssl?
144       }
145     end
146     check_state_and_redirect('/')
147   end
148
149   def check_state_and_redirect(redirection_url)
150     if current_user.pending?
151       flash[:notice] = "You need to accept the terms"
152       redirect_to user_license_path(current_user) and return
153     else
154       flash[:notice] = "Logged in successfully"
155       redirect_back_or_default(redirection_url)
156     end
157   end
158 end