File: installable_logging.cc

package info (click to toggle)
chromium 120.0.6099.224-1~deb11u1
  • links: PTS, VCS
  • area: main
  • in suites: bullseye
  • size: 6,112,112 kB
  • sloc: cpp: 32,907,025; ansic: 8,148,123; javascript: 3,679,536; python: 2,031,248; asm: 959,718; java: 804,675; xml: 617,256; sh: 111,417; objc: 100,835; perl: 88,443; cs: 53,032; makefile: 29,579; fortran: 24,137; php: 21,162; tcl: 21,147; sql: 20,809; ruby: 17,735; pascal: 12,864; yacc: 8,045; lisp: 3,388; lex: 1,323; ada: 727; awk: 329; jsp: 267; csh: 117; exp: 43; sed: 37
file content (339 lines) | stat: -rw-r--r-- 12,514 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
// Copyright 2016 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "components/webapps/browser/installable/installable_logging.h"

#include <vector>

#include "base/no_destructor.h"
#include "base/strings/stringprintf.h"
#include "components/webapps/browser/installable/installable_evaluator.h"
#include "content/public/browser/installability_error.h"
#include "content/public/browser/render_frame_host.h"
#include "content/public/browser/web_contents.h"
#include "third_party/blink/public/mojom/devtools/console_message.mojom.h"

namespace webapps {

namespace {

// Error message strings corresponding to the InstallableStatusCode enum.
static const char kNotFromSecureOriginMessage[] =
    "Page is not served from a secure origin";
static const char kNoManifestMessage[] = "Page has no manifest <link> URL";
static const char kManifestEmptyMessage[] =
    "Manifest could not be fetched, is empty, or could not be parsed";
static const char kStartUrlNotValidMessage[] =
    "Manifest start URL is not valid";
static const char kManifestMissingNameOrShortNameMessage[] =
    "Manifest does not contain a 'name' or 'short_name' field";
static const char kManifestDisplayNotSupportedMessage[] =
    "Manifest 'display' property must be one of 'standalone', 'fullscreen', or "
    "'minimal-ui'";
static const char kManifestMissingSuitableIconMessage[] =
    "Manifest does not contain a suitable icon - PNG, SVG or WebP format of at "
    "least %dpx is required, the sizes attribute must be set, and the purpose "
    "attribute, if set, must include \"any\" or \"maskable\".";
static const char kNoAcceptableIconMessage[] =
    "No supplied icon is at least %dpx square in PNG, SVG or WebP format";
static const char kCannotDownloadIconMessage[] =
    "Could not download a required icon from the manifest";
static const char kNoIconAvailableMessage[] =
    "Downloaded icon was empty or corrupted";
static const char kPlatformNotSupportedOnAndroidMessage[] =
    "The specified application platform is not supported on Android";
static const char kNoIdSpecifiedMessage[] = "No Play store ID provided";
static const char kIdsDoNotMatchMessage[] =
    "The Play Store app URL and Play Store ID do not match";
static const char kAlreadyInstalledMessage[] = "The app is already installed";
static const char kUrlNotSupportedForWebApkMessage[] =
    "A URL in the manifest contains a username, password, or port";
static const char kInIncognitoMessage[] =
    "Page is loaded in an incognito window";
static const char kNotOfflineCapable[] = "Page does not work offline";
static const char kNoUrlForServiceWorker[] =
    "Could not check service worker without a 'start_url' field in the "
    "manifest";
static const char kPreferRelatedApplications[] =
    "Manifest specifies prefer_related_applications: true";
static const char kPreferRelatedApplicationsSupportedOnlyBetaStable[] =
    "prefer_related_applications is only supported on Chrome Beta and Stable "
    "channels on Android.";
static const char kManifestLocationChanged[] =
    "Manifest location changed during fetch";
static const char kManifestDisplayOverrideNotSupportedMessage[] =
    "Manifest contains 'display_override' field, and the first supported "
    "display mode must be one of 'standalone', 'fullscreen', or 'minimal-ui'";
static const char kPipelineRestarted[] =
    "Web app uninstalled so that it stops any running pipeline";

static const char kNotFromSecureOriginId[] = "not-from-secure-origin";
static const char kNoManifestId[] = "no-manifest";
static const char kManifestEmptyId[] = "manifest-empty";
static const char kStartUrlNotValidId[] = "start-url-not-valid";
static const char kManifestMissingNameOrShortNameId[] =
    "manifest-missing-name-or-short-name";
static const char kManifestDisplayNotSupportedId[] =
    "manifest-display-not-supported";
static const char kManifestMissingSuitableIconId[] =
    "manifest-missing-suitable-icon";
static const char kMinimumIconSizeInPixelsId[] = "minimum-icon-size-in-pixels";
static const char kNoAcceptableIconId[] = "no-acceptable-icon";
static const char kCannotDownloadIconId[] = "cannot-download-icon";
static const char kNoIconAvailableId[] = "no-icon-available";
static const char kPlatformNotSupportedOnAndroidId[] =
    "platform-not-supported-on-android";
static const char kNoIdSpecifiedId[] = "no-id-specified";
static const char kIdsDoNotMatchId[] = "ids-do-not-match";
static const char kAlreadyInstalledId[] = "already-installed";
static const char kUrlNotSupportedForWebApkId[] =
    "url-not-supported-for-webapk";
static const char kInIncognitoId[] = "in-incognito";
static const char kNotOfflineCapableId[] = "not-offline-capable";
static const char kNoUrlForServiceWorkerId[] = "no-url-for-service-worker";
static const char kPreferRelatedApplicationsId[] =
    "prefer-related-applications";
static const char kPreferRelatedApplicationsSupportedOnlyBetaStableId[] =
    "prefer-related-applications-only-beta-stable";
static const char kManifestLocationChangedId[] = "manifest-location-changed";
static const char kManifestDisplayOverrideNotSupportedId[] =
    "manifest-display-override-not-supported";
static const char kPipelineRestartedId[] = "pipeline-restarted";

const std::string& GetMessagePrefix() {
  static base::NoDestructor<std::string> message_prefix(
      "Site cannot be installed: ");
  return *message_prefix;
}

}  // namespace

std::string GetErrorMessage(InstallableStatusCode code) {
  std::string message;
  switch (code) {
    case NO_ERROR_DETECTED:
    // These codes are solely used for UMA reporting.
    case RENDERER_EXITING:
    case RENDERER_CANCELLED:
    case USER_NAVIGATED:
    case NO_MATCHING_SERVICE_WORKER:
    case INSUFFICIENT_ENGAGEMENT:
    case PACKAGE_NAME_OR_START_URL_EMPTY:
    case PREVIOUSLY_BLOCKED:
    case PREVIOUSLY_IGNORED:
    case SHOWING_NATIVE_APP_BANNER:
    case SHOWING_WEB_APP_BANNER:
    case FAILED_TO_CREATE_BANNER:
    case WAITING_FOR_MANIFEST:
    case WAITING_FOR_INSTALLABLE_CHECK:
    case NO_GESTURE:
    case WAITING_FOR_NATIVE_DATA:
    case SHOWING_APP_INSTALLATION_DIALOG:
    case DATA_TIMED_OUT:
    case WEBAPK_INSTALL_FAILED:
    case MAX_ERROR_CODE:
      break;
    case NOT_FROM_SECURE_ORIGIN:
      message = kNotFromSecureOriginMessage;
      break;
    case NO_MANIFEST:
      message = kNoManifestMessage;
      break;
    case MANIFEST_EMPTY:
      message = kManifestEmptyMessage;
      break;
    case START_URL_NOT_VALID:
      message = kStartUrlNotValidMessage;
      break;
    case MANIFEST_MISSING_NAME_OR_SHORT_NAME:
      message = kManifestMissingNameOrShortNameMessage;
      break;
    case MANIFEST_DISPLAY_NOT_SUPPORTED:
      message = kManifestDisplayNotSupportedMessage;
      break;
    case MANIFEST_MISSING_SUITABLE_ICON:
      message =
          base::StringPrintf(kManifestMissingSuitableIconMessage,
                             InstallableEvaluator::GetMinimumIconSizeInPx());
      break;
    case NO_ACCEPTABLE_ICON:
      message =
          base::StringPrintf(kNoAcceptableIconMessage,
                             InstallableEvaluator::GetMinimumIconSizeInPx());
      break;
    case CANNOT_DOWNLOAD_ICON:
      message = kCannotDownloadIconMessage;
      break;
    case NO_ICON_AVAILABLE:
      message = kNoIconAvailableMessage;
      break;
    case PLATFORM_NOT_SUPPORTED_ON_ANDROID:
      message = kPlatformNotSupportedOnAndroidMessage;
      break;
    case NO_ID_SPECIFIED:
      message = kNoIdSpecifiedMessage;
      break;
    case IDS_DO_NOT_MATCH:
      message = kIdsDoNotMatchMessage;
      break;
    case ALREADY_INSTALLED:
      message = kAlreadyInstalledMessage;
      break;
    case URL_NOT_SUPPORTED_FOR_WEBAPK:
      message = kUrlNotSupportedForWebApkMessage;
      break;
    case IN_INCOGNITO:
      message = kInIncognitoMessage;
      break;
    case NOT_OFFLINE_CAPABLE:
      message = kNotOfflineCapable;
      break;
    case NO_URL_FOR_SERVICE_WORKER:
      message = kNoUrlForServiceWorker;
      break;
    case PREFER_RELATED_APPLICATIONS:
      message = kPreferRelatedApplications;
      break;
    case PREFER_RELATED_APPLICATIONS_SUPPORTED_ONLY_BETA_STABLE:
      message = kPreferRelatedApplicationsSupportedOnlyBetaStable;
      break;
    case MANIFEST_URL_CHANGED:
      message = kManifestLocationChanged;
      break;
    case MANIFEST_DISPLAY_OVERRIDE_NOT_SUPPORTED:
      message = kManifestDisplayOverrideNotSupportedMessage;
      break;
    case PIPELINE_RESTARTED:
      message = kPipelineRestarted;
      break;
  }

  return message;
}

content::InstallabilityError GetInstallabilityError(
    InstallableStatusCode code) {
  content::InstallabilityError error;
  std::string error_id;
  std::vector<content::InstallabilityErrorArgument> error_arguments;
  switch (code) {
    case NO_ERROR_DETECTED:
    // These codes are solely used for UMA reporting.
    case RENDERER_EXITING:
    case RENDERER_CANCELLED:
    case USER_NAVIGATED:
    case NO_MATCHING_SERVICE_WORKER:
    case INSUFFICIENT_ENGAGEMENT:
    case PACKAGE_NAME_OR_START_URL_EMPTY:
    case PREVIOUSLY_BLOCKED:
    case PREVIOUSLY_IGNORED:
    case SHOWING_NATIVE_APP_BANNER:
    case SHOWING_WEB_APP_BANNER:
    case FAILED_TO_CREATE_BANNER:
    case WAITING_FOR_MANIFEST:
    case WAITING_FOR_INSTALLABLE_CHECK:
    case NO_GESTURE:
    case WAITING_FOR_NATIVE_DATA:
    case SHOWING_APP_INSTALLATION_DIALOG:
    case DATA_TIMED_OUT:
    case WEBAPK_INSTALL_FAILED:
    case MAX_ERROR_CODE:
      break;
    case NOT_FROM_SECURE_ORIGIN:
      error_id = kNotFromSecureOriginId;
      break;
    case NO_MANIFEST:
      error_id = kNoManifestId;
      break;
    case MANIFEST_EMPTY:
      error_id = kManifestEmptyId;
      break;
    case START_URL_NOT_VALID:
      error_id = kStartUrlNotValidId;
      break;
    case MANIFEST_MISSING_NAME_OR_SHORT_NAME:
      error_id = kManifestMissingNameOrShortNameId;
      break;
    case MANIFEST_DISPLAY_NOT_SUPPORTED:
      error_id = kManifestDisplayNotSupportedId;
      break;
    case MANIFEST_MISSING_SUITABLE_ICON:
      error_id = kManifestMissingSuitableIconId;
      error_arguments.emplace_back(
          kMinimumIconSizeInPixelsId,
          base::NumberToString(InstallableEvaluator::GetMinimumIconSizeInPx()));
      break;
    case NO_ACCEPTABLE_ICON:
      error_id = kNoAcceptableIconId;
      error_arguments.emplace_back(
          kMinimumIconSizeInPixelsId,
          base::NumberToString(InstallableEvaluator::GetMinimumIconSizeInPx()));
      break;
    case CANNOT_DOWNLOAD_ICON:
      error_id = kCannotDownloadIconId;
      break;
    case NO_ICON_AVAILABLE:
      error_id = kNoIconAvailableId;
      break;
    case PLATFORM_NOT_SUPPORTED_ON_ANDROID:
      error_id = kPlatformNotSupportedOnAndroidId;
      break;
    case NO_ID_SPECIFIED:
      error_id = kNoIdSpecifiedId;
      break;
    case IDS_DO_NOT_MATCH:
      error_id = kIdsDoNotMatchId;
      break;
    case ALREADY_INSTALLED:
      error_id = kAlreadyInstalledId;
      break;
    case URL_NOT_SUPPORTED_FOR_WEBAPK:
      error_id = kUrlNotSupportedForWebApkId;
      break;
    case IN_INCOGNITO:
      error_id = kInIncognitoId;
      break;
    case NOT_OFFLINE_CAPABLE:
      error_id = kNotOfflineCapableId;
      break;
    case NO_URL_FOR_SERVICE_WORKER:
      error_id = kNoUrlForServiceWorkerId;
      break;
    case PREFER_RELATED_APPLICATIONS:
      error_id = kPreferRelatedApplicationsId;
      break;
    case PREFER_RELATED_APPLICATIONS_SUPPORTED_ONLY_BETA_STABLE:
      error_id = kPreferRelatedApplicationsSupportedOnlyBetaStableId;
      break;
    case MANIFEST_URL_CHANGED:
      error_id = kManifestLocationChangedId;
      break;
    case MANIFEST_DISPLAY_OVERRIDE_NOT_SUPPORTED:
      error_id = kManifestDisplayOverrideNotSupportedId;
      break;
    case PIPELINE_RESTARTED:
      error_id = kPipelineRestartedId;
      break;
  }
  error.error_id = error_id;
  error.installability_error_arguments = error_arguments;
  return error;
}

void LogToConsole(content::WebContents* web_contents,
                  InstallableStatusCode code,
                  blink::mojom::ConsoleMessageLevel level) {
  if (!web_contents)
    return;

  std::string message = GetErrorMessage(code);

  if (message.empty())
    return;

  web_contents->GetPrimaryMainFrame()->AddMessageToConsole(
      level, GetMessagePrefix() + message);
}

}  // namespace webapps