1 // Copyright (c) 2009 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "chrome/browser/ui/login/login_prompt.h"
6
7 #include "base/utf_string_conversions.h"
8 #include "chrome/browser/password_manager/password_manager.h"
9 #include "chrome/browser/tab_contents/tab_util.h"
10 #include "chrome/browser/ui/views/login_view.h"
11 #include "content/browser/browser_thread.h"
12 #include "content/browser/renderer_host/render_process_host.h"
13 #include "content/browser/renderer_host/render_view_host.h"
14 #include "content/browser/renderer_host/resource_dispatcher_host.h"
15 #include "content/browser/tab_contents/tab_contents.h"
16 #include "grit/generated_resources.h"
17 #include "net/url_request/url_request.h"
18 #include "ui/base/l10n/l10n_util.h"
19 #include "views/window/dialog_delegate.h"
20
21 using webkit_glue::PasswordForm;
22
23 // ----------------------------------------------------------------------------
24 // LoginHandlerWin
25
26 // This class simply forwards the authentication from the LoginView (on
27 // the UI thread) to the net::URLRequest (on the I/O thread).
28 // This class uses ref counting to ensure that it lives until all InvokeLaters
29 // have been called.
30 class LoginHandlerWin : public LoginHandler,
31 public ConstrainedDialogDelegate {
32 public:
LoginHandlerWin(net::AuthChallengeInfo * auth_info,net::URLRequest * request)33 LoginHandlerWin(net::AuthChallengeInfo* auth_info, net::URLRequest* request)
34 : LoginHandler(auth_info, request) {
35 }
36
37 // LoginModelObserver implementation.
OnAutofillDataAvailable(const std::wstring & username,const std::wstring & password)38 virtual void OnAutofillDataAvailable(const std::wstring& username,
39 const std::wstring& password) OVERRIDE {
40 // Nothing to do here since LoginView takes care of autofil for win.
41 }
42
43 // views::DialogDelegate methods:
GetDialogButtonLabel(MessageBoxFlags::DialogButton button) const44 virtual std::wstring GetDialogButtonLabel(
45 MessageBoxFlags::DialogButton button) const OVERRIDE {
46 if (button == MessageBoxFlags::DIALOGBUTTON_OK)
47 return l10n_util::GetStringUTF16(IDS_LOGIN_DIALOG_OK_BUTTON_LABEL);
48 return DialogDelegate::GetDialogButtonLabel(button);
49 }
50
GetWindowTitle() const51 virtual std::wstring GetWindowTitle() const OVERRIDE {
52 return l10n_util::GetStringUTF16(IDS_LOGIN_DIALOG_TITLE);
53 }
54
WindowClosing()55 virtual void WindowClosing() OVERRIDE {
56 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
57
58 TabContents* tab = GetTabContentsForLogin();
59 if (tab)
60 tab->render_view_host()->set_ignore_input_events(false);
61
62 // Reference is no longer valid.
63 SetDialog(NULL);
64
65 CancelAuth();
66 }
67
DeleteDelegate()68 virtual void DeleteDelegate() OVERRIDE {
69 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
70
71 // The constrained window is going to delete itself; clear our pointer.
72 SetDialog(NULL);
73 SetModel(NULL);
74
75 ReleaseSoon();
76 }
77
Cancel()78 virtual bool Cancel() OVERRIDE {
79 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
80
81 CancelAuth();
82 return true;
83 }
84
Accept()85 virtual bool Accept() OVERRIDE {
86 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
87
88 SetAuth(login_view_->GetUsername(), login_view_->GetPassword());
89 return true;
90 }
91
GetInitiallyFocusedView()92 virtual views::View* GetInitiallyFocusedView() OVERRIDE {
93 return login_view_->GetInitiallyFocusedView();
94 }
95
GetContentsView()96 virtual views::View* GetContentsView() OVERRIDE {
97 return login_view_;
98 }
99
100 // LoginHandler:
101
BuildViewForPasswordManager(PasswordManager * manager,const string16 & explanation)102 virtual void BuildViewForPasswordManager(
103 PasswordManager* manager,
104 const string16& explanation) OVERRIDE {
105 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
106
107 // Create a new LoginView and set the model for it. The model
108 // (password manager) is owned by the view's parent TabContents,
109 // so natural destruction order means we don't have to worry about
110 // disassociating the model from the view, because the view will
111 // be deleted before the password manager.
112 login_view_ = new LoginView(UTF16ToWideHack(explanation), manager);
113
114 // Scary thread safety note: This can potentially be called *after* SetAuth
115 // or CancelAuth (say, if the request was cancelled before the UI thread got
116 // control). However, that's OK since any UI interaction in those functions
117 // will occur via an InvokeLater on the UI thread, which is guaranteed
118 // to happen after this is called (since this was InvokeLater'd first).
119 SetDialog(GetTabContentsForLogin()->CreateConstrainedDialog(this));
120 NotifyAuthNeeded();
121 }
122
123 private:
124 friend class base::RefCountedThreadSafe<LoginHandlerWin>;
125 friend class LoginPrompt;
126
~LoginHandlerWin()127 ~LoginHandlerWin() {}
128
129 // The LoginView that contains the user's login information
130 LoginView* login_view_;
131
132 DISALLOW_COPY_AND_ASSIGN(LoginHandlerWin);
133 };
134
135 // static
Create(net::AuthChallengeInfo * auth_info,net::URLRequest * request)136 LoginHandler* LoginHandler::Create(net::AuthChallengeInfo* auth_info,
137 net::URLRequest* request) {
138 return new LoginHandlerWin(auth_info, request);
139 }
140