| OLD | NEW |
| 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.webapps; | 5 package org.chromium.chrome.browser.webapps; |
| 6 | 6 |
| 7 import android.content.Context; | 7 import android.content.Context; |
| 8 import android.content.Intent; | 8 import android.content.Intent; |
| 9 import android.content.SharedPreferences; | 9 import android.content.SharedPreferences; |
| 10 import android.graphics.Bitmap; | 10 import android.graphics.Bitmap; |
| (...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 77 // updates less frequently. crbug.com/680128. | 77 // updates less frequently. crbug.com/680128. |
| 78 public static final long RELAXED_UPDATE_INTERVAL = TimeUnit.DAYS.toMillis(30
L); | 78 public static final long RELAXED_UPDATE_INTERVAL = TimeUnit.DAYS.toMillis(30
L); |
| 79 | 79 |
| 80 // Number of milliseconds to wait before re-requesting an updated WebAPK fro
m the WebAPK | 80 // Number of milliseconds to wait before re-requesting an updated WebAPK fro
m the WebAPK |
| 81 // server if the previous update attempt failed. | 81 // server if the previous update attempt failed. |
| 82 public static final long RETRY_UPDATE_DURATION = TimeUnit.HOURS.toMillis(12L
); | 82 public static final long RETRY_UPDATE_DURATION = TimeUnit.HOURS.toMillis(12L
); |
| 83 | 83 |
| 84 // The default shell Apk version of WebAPKs. | 84 // The default shell Apk version of WebAPKs. |
| 85 static final int DEFAULT_SHELL_APK_VERSION = 1; | 85 static final int DEFAULT_SHELL_APK_VERSION = 1; |
| 86 | 86 |
| 87 // Unset/invalid constants for last used times and URLs. 0 is used as the nu
ll last used time as | 87 // Invalid constants for timestamps and URLs. '0' is used as the invalid tim
estamp as |
| 88 // WebappRegistry assumes that this is always a valid timestamp. | 88 // WebappRegistry and WebApkUpdateManager assume that timestamps are always
valid. |
| 89 static final long LAST_USED_UNSET = 0; | 89 static final long TIMESTAMP_INVALID = 0; |
| 90 static final long LAST_USED_INVALID = -1; | |
| 91 static final String URL_INVALID = ""; | 90 static final String URL_INVALID = ""; |
| 92 static final int VERSION_INVALID = 0; | 91 static final int VERSION_INVALID = 0; |
| 93 | 92 |
| 94 // We use a heuristic to determine whether a web app is still installed on t
he home screen, as | 93 // We use a heuristic to determine whether a web app is still installed on t
he home screen, as |
| 95 // there is no way to do so directly. Any web app which has been opened in t
he last ten days | 94 // there is no way to do so directly. Any web app which has been opened in t
he last ten days |
| 96 // is considered to be still on the home screen. | 95 // is considered to be still on the home screen. |
| 97 static final long WEBAPP_LAST_OPEN_MAX_TIME = TimeUnit.DAYS.toMillis(10L); | 96 static final long WEBAPP_LAST_OPEN_MAX_TIME = TimeUnit.DAYS.toMillis(10L); |
| 98 | 97 |
| 99 private static Clock sClock = new Clock(); | 98 private static Clock sClock = new Clock(); |
| 100 private static Factory sFactory = new Factory(); | 99 private static Factory sFactory = new Factory(); |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 132 */ | 131 */ |
| 133 public long currentTimeMillis() { | 132 public long currentTimeMillis() { |
| 134 return System.currentTimeMillis(); | 133 return System.currentTimeMillis(); |
| 135 } | 134 } |
| 136 } | 135 } |
| 137 | 136 |
| 138 /** | 137 /** |
| 139 * Opens an instance of WebappDataStorage for the web app specified. | 138 * Opens an instance of WebappDataStorage for the web app specified. |
| 140 * @param webappId The ID of the web app. | 139 * @param webappId The ID of the web app. |
| 141 */ | 140 */ |
| 142 static WebappDataStorage open(final String webappId) { | 141 static WebappDataStorage open(String webappId) { |
| 143 final WebappDataStorage storage = sFactory.create(webappId); | 142 return sFactory.create(webappId); |
| 144 if (storage.getLastUsedTime() == LAST_USED_INVALID) { | |
| 145 // If the last used time is invalid then ensure that there is no dat
a in the | |
| 146 // WebappDataStorage which needs to be cleaned up. | |
| 147 assert storage.isEmpty(); | |
| 148 } | |
| 149 return storage; | |
| 150 } | 143 } |
| 151 | 144 |
| 152 /** | 145 /** |
| 153 * Sets the clock used to get the current time. | 146 * Sets the clock used to get the current time. |
| 154 */ | 147 */ |
| 155 @VisibleForTesting | 148 @VisibleForTesting |
| 156 public static void setClockForTests(Clock clock) { | 149 public static void setClockForTests(Clock clock) { |
| 157 sClock = clock; | 150 sClock = clock; |
| 158 } | 151 } |
| 159 | 152 |
| (...skipping 154 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 314 mPreferences.edit().clear().apply(); | 307 mPreferences.edit().clear().apply(); |
| 315 } | 308 } |
| 316 | 309 |
| 317 /** | 310 /** |
| 318 * Deletes the URL and scope, and sets all timestamps to 0 in SharedPreferen
ces. | 311 * Deletes the URL and scope, and sets all timestamps to 0 in SharedPreferen
ces. |
| 319 * This does not remove the stored splash screen image (if any) for the app. | 312 * This does not remove the stored splash screen image (if any) for the app. |
| 320 */ | 313 */ |
| 321 void clearHistory() { | 314 void clearHistory() { |
| 322 SharedPreferences.Editor editor = mPreferences.edit(); | 315 SharedPreferences.Editor editor = mPreferences.edit(); |
| 323 | 316 |
| 324 // The last used time is set to 0 to ensure that a valid value is always
present. | 317 editor.remove(KEY_LAST_USED); |
| 325 // If the web app is not launched prior to the next cleanup, then its re
maining data will be | |
| 326 // removed. Otherwise, the next launch from home screen will update the
last used time. | |
| 327 editor.putLong(KEY_LAST_USED, LAST_USED_UNSET); | |
| 328 editor.remove(KEY_URL); | 318 editor.remove(KEY_URL); |
| 329 editor.remove(KEY_SCOPE); | 319 editor.remove(KEY_SCOPE); |
| 330 editor.remove(KEY_LAST_CHECK_WEB_MANIFEST_UPDATE_TIME); | 320 editor.remove(KEY_LAST_CHECK_WEB_MANIFEST_UPDATE_TIME); |
| 331 editor.remove(KEY_LAST_UPDATE_REQUEST_COMPLETE_TIME); | 321 editor.remove(KEY_LAST_UPDATE_REQUEST_COMPLETE_TIME); |
| 332 editor.remove(KEY_DID_LAST_UPDATE_REQUEST_SUCCEED); | 322 editor.remove(KEY_DID_LAST_UPDATE_REQUEST_SUCCEED); |
| 333 editor.remove(KEY_UPDATE_REQUESTED); | 323 editor.remove(KEY_UPDATE_REQUESTED); |
| 334 editor.remove(KEY_RELAX_UPDATES); | 324 editor.remove(KEY_RELAX_UPDATES); |
| 335 editor.remove(KEY_DISMISSED_DISCLOSURE); | 325 editor.remove(KEY_DISMISSED_DISCLOSURE); |
| 336 editor.apply(); | 326 editor.apply(); |
| 337 } | 327 } |
| (...skipping 19 matching lines...) Expand all Loading... |
| 357 | 347 |
| 358 /** Updates the source. */ | 348 /** Updates the source. */ |
| 359 public void updateSource(int source) { | 349 public void updateSource(int source) { |
| 360 mPreferences.edit().putInt(KEY_SOURCE, source).apply(); | 350 mPreferences.edit().putInt(KEY_SOURCE, source).apply(); |
| 361 } | 351 } |
| 362 | 352 |
| 363 /** | 353 /** |
| 364 * Returns the last used time of this object, or -1 if it is not stored. | 354 * Returns the last used time of this object, or -1 if it is not stored. |
| 365 */ | 355 */ |
| 366 public long getLastUsedTime() { | 356 public long getLastUsedTime() { |
| 367 return mPreferences.getLong(KEY_LAST_USED, LAST_USED_INVALID); | 357 return mPreferences.getLong(KEY_LAST_USED, TIMESTAMP_INVALID); |
| 368 } | 358 } |
| 369 | 359 |
| 370 /** | 360 /** |
| 371 * Update the information associated with the web app with the specified dat
a. Used for testing. | 361 * Update the information associated with the web app with the specified dat
a. Used for testing. |
| 372 * @param splashScreenImage The image encoded as a string which should be sh
own on the splash | 362 * @param splashScreenImage The image encoded as a string which should be sh
own on the splash |
| 373 * screen of the web app. | 363 * screen of the web app. |
| 374 */ | 364 */ |
| 375 @VisibleForTesting | 365 @VisibleForTesting |
| 376 void updateSplashScreenImageForTests(String splashScreenImage) { | 366 void updateSplashScreenImageForTests(String splashScreenImage) { |
| 377 mPreferences.edit().putString(KEY_SPLASH_ICON, splashScreenImage).apply(
); | 367 mPreferences.edit().putString(KEY_SPLASH_ICON, splashScreenImage).apply(
); |
| (...skipping 21 matching lines...) Expand all Loading... |
| 399 mPreferences.edit() | 389 mPreferences.edit() |
| 400 .putLong(KEY_LAST_CHECK_WEB_MANIFEST_UPDATE_TIME, sClock.current
TimeMillis()) | 390 .putLong(KEY_LAST_CHECK_WEB_MANIFEST_UPDATE_TIME, sClock.current
TimeMillis()) |
| 401 .apply(); | 391 .apply(); |
| 402 } | 392 } |
| 403 | 393 |
| 404 /** | 394 /** |
| 405 * Returns the completion time of the last check for whether the WebAPK's We
b Manifest was | 395 * Returns the completion time of the last check for whether the WebAPK's We
b Manifest was |
| 406 * updated. This time needs to be set when the WebAPK is registered. | 396 * updated. This time needs to be set when the WebAPK is registered. |
| 407 */ | 397 */ |
| 408 private long getLastCheckForWebManifestUpdateTime() { | 398 private long getLastCheckForWebManifestUpdateTime() { |
| 409 return mPreferences.getLong(KEY_LAST_CHECK_WEB_MANIFEST_UPDATE_TIME, LAS
T_USED_INVALID); | 399 return mPreferences.getLong(KEY_LAST_CHECK_WEB_MANIFEST_UPDATE_TIME, TIM
ESTAMP_INVALID); |
| 410 } | 400 } |
| 411 | 401 |
| 412 /** | 402 /** |
| 413 * Updates when the last WebAPK update request finished (successfully or uns
uccessfully). | 403 * Updates when the last WebAPK update request finished (successfully or uns
uccessfully). |
| 414 */ | 404 */ |
| 415 void updateTimeOfLastWebApkUpdateRequestCompletion() { | 405 void updateTimeOfLastWebApkUpdateRequestCompletion() { |
| 416 mPreferences.edit() | 406 mPreferences.edit() |
| 417 .putLong(KEY_LAST_UPDATE_REQUEST_COMPLETE_TIME, sClock.currentTi
meMillis()) | 407 .putLong(KEY_LAST_UPDATE_REQUEST_COMPLETE_TIME, sClock.currentTi
meMillis()) |
| 418 .apply(); | 408 .apply(); |
| 419 } | 409 } |
| 420 | 410 |
| 421 /** | 411 /** |
| 422 * Returns when the last WebAPK update request completed (successfully or un
successfully). | 412 * Returns when the last WebAPK update request completed (successfully or un
successfully). |
| 423 * This time needs to be set when the WebAPK is registered. | 413 * This time needs to be set when the WebAPK is registered. |
| 424 */ | 414 */ |
| 425 long getLastWebApkUpdateRequestCompletionTime() { | 415 long getLastWebApkUpdateRequestCompletionTime() { |
| 426 return mPreferences.getLong(KEY_LAST_UPDATE_REQUEST_COMPLETE_TIME, LAST_
USED_INVALID); | 416 return mPreferences.getLong(KEY_LAST_UPDATE_REQUEST_COMPLETE_TIME, TIMES
TAMP_INVALID); |
| 427 } | 417 } |
| 428 | 418 |
| 429 /** | 419 /** |
| 430 * Updates whether the last update request to WebAPK Server succeeded. | 420 * Updates whether the last update request to WebAPK Server succeeded. |
| 431 */ | 421 */ |
| 432 void updateDidLastWebApkUpdateRequestSucceed(boolean success) { | 422 void updateDidLastWebApkUpdateRequestSucceed(boolean success) { |
| 433 mPreferences.edit().putBoolean(KEY_DID_LAST_UPDATE_REQUEST_SUCCEED, succ
ess).apply(); | 423 mPreferences.edit().putBoolean(KEY_DID_LAST_UPDATE_REQUEST_SUCCEED, succ
ess).apply(); |
| 434 } | 424 } |
| 435 | 425 |
| 436 /** | 426 /** |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 478 int getLastRequestedShellApkVersion() { | 468 int getLastRequestedShellApkVersion() { |
| 479 return mPreferences.getInt(KEY_LAST_REQUESTED_SHELL_APK_VERSION, DEFAULT
_SHELL_APK_VERSION); | 469 return mPreferences.getInt(KEY_LAST_REQUESTED_SHELL_APK_VERSION, DEFAULT
_SHELL_APK_VERSION); |
| 480 } | 470 } |
| 481 | 471 |
| 482 /** | 472 /** |
| 483 * Returns whether the previous WebAPK update attempt succeeded. Returns tru
e if there has not | 473 * Returns whether the previous WebAPK update attempt succeeded. Returns tru
e if there has not |
| 484 * been any update attempts. | 474 * been any update attempts. |
| 485 */ | 475 */ |
| 486 boolean didPreviousUpdateSucceed() { | 476 boolean didPreviousUpdateSucceed() { |
| 487 long lastUpdateCompletionTime = getLastWebApkUpdateRequestCompletionTime
(); | 477 long lastUpdateCompletionTime = getLastWebApkUpdateRequestCompletionTime
(); |
| 488 if (lastUpdateCompletionTime == WebappDataStorage.LAST_USED_INVALID) { | 478 if (lastUpdateCompletionTime == TIMESTAMP_INVALID) { |
| 489 return true; | 479 return true; |
| 490 } | 480 } |
| 491 return getDidLastWebApkUpdateRequestSucceed(); | 481 return getDidLastWebApkUpdateRequestSucceed(); |
| 492 } | 482 } |
| 493 | 483 |
| 494 /** Sets whether we should check for updates less frequently. */ | 484 /** Sets whether we should check for updates less frequently. */ |
| 495 void setRelaxedUpdates(boolean relaxUpdates) { | 485 void setRelaxedUpdates(boolean relaxUpdates) { |
| 496 mPreferences.edit().putBoolean(KEY_RELAX_UPDATES, relaxUpdates).apply(); | 486 mPreferences.edit().putBoolean(KEY_RELAX_UPDATES, relaxUpdates).apply(); |
| 497 } | 487 } |
| 498 | 488 |
| (...skipping 13 matching lines...) Expand all Loading... |
| 512 long sinceLastUpdateRequestDurationMs = now - getLastWebApkUpdateRequest
CompletionTime(); | 502 long sinceLastUpdateRequestDurationMs = now - getLastWebApkUpdateRequest
CompletionTime(); |
| 513 return sinceLastUpdateRequestDurationMs >= RETRY_UPDATE_DURATION | 503 return sinceLastUpdateRequestDurationMs >= RETRY_UPDATE_DURATION |
| 514 && !didPreviousUpdateSucceed(); | 504 && !didPreviousUpdateSucceed(); |
| 515 } | 505 } |
| 516 | 506 |
| 517 protected WebappDataStorage(String webappId) { | 507 protected WebappDataStorage(String webappId) { |
| 518 mId = webappId; | 508 mId = webappId; |
| 519 mPreferences = ContextUtils.getApplicationContext().getSharedPreferences
( | 509 mPreferences = ContextUtils.getApplicationContext().getSharedPreferences
( |
| 520 SHARED_PREFS_FILE_PREFIX + webappId, Context.MODE_PRIVATE); | 510 SHARED_PREFS_FILE_PREFIX + webappId, Context.MODE_PRIVATE); |
| 521 } | 511 } |
| 522 | |
| 523 private boolean isEmpty() { | |
| 524 return mPreferences.getAll().isEmpty(); | |
| 525 } | |
| 526 } | 512 } |
| OLD | NEW |