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

Side by Side Diff: chrome/android/java/src/org/chromium/chrome/browser/externalnav/ExternalNavigationHandler.java

Issue 1039013002: Use fallback URL more extensively (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 5 years, 9 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
« no previous file with comments | « no previous file | chrome/android/java/src/org/chromium/chrome/browser/tab/TabRedirectHandler.java » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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 package org.chromium.chrome.browser.externalnav; 5 package org.chromium.chrome.browser.externalnav;
6 6
7 import android.annotation.TargetApi; 7 import android.annotation.TargetApi;
8 import android.app.Activity; 8 import android.app.Activity;
9 import android.content.ActivityNotFoundException; 9 import android.content.ActivityNotFoundException;
10 import android.content.ComponentName; 10 import android.content.ComponentName;
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after
101 // - http://crbug.com/159153 : Don't override http or https URLs from th e NTP or bookmarks. 101 // - http://crbug.com/159153 : Don't override http or https URLs from th e NTP or bookmarks.
102 // - http://crbug.com/162106: Intent picker should not be presented on r eturning to a page. 102 // - http://crbug.com/162106: Intent picker should not be presented on r eturning to a page.
103 // This should be covered by not showing the picker if the core type i s reload. 103 // This should be covered by not showing the picker if the core type i s reload.
104 104
105 // http://crbug.com/164194 . A navigation forwards or backwards should n ever trigger 105 // http://crbug.com/164194 . A navigation forwards or backwards should n ever trigger
106 // the intent picker. 106 // the intent picker.
107 if (isForwardBackNavigation) { 107 if (isForwardBackNavigation) {
108 return OverrideUrlLoadingResult.NO_OVERRIDE; 108 return OverrideUrlLoadingResult.NO_OVERRIDE;
109 } 109 }
110 110
111 // http://crbug/331571 : Do not override a navigation started from user typing. 111 Intent intent;
112 // http://crbug/424029 : Need to stay in Chrome for an intent heading ex plicitly to Chrome. 112 // perform generic parsing of the URI to turn it into an Intent.
113 if (params.getRedirectHandler() != null 113 try {
114 && params.getRedirectHandler().shouldStayInChrome()) { 114 intent = Intent.parseUri(params.getUrl(), Intent.URI_INTENT_SCHEME);
115 } catch (URISyntaxException ex) {
116 Log.w(TAG, "Bad URI " + params.getUrl() + ": " + ex.getMessage());
115 return OverrideUrlLoadingResult.NO_OVERRIDE; 117 return OverrideUrlLoadingResult.NO_OVERRIDE;
116 } 118 }
117 119
120 boolean hasBrowserFallbackUrl = false;
121 String browserFallbackUrl = intent.getStringExtra(EXTRA_BROWSER_FALLBACK _URL);
122 if (browserFallbackUrl != null
123 && UrlUtilities.isValidForIntentFallbackNavigation(browserFallba ckUrl)) {
124 hasBrowserFallbackUrl = true;
125 }
126
127 if (params.getRedirectHandler() != null) {
128 // http://crbug/331571 : Do not override a navigation started from u ser typing.
129 // http://crbug/424029 : Need to stay in Chrome for an intent headin g explicitly to
130 // Chrome.
131 if (params.getRedirectHandler().shouldStayInChrome()) {
132 if (hasBrowserFallbackUrl) {
133 return clobberCurrentTabWithFallbackUrl(browserFallbackUrl, params);
134 } else {
135 return OverrideUrlLoadingResult.NO_OVERRIDE;
136 }
137 } else if (params.getRedirectHandler().shouldNotOverrideUrlLoading() ) {
138 // For instance, if this is a chained fallback URL, we ignore it .
139 return OverrideUrlLoadingResult.NO_OVERRIDE;
140 }
141 }
142
118 // http://crbug.com/149218: We want to show the intent picker for ordina ry links, providing 143 // http://crbug.com/149218: We want to show the intent picker for ordina ry links, providing
119 // the link is not an incoming intent from another application, unless i t's a redirect (see 144 // the link is not an incoming intent from another application, unless i t's a redirect (see
120 // below). 145 // below).
121 boolean linkNotFromIntent = isLink && !isFromIntent; 146 boolean linkNotFromIntent = isLink && !isFromIntent;
122 147
123 boolean isOnEffectiveIntentRedirect = params.getRedirectHandler() == nul l ? false 148 boolean isOnEffectiveIntentRedirect = params.getRedirectHandler() == nul l ? false
124 : params.getRedirectHandler().isOnEffectiveIntentRedirectChain() ; 149 : params.getRedirectHandler().isOnEffectiveIntentRedirectChain() ;
125 150
126 // http://crbug.com/170925: We need to show the intent picker when we re ceive an intent from 151 // http://crbug.com/170925: We need to show the intent picker when we re ceive an intent from
127 // another app that 30x redirects to a YouTube/Google Maps/Play Store/Go ogle+ URL etc. 152 // another app that 30x redirects to a YouTube/Google Maps/Play Store/Go ogle+ URL etc.
(...skipping 13 matching lines...) Expand all
141 // page, there is clear intent to complete the navigation in Chrome. 166 // page, there is clear intent to complete the navigation in Chrome.
142 if (params.getReferrerUrl() != null && params.getReferrerUrl().startsWit h( 167 if (params.getReferrerUrl() != null && params.getReferrerUrl().startsWit h(
143 UrlConstants.CHROME_SCHEME) && (params.getUrl().startsWith(UrlCo nstants.HTTP_SCHEME) 168 UrlConstants.CHROME_SCHEME) && (params.getUrl().startsWith(UrlCo nstants.HTTP_SCHEME)
144 || params.getUrl().startsWith(UrlConstants.HTTPS_SCHEME) )) { 169 || params.getUrl().startsWith(UrlConstants.HTTPS_SCHEME) )) {
145 return OverrideUrlLoadingResult.NO_OVERRIDE; 170 return OverrideUrlLoadingResult.NO_OVERRIDE;
146 } 171 }
147 172
148 if (params.getUrl().startsWith(SCHEME_WTAI_MC)) { 173 if (params.getUrl().startsWith(SCHEME_WTAI_MC)) {
149 // wtai://wp/mc;number 174 // wtai://wp/mc;number
150 // number=string(phone-number) 175 // number=string(phone-number)
151 Intent intent = new Intent(Intent.ACTION_VIEW, 176 mDelegate.startActivity(new Intent(Intent.ACTION_VIEW,
152 Uri.parse(WebView.SCHEME_TEL 177 Uri.parse(WebView.SCHEME_TEL
153 + params.getUrl().substring(SCHEME_WTAI_MC.length()) )); 178 + params.getUrl().substring(SCHEME_WTAI_MC.length()) )));
154 mDelegate.startActivity(intent);
155 return OverrideUrlLoadingResult.OVERRIDE_WITH_EXTERNAL_INTENT; 179 return OverrideUrlLoadingResult.OVERRIDE_WITH_EXTERNAL_INTENT;
156 } else if (params.getUrl().startsWith(SCHEME_WTAI)) { 180 } else if (params.getUrl().startsWith(SCHEME_WTAI)) {
157 // TODO: handle other WTAI schemes. 181 // TODO: handle other WTAI schemes.
158 return OverrideUrlLoadingResult.NO_OVERRIDE; 182 return OverrideUrlLoadingResult.NO_OVERRIDE;
159 } 183 }
160 184
161 // The "about:" schemes are internal to the browser; don't want these to 185 // The "about:" schemes are internal to the browser; don't want these to
162 // be dispatched to other apps. 186 // be dispatched to other apps.
163 if (params.getUrl().startsWith("about:")) { 187 if (params.getUrl().startsWith("about:")) {
164 return OverrideUrlLoadingResult.NO_OVERRIDE; 188 return OverrideUrlLoadingResult.NO_OVERRIDE;
(...skipping 11 matching lines...) Expand all
176 if (params.getUrl().matches(".*youtube\\.com.*[?&]pairingCode=.*")) { 200 if (params.getUrl().matches(".*youtube\\.com.*[?&]pairingCode=.*")) {
177 return OverrideUrlLoadingResult.NO_OVERRIDE; 201 return OverrideUrlLoadingResult.NO_OVERRIDE;
178 } 202 }
179 203
180 // TODO(changwan): check if we need to handle URL even when external int ent is off. 204 // TODO(changwan): check if we need to handle URL even when external int ent is off.
181 if (CommandLine.getInstance().hasSwitch( 205 if (CommandLine.getInstance().hasSwitch(
182 ChromeSwitches.DISABLE_EXTERNAL_INTENT_REQUESTS)) { 206 ChromeSwitches.DISABLE_EXTERNAL_INTENT_REQUESTS)) {
183 return OverrideUrlLoadingResult.NO_OVERRIDE; 207 return OverrideUrlLoadingResult.NO_OVERRIDE;
184 } 208 }
185 209
186 Intent intent;
187 // perform generic parsing of the URI to turn it into an Intent.
188 try {
189 intent = Intent.parseUri(params.getUrl(), Intent.URI_INTENT_SCHEME);
190 } catch (URISyntaxException ex) {
191 Log.w(TAG, "Bad URI " + params.getUrl() + ": " + ex.getMessage());
192 return OverrideUrlLoadingResult.NO_OVERRIDE;
193 }
194
195 boolean hasBrowserFallbackUrl = false;
196 String browserFallbackUrl = intent.getStringExtra(EXTRA_BROWSER_FALLBACK _URL);
197 if (browserFallbackUrl != null
198 && UrlUtilities.isValidForIntentFallbackNavigation(browserFallba ckUrl)) {
199 hasBrowserFallbackUrl = true;
200 }
201
202 // check whether the intent can be resolved. If not, we will see 210 // check whether the intent can be resolved. If not, we will see
203 // whether we can download it from the Market. 211 // whether we can download it from the Market.
204 if (!mDelegate.canResolveActivity(intent)) { 212 if (!mDelegate.canResolveActivity(intent)) {
205 if (hasBrowserFallbackUrl) { 213 if (hasBrowserFallbackUrl) {
206 // NOTE: any further redirection from fall-back URL should not o verride URL loading. 214 return clobberCurrentTabWithFallbackUrl(browserFallbackUrl, para ms);
207 // Otherwise, it can be used in chain for fingerprinting multipl e app installation
208 // status in one shot. In order to prevent this scenario, we not ify redirection
209 // handler that redirection from the current navigation should s tay in Chrome.
210 if (params.getRedirectHandler() != null) {
211 params.getRedirectHandler()
212 .setShouldStayInChromeUntilNewUrlLoading();
213 }
214 return mDelegate.clobberCurrentTab(browserFallbackUrl, params.ge tReferrerUrl(),
215 params.getTab());
216 } 215 }
217 String packagename = intent.getPackage(); 216 String packagename = intent.getPackage();
218 if (packagename != null) { 217 if (packagename != null) {
219 try { 218 try {
220 intent = new Intent(Intent.ACTION_VIEW, Uri.parse( 219 intent = new Intent(Intent.ACTION_VIEW, Uri.parse(
221 "market://details?id=" + packagename 220 "market://details?id=" + packagename
222 + "&referrer=" + mDelegate.getPackageName())); 221 + "&referrer=" + mDelegate.getPackageName()));
223 intent.addCategory(Intent.CATEGORY_BROWSABLE); 222 intent.addCategory(Intent.CATEGORY_BROWSABLE);
224 intent.setPackage("com.android.vending"); 223 intent.setPackage("com.android.vending");
225 mDelegate.startActivity(intent); 224 mDelegate.startActivity(intent);
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after
332 } 331 }
333 } catch (ActivityNotFoundException ex) { 332 } catch (ActivityNotFoundException ex) {
334 // Ignore the error. If no application can handle the URL, 333 // Ignore the error. If no application can handle the URL,
335 // assume the browser can handle it. 334 // assume the browser can handle it.
336 } 335 }
337 336
338 return OverrideUrlLoadingResult.NO_OVERRIDE; 337 return OverrideUrlLoadingResult.NO_OVERRIDE;
339 } 338 }
340 339
341 /** 340 /**
341 * Clobber the current tab with fallback URL.
342 *
343 * @param browserFallbackUrl The fallback URL.
344 * @param params The external navigation params.
345 * @return {@link OverrideUrlLoadingResult} (if the tab was clobbered, or we launched an
346 *intent.)
Maria 2015/03/27 00:12:59 indent 8 on second line and don't need parenthesis
Changwan Ryu 2015/03/27 02:09:50 Done.
347 */
348 private OverrideUrlLoadingResult clobberCurrentTabWithFallbackUrl(
349 String browserFallbackUrl, ExternalNavigationParams params) {
350 // NOTE: any further redirection from fall-back URL should not override URL loading.
351 // Otherwise, it can be used in chain for fingerprinting multiple app in stallation
352 // status in one shot. In order to prevent this scenario, we notify redi rection
353 // handler that redirection from the current navigation should stay in C hrome.
354 if (params.getRedirectHandler() != null) {
355 params.getRedirectHandler().setShouldNotOverrideUrlLoadingUntilNewUr lLoading();
356 }
357 return mDelegate.clobberCurrentTab(
358 browserFallbackUrl, params.getReferrerUrl(), params.getTab());
359 }
360
361 /**
342 * @return Whether the |url| could be handled by an external application on the system. 362 * @return Whether the |url| could be handled by an external application on the system.
343 */ 363 */
344 public boolean canExternalAppHandleUrl(String url) { 364 public boolean canExternalAppHandleUrl(String url) {
345 if (url.startsWith(SCHEME_WTAI_MC)) return true; 365 if (url.startsWith(SCHEME_WTAI_MC)) return true;
346 try { 366 try {
347 Intent intent = Intent.parseUri(url, Intent.URI_INTENT_SCHEME); 367 Intent intent = Intent.parseUri(url, Intent.URI_INTENT_SCHEME);
348 return intent.getPackage() != null || mDelegate.canResolveActivity(i ntent); 368 return intent.getPackage() != null || mDelegate.canResolveActivity(i ntent);
349 } catch (URISyntaxException ex) { 369 } catch (URISyntaxException ex) {
350 // Ignore the error. 370 // Ignore the error.
351 } 371 }
352 return false; 372 return false;
353 } 373 }
354 } 374 }
OLDNEW
« no previous file with comments | « no previous file | chrome/android/java/src/org/chromium/chrome/browser/tab/TabRedirectHandler.java » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698