Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(447)

Side by Side Diff: chrome/browser/notifications/desktop_notification_service.cc

Issue 194108: adds DesktopNotificationService to Profile (Closed)
Patch Set: more feedback Created 11 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
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/notifications/desktop_notification_service.h"
6
7 #include "app/l10n_util.h"
8 #include "app/resource_bundle.h"
9 #include "base/thread.h"
10 #include "chrome/browser/browser_list.h"
11 #include "chrome/browser/browser_process.h"
12 #include "chrome/browser/chrome_thread.h"
13 #include "chrome/browser/notifications/notification.h"
14 #include "chrome/browser/notifications/notification_ui_manager.h"
15 #include "chrome/browser/notifications/notification_object_proxy.h"
16 #include "chrome/browser/notifications/notifications_prefs_cache.h"
17 #include "chrome/browser/profile.h"
18 #include "chrome/browser/renderer_host/render_process_host.h"
19 #include "chrome/browser/renderer_host/render_view_host.h"
20 #include "chrome/browser/renderer_host/site_instance.h"
21 #include "chrome/browser/tab_contents/infobar_delegate.h"
22 #include "chrome/browser/tab_contents/tab_contents.h"
23 #include "chrome/browser/worker_host/worker_process_host.h"
24 #include "chrome/common/child_process_host.h"
25 #include "chrome/common/pref_names.h"
26 #include "chrome/common/pref_service.h"
27 #include "chrome/common/render_messages.h"
28 #include "webkit/api/public/WebNotificationPresenter.h"
29 #include "grit/chromium_strings.h"
30 #include "grit/generated_resources.h"
31 #include "grit/theme_resources.h"
32
33 using WebKit::WebNotificationPresenter;
34
35 // A task object which calls the renderer to inform the web page that the
36 // permission request has completed.
37 class NotificationPermissionCallbackTask : public Task {
38 public:
39 NotificationPermissionCallbackTask(int process_id, int route_id,
40 int request_id)
41 : process_id_(process_id),
42 route_id_(route_id),
43 request_id_(request_id) {
44 }
45
46 virtual void Run() {
michaeln 2009/10/10 19:10:51 maybe DCHECK(ChromeThread::CurrentlyOn(ChromeThrea
47 RenderViewHost* host = RenderViewHost::FromID(process_id_, route_id_);
48 if (host)
49 host->Send(new ViewMsg_PermissionRequestDone(route_id_, request_id_));
50 }
51
52 private:
53 int process_id_;
54 int route_id_;
55 int request_id_;
56 };
57
58 // The delegate for the infobar shown when an origin requests notification
59 // permissions.
60 class NotificationPermissionInfoBarDelegate : public ConfirmInfoBarDelegate {
michaeln 2009/10/10 19:10:51 I'm not familiar with the infobar ui infrastructur
61 public:
62 NotificationPermissionInfoBarDelegate(TabContents* contents,
63 const GURL& origin,
64 int callback_context)
65 : ConfirmInfoBarDelegate(contents),
66 origin_(origin),
67 profile_(contents->profile()),
68 process_id_(contents->process()->id()),
69 route_id_(contents->render_view_host()->routing_id()),
70 callback_context_(callback_context),
71 action_taken_(false) {
72 }
73
74 // Overridden from ConfirmInfoBarDelegate:
75 virtual void InfoBarClosed() {
76 if (!action_taken_)
77 UMA_HISTOGRAM_COUNTS("NotificationPermissionRequest.Ignored", 1);
78
79 base::Thread* io_thread = g_browser_process->io_thread();
80 if (io_thread && io_thread->message_loop()) {
81 io_thread->message_loop()->PostTask(FROM_HERE,
82 new NotificationPermissionCallbackTask(process_id_, route_id_,
83 callback_context_));
84 }
85
86 delete this;
87 }
88
89 virtual std::wstring GetMessageText() const {
90 return l10n_util::GetStringF(IDS_NOTIFICATION_PERMISSIONS,
91 UTF8ToWide(origin_.spec()));
92 }
93
94 virtual SkBitmap* GetIcon() const {
95 return ResourceBundle::GetSharedInstance().GetBitmapNamed(
96 IDR_PRODUCT_ICON_32);
97 }
98
99 virtual int GetButtons() const {
100 return BUTTON_OK | BUTTON_CANCEL | BUTTON_OK_DEFAULT;
101 }
102
103 virtual std::wstring GetButtonLabel(InfoBarButton button) const {
104 return button == BUTTON_OK ?
105 l10n_util::GetString(IDS_NOTIFICATION_PERMISSION_YES) :
106 l10n_util::GetString(IDS_NOTIFICATION_PERMISSION_NO);
107 }
108
109 virtual bool Accept() {
110 UMA_HISTOGRAM_COUNTS("NotificationPermissionRequest.Allowed", 1);
111 profile_->GetDesktopNotificationService()->GrantPermission(origin_);
112 action_taken_ = true;
113 return true;
114 }
115
116 virtual bool Cancel() {
117 UMA_HISTOGRAM_COUNTS("NotificationPermissionRequest.Denied", 1);
118 profile_->GetDesktopNotificationService()->DenyPermission(origin_);
119 action_taken_ = true;
120 return true;
121 }
122
123 private:
124 // The origin we are asking for permissions on.
125 GURL origin_;
126
127 // The Profile that we restore sessions from.
128 Profile* profile_;
129
130 // The callback information that tells us how to respond to javascript via
131 // the correct RenderView.
132 int process_id_;
133 int route_id_;
134 int callback_context_;
135
136 // Whether the user clicked one of the buttons.
137 bool action_taken_;
138
139 DISALLOW_COPY_AND_ASSIGN(NotificationPermissionInfoBarDelegate);
140 };
141
142 DesktopNotificationService::DesktopNotificationService(Profile* profile,
143 NotificationUIManager* ui_manager)
144 : profile_(profile),
145 ui_manager_(ui_manager) {
146 InitPrefs();
147 }
148
149 DesktopNotificationService::~DesktopNotificationService() {
150 }
151
152 // Initialize the cache with the allowed and denied origins, or
153 // create the preferences if they don't exist yet.
154 void DesktopNotificationService::InitPrefs() {
155 PrefService* prefs = profile_->GetPrefs();
156 ListValue* allowed_sites = NULL;
157 ListValue* denied_sites = NULL;
158
159 if (prefs->FindPreference(prefs::kDesktopNotificationAllowedOrigins))
160 allowed_sites =
161 prefs->GetMutableList(prefs::kDesktopNotificationAllowedOrigins);
162 else
163 prefs->RegisterListPref(prefs::kDesktopNotificationAllowedOrigins);
164
165 if (prefs->FindPreference(prefs::kDesktopNotificationDeniedOrigins))
166 denied_sites =
167 prefs->GetMutableList(prefs::kDesktopNotificationDeniedOrigins);
168 else
169 prefs->RegisterListPref(prefs::kDesktopNotificationDeniedOrigins);
170
171 prefs_cache_ = new NotificationsPrefsCache(allowed_sites, denied_sites);
172 }
173
174 void DesktopNotificationService::GrantPermission(const GURL& origin) {
175 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::UI));
176 PrefService* prefs = profile_->GetPrefs();
177 ListValue* allowed_sites =
178 prefs->GetMutableList(prefs::kDesktopNotificationAllowedOrigins);
179 ListValue* denied_sites =
180 prefs->GetMutableList(prefs::kDesktopNotificationDeniedOrigins);
181 // Remove from the black-list and add to the white-list.
182 StringValue* value = new StringValue(origin.spec());
183 denied_sites->Remove(*value);
184 allowed_sites->Append(value);
185 prefs->ScheduleSavePersistentPrefs();
186
187 // Schedule a cache update on the IO thread.
188 base::Thread* io_thread = g_browser_process->io_thread();
189 if (io_thread && io_thread->message_loop()) {
190 io_thread->message_loop()->PostTask(FROM_HERE,
191 NewRunnableMethod(prefs_cache_.get(),
192 &NotificationsPrefsCache::CacheAllowedOrigin,
193 origin));
194 }
195 }
196
197 void DesktopNotificationService::DenyPermission(const GURL& origin) {
198 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::UI));
199 PrefService* prefs = profile_->GetPrefs();
200 ListValue* allowed_sites =
201 prefs->GetMutableList(prefs::kDesktopNotificationAllowedOrigins);
202 ListValue* denied_sites =
203 prefs->GetMutableList(prefs::kDesktopNotificationDeniedOrigins);
204 StringValue* value = new StringValue(origin.spec());
205 // Remove from the white-list and add to the black-list.
206 allowed_sites->Remove(*value);
207 denied_sites->Append(value);
208 prefs->ScheduleSavePersistentPrefs();
209
210 // Schedule a cache update on the IO thread.
211 base::Thread* io_thread = g_browser_process->io_thread();
212 if (io_thread && io_thread->message_loop()) {
213 io_thread->message_loop()->PostTask(FROM_HERE,
214 NewRunnableMethod(prefs_cache_.get(),
215 &NotificationsPrefsCache::CacheDeniedOrigin,
216 origin));
217 }
218 }
219
220 void DesktopNotificationService::RequestPermission(
221 const GURL& origin, int callback_context) {
222 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::UI));
223 // Show an info bar requesting permission.
224 Browser* browser = BrowserList::GetLastActive();
225 if (!browser) {
226 // Reached during ui tests.
227 return;
228 }
229 TabContents* tab = browser->GetSelectedTabContents();
230 if (!tab)
231 return;
232 tab->AddInfoBar(new NotificationPermissionInfoBarDelegate(tab, origin,
233 callback_context));
234 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698