Fix breakages in https://codereview.chromium.org/1155713003/
[chromium-blink-merge.git] / ios / web / web_state / ui / wk_web_view_configuration_provider.mm
blobf5015a1fa3ce0b508493b16b8df2b740c2fde3ca
1 // Copyright 2015 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.
5 #import "ios/web/web_state/ui/wk_web_view_configuration_provider.h"
7 #import <Foundation/Foundation.h>
8 #import <WebKit/WebKit.h>
10 #import "base/ios/weak_nsobject.h"
11 #import "base/logging.h"
12 #import "ios/web/alloc_with_zone_interceptor.h"
13 #include "ios/web/public/browser_state.h"
14 #import "ios/web/web_state/js/page_script_util.h"
16 #if !defined(NDEBUG)
18 namespace {
19 BOOL gAllowWKProcessPoolCreation = NO;
22 @interface WKProcessPool (CRWAdditions)
23 @end
25 @implementation WKProcessPool (CRWAdditions)
27 + (void)load {
28   id (^allocator)(Class klass, NSZone* zone) = ^id(Class klass, NSZone* zone) {
29     if (gAllowWKProcessPoolCreation) {
30       return NSAllocateObject(klass, 0, zone);
31     }
32     // You have hit this because you are trying to create a WKProcessPool
33     // directly or indirectly (f.e. by creating WKWebViewConfiguration
34     // manually). Please use GetWebViewConfiguration() to get
35     // WKWebViewConfiguration object.
36     NOTREACHED();
37     return nil;
38   };
39   web::AddAllocWithZoneMethod([WKProcessPool class], allocator);
42 @end
44 #endif  // !defined(NDEBUG)
46 namespace web {
48 namespace {
49 // A key used to associate a WKWebViewConfigurationProvider with a BrowserState.
50 const char kWKWebViewConfigProviderKeyName[] = "wk_web_view_config_provider";
52 // Returns an autoreleased instance of WKUserScript to be added to
53 // configuration's userContentController.
54 WKUserScript* GetEarlyPageScript() {
55   return [[[WKUserScript alloc]
56         initWithSource:GetEarlyPageScript(WK_WEB_VIEW_TYPE)
57          injectionTime:WKUserScriptInjectionTimeAtDocumentStart
58       forMainFrameOnly:YES] autorelease];
61 }  // namespace
63 // static
64 WKWebViewConfigurationProvider&
65 WKWebViewConfigurationProvider::FromBrowserState(BrowserState* browser_state) {
66   DCHECK([NSThread isMainThread]);
67   DCHECK(browser_state);
68   if (!browser_state->GetUserData(kWKWebViewConfigProviderKeyName)) {
69     browser_state->SetUserData(kWKWebViewConfigProviderKeyName,
70                                new WKWebViewConfigurationProvider());
71   }
72   return *(static_cast<WKWebViewConfigurationProvider*>(
73       browser_state->GetUserData(kWKWebViewConfigProviderKeyName)));
76 WKWebViewConfigurationProvider::WKWebViewConfigurationProvider() {
79 WKWebViewConfigurationProvider::~WKWebViewConfigurationProvider() {
82 WKWebViewConfiguration*
83 WKWebViewConfigurationProvider::GetWebViewConfiguration() {
84   DCHECK([NSThread isMainThread]);
85   if (!configuration_) {
86     configuration_.reset([[WKWebViewConfiguration alloc] init]);
87     // setJavaScriptCanOpenWindowsAutomatically is required to support popups.
88     [[configuration_ preferences] setJavaScriptCanOpenWindowsAutomatically:YES];
89     [[configuration_ userContentController] addUserScript:GetEarlyPageScript()];
90 #if !defined(NDEBUG)
91     // Lazily load WKProcessPool. -[[WKProcessPool alloc] init] call is not
92     // allowed except when creating config object inside this class.
93     // Unmanaged creation of WKProcessPool may lead to issues with cookie
94     // clearing and Browsing Data Partitioning implementation.
95     gAllowWKProcessPoolCreation = YES;
96     CHECK([configuration_ processPool]);
97     gAllowWKProcessPoolCreation = NO;
98 #endif  // !defined(NDEBUG)
99   }
100   // Prevent callers from changing the internals of configuration.
101   return [[configuration_ copy] autorelease];
104 bool WKWebViewConfigurationProvider::HasWebViewConfiguration() const {
105   DCHECK([NSThread isMainThread]);
106   return configuration_;
109 void WKWebViewConfigurationProvider::Purge() {
110   DCHECK([NSThread isMainThread]);
111 #if !defined(NDEBUG) || !defined(DCHECK_ALWAYS_ON)  // Matches DCHECK_IS_ON.
112   base::WeakNSObject<id> weak_configuration(configuration_);
113   base::WeakNSObject<id> weak_process_pool([configuration_ processPool]);
114 #endif  // !defined(NDEBUG) || defined(DCHECK_ALWAYS_ON)
115   configuration_.reset();
116   // Make sure that no one retains configuration and processPool.
117   DCHECK(!weak_configuration);
118   DCHECK(!weak_process_pool);
121 }  // namespace web