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

Side by Side Diff: chrome/browser/android/banners/app_banner_manager_android.cc

Issue 2124243002: Refactor the Java AppBannerManager to be owned by native code. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 5 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
1 // Copyright 2015 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/android/banners/app_banner_manager_android.h" 5 #include "chrome/browser/android/banners/app_banner_manager_android.h"
6 6
7 #include "base/android/jni_android.h" 7 #include "base/android/jni_android.h"
8 #include "base/android/jni_string.h" 8 #include "base/android/jni_string.h"
9 #include "chrome/browser/android/banners/app_banner_data_fetcher_android.h" 9 #include "chrome/browser/android/banners/app_banner_data_fetcher_android.h"
10 #include "chrome/browser/android/shortcut_helper.h" 10 #include "chrome/browser/android/shortcut_helper.h"
11 #include "chrome/browser/banners/app_banner_metrics.h" 11 #include "chrome/browser/banners/app_banner_metrics.h"
12 #include "chrome/common/chrome_constants.h" 12 #include "chrome/common/chrome_constants.h"
13 #include "content/public/browser/web_contents.h" 13 #include "content/public/browser/web_contents.h"
14 #include "content/public/common/frame_navigate_params.h" 14 #include "content/public/common/frame_navigate_params.h"
15 #include "jni/AppBannerManager_jni.h" 15 #include "jni/AppBannerManager_jni.h"
16 16
17 using base::android::ConvertJavaStringToUTF8; 17 using base::android::ConvertJavaStringToUTF8;
18 using base::android::ConvertJavaStringToUTF16; 18 using base::android::ConvertJavaStringToUTF16;
19 using base::android::ConvertUTF8ToJavaString; 19 using base::android::ConvertUTF8ToJavaString;
20 using base::android::ConvertUTF16ToJavaString; 20 using base::android::ConvertUTF16ToJavaString;
21 21
22 DEFINE_WEB_CONTENTS_USER_DATA_KEY(banners::AppBannerManagerAndroid);
23
22 namespace { 24 namespace {
23 25
24 const char kPlayPlatform[] = "play"; 26 const char kPlayPlatform[] = "play";
25 const char kReferrerName[] = "referrer"; 27 const char kReferrerName[] = "referrer";
26 const char kIdName[] = "id"; 28 const char kIdName[] = "id";
27 const char kPlayInlineReferrer[] = "playinline=chrome_inline"; 29 const char kPlayInlineReferrer[] = "playinline=chrome_inline";
28 30
29 } // anonymous namespace 31 } // anonymous namespace
30 32
31 namespace banners { 33 namespace banners {
32 34
33 AppBannerManagerAndroid::AppBannerManagerAndroid( 35 AppBannerManagerAndroid::AppBannerManagerAndroid(
34 JNIEnv* env, 36 content::WebContents* web_contents)
35 jobject obj) 37 : AppBannerManager(web_contents) {
36 : AppBannerManager(nullptr), 38 CreateJavaBannerManager();
37 weak_java_banner_view_manager_(env, obj) {
38 } 39 }
39 40
40 AppBannerManagerAndroid::~AppBannerManagerAndroid() { 41 AppBannerManagerAndroid::~AppBannerManagerAndroid() {
42 JNIEnv* env = base::android::AttachCurrentThread();
43 Java_AppBannerManager_destroy(env, java_banner_manager_.obj());
44 java_banner_manager_.Reset();
41 } 45 }
42 46
43 void AppBannerManagerAndroid::Destroy(JNIEnv* env, 47 const base::android::ScopedJavaGlobalRef<jobject>&
44 const JavaParamRef<jobject>& obj) { 48 AppBannerManagerAndroid::GetJavaBannerManager() const {
45 delete this; 49 return java_banner_manager_;
46 } 50 }
47 51
48 void AppBannerManagerAndroid::ReplaceWebContents( 52 bool AppBannerManagerAndroid::IsFetcherActive(
53 JNIEnv* env,
54 const JavaParamRef<jobject>& obj) {
55 return AppBannerManager::IsFetcherActive();
56 }
57
58 bool AppBannerManagerAndroid::OnAppDetailsRetrieved(
49 JNIEnv* env, 59 JNIEnv* env,
50 const JavaParamRef<jobject>& obj, 60 const JavaParamRef<jobject>& obj,
51 const JavaParamRef<jobject>& jweb_contents) { 61 const JavaParamRef<jobject>& japp_data,
52 content::WebContents* web_contents = 62 const JavaParamRef<jstring>& japp_title,
53 content::WebContents::FromJavaWebContents(jweb_contents); 63 const JavaParamRef<jstring>& japp_package,
54 AppBannerManager::ReplaceWebContents(web_contents); 64 const JavaParamRef<jstring>& jicon_url) {
65 AppBannerDataFetcherAndroid* android_fetcher =
66 static_cast<AppBannerDataFetcherAndroid*>(data_fetcher().get());
67 if (!CheckFetcherMatchesContents(android_fetcher->is_debug_mode()))
68 return false;
69
70 GURL image_url = GURL(ConvertJavaStringToUTF8(env, jicon_url));
71
72 return android_fetcher->ContinueFetching(
73 ConvertJavaStringToUTF16(env, japp_title),
74 ConvertJavaStringToUTF8(env, japp_package), japp_data, image_url);
75 }
76
77 void AppBannerManagerAndroid::RequestAppBanner(const GURL& validated_url,
78 bool is_debug_mode) {
79 JNIEnv* env = base::android::AttachCurrentThread();
80 if (!Java_AppBannerManager_isEnabled(env))
81 return;
82
83 AppBannerManager::RequestAppBanner(validated_url, is_debug_mode);
84 }
85
86 AppBannerDataFetcher* AppBannerManagerAndroid::CreateAppBannerDataFetcher(
87 base::WeakPtr<Delegate> weak_delegate,
88 bool is_debug_mode) {
89 return new AppBannerDataFetcherAndroid(
90 web_contents(), weak_delegate,
91 ShortcutHelper::GetIdealHomescreenIconSizeInDp(),
92 ShortcutHelper::GetMinimumHomescreenIconSizeInDp(),
93 ShortcutHelper::GetIdealSplashImageSizeInDp(),
94 ShortcutHelper::GetMinimumSplashImageSizeInDp(), is_debug_mode);
55 } 95 }
56 96
57 bool AppBannerManagerAndroid::HandleNonWebApp(const std::string& platform, 97 bool AppBannerManagerAndroid::HandleNonWebApp(const std::string& platform,
58 const GURL& url, 98 const GURL& url,
59 const std::string& id, 99 const std::string& id,
60 bool is_debug_mode) { 100 bool is_debug_mode) {
61 if (!CheckPlatformAndId(platform, id, is_debug_mode)) 101 if (!CheckPlatformAndId(platform, id, is_debug_mode))
62 return false; 102 return false;
63 103
64 banners::TrackDisplayEvent(DISPLAY_EVENT_NATIVE_APP_BANNER_REQUESTED); 104 banners::TrackDisplayEvent(DISPLAY_EVENT_NATIVE_APP_BANNER_REQUESTED);
65 105
66 // Send the info to the Java side to get info about the app. 106 // Send the info to the Java side to get info about the app.
67 JNIEnv* env = base::android::AttachCurrentThread(); 107 JNIEnv* env = base::android::AttachCurrentThread();
68 ScopedJavaLocalRef<jobject> jobj = weak_java_banner_view_manager_.get(env); 108 if (java_banner_manager_.is_null())
69 if (jobj.is_null())
70 return false; 109 return false;
71 110
72 std::string id_from_app_url = ExtractQueryValueForName(url, kIdName); 111 std::string id_from_app_url = ExtractQueryValueForName(url, kIdName);
73 if (id_from_app_url.size() && id != id_from_app_url) { 112 if (id_from_app_url.size() && id != id_from_app_url) {
74 banners::OutputDeveloperNotShownMessage( 113 banners::OutputDeveloperNotShownMessage(
75 web_contents(), banners::kIgnoredIdsDoNotMatch, is_debug_mode); 114 web_contents(), banners::kIgnoredIdsDoNotMatch, is_debug_mode);
76 return false; 115 return false;
77 } 116 }
78 117
79 std::string referrer = 118 std::string referrer =
80 ExtractQueryValueForName(url, kReferrerName); 119 ExtractQueryValueForName(url, kReferrerName);
81 120
82 // Attach the chrome_inline referrer value, prefixed with "&" if the referrer 121 // Attach the chrome_inline referrer value, prefixed with "&" if the referrer
83 // is non empty. 122 // is non empty.
84 if (referrer.empty()) 123 if (referrer.empty())
85 referrer = kPlayInlineReferrer; 124 referrer = kPlayInlineReferrer;
86 else 125 else
87 referrer.append("&").append(kPlayInlineReferrer); 126 referrer.append("&").append(kPlayInlineReferrer);
88 127
89 ScopedJavaLocalRef<jstring> jurl( 128 ScopedJavaLocalRef<jstring> jurl(
90 ConvertUTF8ToJavaString(env, data_fetcher()->validated_url().spec())); 129 ConvertUTF8ToJavaString(env, data_fetcher()->validated_url().spec()));
91 ScopedJavaLocalRef<jstring> jpackage( 130 ScopedJavaLocalRef<jstring> jpackage(
92 ConvertUTF8ToJavaString(env, id)); 131 ConvertUTF8ToJavaString(env, id));
93 ScopedJavaLocalRef<jstring> jreferrer( 132 ScopedJavaLocalRef<jstring> jreferrer(
94 ConvertUTF8ToJavaString(env, referrer)); 133 ConvertUTF8ToJavaString(env, referrer));
95 Java_AppBannerManager_fetchAppDetails( 134 Java_AppBannerManager_fetchAppDetails(
96 env, jobj.obj(), jurl.obj(), 135 env, java_banner_manager_.obj(), jurl.obj(),
97 jpackage.obj(), jreferrer.obj(), 136 jpackage.obj(), jreferrer.obj(),
98 ShortcutHelper::GetIdealHomescreenIconSizeInDp()); 137 ShortcutHelper::GetIdealHomescreenIconSizeInDp());
99 return true; 138 return true;
100 } 139 }
101 140
141 void AppBannerManagerAndroid::CreateJavaBannerManager() {
142 JNIEnv* env = base::android::AttachCurrentThread();
143 java_banner_manager_.Reset(
144 Java_AppBannerManager_create(env, reinterpret_cast<intptr_t>(this)));
145 }
146
147 bool AppBannerManagerAndroid::CheckFetcherMatchesContents(bool is_debug_mode) {
148 if (!web_contents())
149 return false;
150
151 if (!data_fetcher() ||
152 data_fetcher()->validated_url() != web_contents()->GetURL()) {
153 banners::OutputDeveloperNotShownMessage(
154 web_contents(), banners::kUserNavigatedBeforeBannerShown,
155 is_debug_mode);
156 return false;
157 }
158 return true;
159 }
160
102 bool AppBannerManagerAndroid::CheckPlatformAndId(const std::string& platform, 161 bool AppBannerManagerAndroid::CheckPlatformAndId(const std::string& platform,
103 const std::string& id, 162 const std::string& id,
104 bool is_debug_mode) { 163 bool is_debug_mode) {
105 if (platform != kPlayPlatform) { 164 if (platform != kPlayPlatform) {
106 banners::OutputDeveloperNotShownMessage( 165 banners::OutputDeveloperNotShownMessage(
107 web_contents(), banners::kIgnoredNotSupportedOnAndroid, platform, 166 web_contents(), banners::kIgnoredNotSupportedOnAndroid, platform,
108 is_debug_mode); 167 is_debug_mode);
109 return false; 168 return false;
110 } 169 }
111 if (id.empty()) { 170 if (id.empty()) {
112 banners::OutputDeveloperNotShownMessage( 171 banners::OutputDeveloperNotShownMessage(
113 web_contents(), banners::kIgnoredNoId, is_debug_mode); 172 web_contents(), banners::kIgnoredNoId, is_debug_mode);
114 return false; 173 return false;
115 } 174 }
116 return true; 175 return true;
117 } 176 }
118 177
119 bool AppBannerManagerAndroid::CheckFetcherMatchesContents(bool is_debug_mode) {
120 if (!web_contents())
121 return false;
122
123 if (!data_fetcher() ||
124 data_fetcher()->validated_url() != web_contents()->GetURL()) {
125 banners::OutputDeveloperNotShownMessage(
126 web_contents(), banners::kUserNavigatedBeforeBannerShown,
127 is_debug_mode);
128 return false;
129 }
130 return true;
131 }
132
133 std::string AppBannerManagerAndroid::ExtractQueryValueForName( 178 std::string AppBannerManagerAndroid::ExtractQueryValueForName(
134 const GURL& url, 179 const GURL& url,
135 const std::string& name) { 180 const std::string& name) {
136 url::Component query = url.parsed_for_possibly_invalid_spec().query; 181 url::Component query = url.parsed_for_possibly_invalid_spec().query;
137 url::Component key, value; 182 url::Component key, value;
138 const char* url_spec = url.spec().c_str(); 183 const char* url_spec = url.spec().c_str();
139 184
140 while (url::ExtractQueryKeyValue(url_spec, &query, &key, &value)) { 185 while (url::ExtractQueryKeyValue(url_spec, &query, &key, &value)) {
141 std::string key_str(url_spec, key.begin, key.len); 186 std::string key_str(url_spec, key.begin, key.len);
142 std::string value_str(url_spec, value.begin, value.len); 187 std::string value_str(url_spec, value.begin, value.len);
143 if (key_str == name) 188 if (key_str == name)
144 return value_str; 189 return value_str;
145 } 190 }
146 return ""; 191 return "";
147 } 192 }
148 193
149 AppBannerDataFetcher* AppBannerManagerAndroid::CreateAppBannerDataFetcher(
150 base::WeakPtr<Delegate> weak_delegate,
151 bool is_debug_mode) {
152 return new AppBannerDataFetcherAndroid(
153 web_contents(), weak_delegate,
154 ShortcutHelper::GetIdealHomescreenIconSizeInDp(),
155 ShortcutHelper::GetMinimumHomescreenIconSizeInDp(),
156 ShortcutHelper::GetIdealSplashImageSizeInDp(),
157 ShortcutHelper::GetMinimumSplashImageSizeInDp(), is_debug_mode);
158 }
159
160 bool AppBannerManagerAndroid::OnAppDetailsRetrieved(
161 JNIEnv* env,
162 const JavaParamRef<jobject>& obj,
163 const JavaParamRef<jobject>& japp_data,
164 const JavaParamRef<jstring>& japp_title,
165 const JavaParamRef<jstring>& japp_package,
166 const JavaParamRef<jstring>& jicon_url) {
167 AppBannerDataFetcherAndroid* android_fetcher =
168 static_cast<AppBannerDataFetcherAndroid*>(data_fetcher().get());
169 if (!CheckFetcherMatchesContents(android_fetcher->is_debug_mode()))
170 return false;
171
172 GURL image_url = GURL(ConvertJavaStringToUTF8(env, jicon_url));
173
174 return android_fetcher->ContinueFetching(
175 ConvertJavaStringToUTF16(env, japp_title),
176 ConvertJavaStringToUTF8(env, japp_package), japp_data, image_url);
177 }
178
179 bool AppBannerManagerAndroid::IsFetcherActive(
180 JNIEnv* env,
181 const JavaParamRef<jobject>& obj) {
182 return AppBannerManager::IsFetcherActive();
183 }
184
185 void AppBannerManagerAndroid::RequestAppBanner(
186 JNIEnv* env,
187 const JavaParamRef<jobject>& obj) {
188 // Set debug mode to true as this method is only called from DevTools.
189 AppBannerManager::RequestAppBanner(web_contents()->GetLastCommittedURL(),
190 true /* is_debug_mode */);
191 }
192
193 // static 194 // static
194 bool AppBannerManagerAndroid::Register(JNIEnv* env) { 195 bool AppBannerManagerAndroid::Register(JNIEnv* env) {
195 return RegisterNativesImpl(env); 196 return RegisterNativesImpl(env);
196 } 197 }
197 198
198 jlong Init(JNIEnv* env, 199 // static
199 const JavaParamRef<jobject>& obj) { 200 ScopedJavaLocalRef<jobject> GetJavaBannerManagerForWebContents(
200 AppBannerManagerAndroid* manager = new AppBannerManagerAndroid(env, obj); 201 JNIEnv* env,
201 return reinterpret_cast<intptr_t>(manager); 202 const JavaParamRef<jclass>& clazz,
203 const JavaParamRef<jobject>& java_web_contents) {
204 AppBannerManagerAndroid* manager = AppBannerManagerAndroid::FromWebContents(
205 content::WebContents::FromJavaWebContents(java_web_contents));
206 if (!manager)
207 return ScopedJavaLocalRef<jobject>();
208
209 return ScopedJavaLocalRef<jobject>(manager->GetJavaBannerManager());
202 } 210 }
203 211
204 void SetTimeDeltaForTesting(JNIEnv* env, 212 // static
205 const JavaParamRef<jclass>& clazz,
206 jint days) {
207 AppBannerDataFetcher::SetTimeDeltaForTesting(days);
208 }
209
210 void DisableSecureSchemeCheckForTesting(JNIEnv* env, 213 void DisableSecureSchemeCheckForTesting(JNIEnv* env,
211 const JavaParamRef<jclass>& clazz) { 214 const JavaParamRef<jclass>& clazz) {
212 AppBannerManager::DisableSecureSchemeCheckForTesting(); 215 AppBannerManager::DisableSecureSchemeCheckForTesting();
213 } 216 }
214 217
218 // static
215 void SetEngagementWeights(JNIEnv* env, 219 void SetEngagementWeights(JNIEnv* env,
216 const JavaParamRef<jclass>& clazz, 220 const JavaParamRef<jclass>& clazz,
217 jdouble direct_engagement, 221 jdouble direct_engagement,
218 jdouble indirect_engagement) { 222 jdouble indirect_engagement) {
219 AppBannerManager::SetEngagementWeights(direct_engagement, 223 AppBannerManager::SetEngagementWeights(direct_engagement,
220 indirect_engagement); 224 indirect_engagement);
221 } 225 }
222 226
227 // static
228 void SetTimeDeltaForTesting(JNIEnv* env,
229 const JavaParamRef<jclass>& clazz,
230 jint days) {
231 AppBannerDataFetcher::SetTimeDeltaForTesting(days);
232 }
233
223 } // namespace banners 234 } // namespace banners
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698