16c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen/* 26c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * Copyright (C) 2010 Google Inc. All rights reserved. 36c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * 46c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * Redistribution and use in source and binary forms, with or without 56c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * modification, are permitted provided that the following conditions are 66c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * met: 76c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * 86c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * * Redistributions of source code must retain the above copyright 96c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * notice, this list of conditions and the following disclaimer. 106c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * * Redistributions in binary form must reproduce the above 116c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * copyright notice, this list of conditions and the following disclaimer 126c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * in the documentation and/or other materials provided with the 136c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * distribution. 146c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * * Neither the name of Google Inc. nor the names of its 156c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * contributors may be used to endorse or promote products derived from 166c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * this software without specific prior written permission. 176c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * 186c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 196c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 206c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 216c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 226c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 236c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 246c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 256c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 266c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 276c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 286c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 296c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen */ 306c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 316c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen#include "config.h" 326c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen#include "NotificationPresenter.h" 336c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 34a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "WebKit.h" 35a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "WebKitClient.h" 36a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "WebNotification.h" 37a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "WebNotificationPermissionCallback.h" 38a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "WebSecurityOrigin.h" 39a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "WebString.h" 40a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch#include "WebURL.h" 416c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen#include "googleurl/src/gurl.h" 425ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include <wtf/text/CString.h> 435ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include <wtf/text/WTFString.h> 446c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 456c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsenusing namespace WebKit; 466c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 475ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenstatic WebString identifierForNotification(const WebNotification& notification) 485ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 495ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if (notification.isHTML()) 505ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return notification.url().spec().utf16(); 515ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return notification.title(); 525ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 535ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 545abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrickstatic void deferredDisplayDispatch(void* context) 555ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 565abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick WebNotification* notification = static_cast<WebNotification*>(context); 575abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick notification->dispatchDisplayEvent(); 585abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick delete notification; 595ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 605ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 616c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsenvoid NotificationPresenter::grantPermission(const WebString& origin) 626c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen{ 636c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen // Make sure it's in the form of an origin. 646c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen GURL url(origin); 65f486d19d62f1bc33246748b14b14a9dfa617b57fIain Merrick m_allowedOrigins.add(WTF::String(url.GetOrigin().spec().c_str())); 666c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen} 676c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 685ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenbool NotificationPresenter::simulateClick(const WebString& title) 695ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 705ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WTF::String id(title.data(), title.length()); 715ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if (m_activeNotifications.find(id) == m_activeNotifications.end()) 725ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return false; 735ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 745ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen const WebNotification& notification = m_activeNotifications.find(id)->second; 755ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WebNotification eventTarget(notification); 765ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen eventTarget.dispatchClickEvent(); 775ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return true; 785ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 795ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 806c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen// The output from all these methods matches what DumpRenderTree produces. 816c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsenbool NotificationPresenter::show(const WebNotification& notification) 826c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen{ 835ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WebString identifier = identifierForNotification(notification); 845af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke if (!notification.replaceId().isEmpty()) { 85f486d19d62f1bc33246748b14b14a9dfa617b57fIain Merrick WTF::String replaceId(notification.replaceId().data(), notification.replaceId().length()); 865af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke if (m_replacements.find(replaceId) != m_replacements.end()) 875af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke printf("REPLACING NOTIFICATION %s\n", 885af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke m_replacements.find(replaceId)->second.utf8().data()); 895af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke 90f486d19d62f1bc33246748b14b14a9dfa617b57fIain Merrick m_replacements.set(replaceId, WTF::String(identifier.data(), identifier.length())); 915af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke } 925af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke 936c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen if (notification.isHTML()) { 946c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen printf("DESKTOP NOTIFICATION: contents at %s\n", 956c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen notification.url().spec().data()); 966c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen } else { 975af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke printf("DESKTOP NOTIFICATION:%s icon %s, title %s, text %s\n", 982fc2651226baac27029e38c9d6ef883fa32084dbSteve Block notification.direction() == WebTextDirectionRightToLeft ? "(RTL)" : "", 996c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen notification.iconURL().isEmpty() ? "" : 1006c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen notification.iconURL().spec().data(), 1016c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen notification.title().isEmpty() ? "" : 1026c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen notification.title().utf8().data(), 1036c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen notification.body().isEmpty() ? "" : 1046c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen notification.body().utf8().data()); 1056c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen } 1066c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 1075ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WTF::String id(identifier.data(), identifier.length()); 1085ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_activeNotifications.set(id, notification); 1095ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1105abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick webKitClient()->callOnMainThread(deferredDisplayDispatch, new WebNotification(notification)); 1116c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen return true; 1126c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen} 1136c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 1146c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsenvoid NotificationPresenter::cancel(const WebNotification& notification) 1156c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen{ 1165ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WebString identifier = identifierForNotification(notification); 1176c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen printf("DESKTOP NOTIFICATION CLOSED: %s\n", identifier.utf8().data()); 1186c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen WebNotification eventTarget(notification); 1196c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen eventTarget.dispatchCloseEvent(false); 1205ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1215ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WTF::String id(identifier.data(), identifier.length()); 1225ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_activeNotifications.remove(id); 1236c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen} 1246c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 1256c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsenvoid NotificationPresenter::objectDestroyed(const WebKit::WebNotification& notification) 1266c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen{ 1275ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WebString identifier = identifierForNotification(notification); 1285ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen WTF::String id(identifier.data(), identifier.length()); 1295ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_activeNotifications.remove(id); 1306c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen} 1316c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 1326c2af9490927c3c5959b5cb07461b646f8b32f6cKristian MonsenWebNotificationPresenter::Permission NotificationPresenter::checkPermission(const WebURL& url) 1336c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen{ 1346c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen // Check with the layout test controller 135f486d19d62f1bc33246748b14b14a9dfa617b57fIain Merrick WTF::String origin = WTF::String(static_cast<GURL>(url).GetOrigin().spec().c_str()); 1366c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen bool allowed = m_allowedOrigins.find(origin) != m_allowedOrigins.end(); 1376c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen return allowed ? WebNotificationPresenter::PermissionAllowed 1386c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen : WebNotificationPresenter::PermissionDenied; 1396c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen} 1406c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen 1416c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsenvoid NotificationPresenter::requestPermission( 1426c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen const WebSecurityOrigin& origin, 1436c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen WebNotificationPermissionCallback* callback) 1446c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen{ 1456c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen printf("DESKTOP NOTIFICATION PERMISSION REQUESTED: %s\n", 1466c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen origin.toString().utf8().data()); 1476c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen callback->permissionRequestComplete(); 1486c2af9490927c3c5959b5cb07461b646f8b32f6cKristian Monsen} 149