1import { registerVersion, _registerComponent, _getProvider, getApp } from 'https://www.gstatic.com/firebasejs/9.5.0/firebase-app.js'; 2 3/** 4 * @license 5 * Copyright 2017 Google LLC 6 * 7 * Licensed under the Apache License, Version 2.0 (the "License"); 8 * you may not use this file except in compliance with the License. 9 * You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, software 14 * distributed under the License is distributed on an "AS IS" BASIS, 15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 16 * See the License for the specific language governing permissions and 17 * limitations under the License. 18 */ 19/** 20 * This method checks if indexedDB is supported by current browser/service worker context 21 * @return true if indexedDB is supported by current browser/service worker context 22 */ 23function isIndexedDBAvailable() { 24 return typeof indexedDB === 'object'; 25} 26/** 27 * This method validates browser/sw context for indexedDB by opening a dummy indexedDB database and reject 28 * if errors occur during the database open operation. 29 * 30 * @throws exception if current browser/sw context can't run idb.open (ex: Safari iframe, Firefox 31 * private browsing) 32 */ 33function validateIndexedDBOpenable() { 34 return new Promise((resolve, reject) => { 35 try { 36 let preExist = true; 37 const DB_CHECK_NAME = 'validate-browser-context-for-indexeddb-analytics-module'; 38 const request = self.indexedDB.open(DB_CHECK_NAME); 39 request.onsuccess = () => { 40 request.result.close(); 41 // delete database only when it doesn't pre-exist 42 if (!preExist) { 43 self.indexedDB.deleteDatabase(DB_CHECK_NAME); 44 } 45 resolve(true); 46 }; 47 request.onupgradeneeded = () => { 48 preExist = false; 49 }; 50 request.onerror = () => { 51 var _a; 52 reject(((_a = request.error) === null || _a === void 0 ? void 0 : _a.message) || ''); 53 }; 54 } 55 catch (error) { 56 reject(error); 57 } 58 }); 59} 60/** 61 * 62 * This method checks whether cookie is enabled within current browser 63 * @return true if cookie is enabled within current browser 64 */ 65function areCookiesEnabled() { 66 if (typeof navigator === 'undefined' || !navigator.cookieEnabled) { 67 return false; 68 } 69 return true; 70} 71 72/** 73 * @license 74 * Copyright 2017 Google LLC 75 * 76 * Licensed under the Apache License, Version 2.0 (the "License"); 77 * you may not use this file except in compliance with the License. 78 * You may obtain a copy of the License at 79 * 80 * http://www.apache.org/licenses/LICENSE-2.0 81 * 82 * Unless required by applicable law or agreed to in writing, software 83 * distributed under the License is distributed on an "AS IS" BASIS, 84 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 85 * See the License for the specific language governing permissions and 86 * limitations under the License. 87 */ 88/** 89 * @fileoverview Standardized Firebase Error. 90 * 91 * Usage: 92 * 93 * // Typescript string literals for type-safe codes 94 * type Err = 95 * 'unknown' | 96 * 'object-not-found' 97 * ; 98 * 99 * // Closure enum for type-safe error codes 100 * // at-enum {string} 101 * var Err = { 102 * UNKNOWN: 'unknown', 103 * OBJECT_NOT_FOUND: 'object-not-found', 104 * } 105 * 106 * let errors: Map<Err, string> = { 107 * 'generic-error': "Unknown error", 108 * 'file-not-found': "Could not find file: {$file}", 109 * }; 110 * 111 * // Type-safe function - must pass a valid error code as param. 112 * let error = new ErrorFactory<Err>('service', 'Service', errors); 113 * 114 * ... 115 * throw error.create(Err.GENERIC); 116 * ... 117 * throw error.create(Err.FILE_NOT_FOUND, {'file': fileName}); 118 * ... 119 * // Service: Could not file file: foo.txt (service/file-not-found). 120 * 121 * catch (e) { 122 * assert(e.message === "Could not find file: foo.txt."); 123 * if (e.code === 'service/file-not-found') { 124 * console.log("Could not read file: " + e['file']); 125 * } 126 * } 127 */ 128const ERROR_NAME = 'FirebaseError'; 129// Based on code from: 130// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error#Custom_Error_Types
131class FirebaseError extends Error { 132 constructor(code, message, customData) { 133 super(message); 134 this.code = code; 135 this.customData = customData; 136 this.name = ERROR_NAME; 137 // Fix For ES5 138 // https://github.com/Microsoft/TypeScript-wiki/blob/master/Breaking-Changes.md#extending-built-ins-like-error-array-and-map-may-no-longer-work 139 Object.setPrototypeOf(this, FirebaseError.prototype); 140 // Maintains proper stack trace for where our error was thrown. 141 // Only available on V8. 142 if (Error.captureStackTrace) { 143 Error.captureStackTrace(this, ErrorFactory.prototype.create); 144 } 145 } 146} 147class ErrorFactory { 148 constructor(service, serviceName, errors) { 149 this.service = service; 150 this.serviceName = serviceName; 151 this.errors = errors; 152 } 153 create(code, ...data) { 154 const customData = data[0] || {}; 155 const fullCode = `${this.service}/${code}`; 156 const template = this.errors[code]; 157 const message = template ? replaceTemplate(template, customData) : 'Error'; 158 // Service Name: Error message (service/code). 159 const fullMessage = `${this.serviceName}: ${message} (${fullCode}).`; 160 const error = new FirebaseError(fullCode, fullMessage, customData); 161 return error; 162 } 163} 164function replaceTemplate(template, data) { 165 return template.replace(PATTERN, (_, key) => { 166 const value = data[key]; 167 return value != null ? String(value) : `<${key}?>`; 168 }); 169} 170const PATTERN = /\{\$([^}]+)}/g; 171 172/** 173 * @license 174 * Copyright 2021 Google LLC 175 * 176 * Licensed under the Apache License, Version 2.0 (the "License"); 177 * you may not use this file except in compliance with the License. 178 * You may obtain a copy of the License at 179 * 180 * http://www.apache.org/licenses/LICENSE-2.0 181 * 182 * Unless required by applicable law or agreed to in writing, software 183 * distributed under the License is distributed on an "AS IS" BASIS, 184 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 185 * See the License for the specific language governing permissions and 186 * limitations under the License. 187 */ 188function getModularInstance(service) { 189 if (service && service._delegate) { 190 return service._delegate; 191 } 192 else { 193 return service; 194 } 195} 196 197/** 198 * Component for service name T, e.g. `auth`, `auth-internal` 199 */ 200class Component { 201 /** 202 * 203 * @param name The public service name, e.g. app, auth, firestore, database 204 * @param instanceFactory Service factory responsible for creating the public interface 205 * @param type whether the service provided by the component is public or private 206 */ 207 constructor(name, instanceFactory, type) { 208 this.name = name; 209 this.instanceFactory = instanceFactory; 210 this.type = type; 211 this.multipleInstances = false; 212 /** 213 * Properties to be added to the service namespace 214 */ 215 this.serviceProps = {}; 216 this.instantiationMode = "LAZY" /* LAZY */; 217 this.onInstanceCreated = null; 218 } 219 setInstantiationMode(mode) { 220 this.instantiationMode = mode; 221 return this; 222 } 223 setMultipleInstances(multipleInstances) { 224 this.multipleInstances = multipleInstances; 225 return this; 226 } 227 setServiceProps(props) { 228 this.serviceProps = props; 229 return this; 230 } 231 setInstanceCreatedCallback(callback) { 232 this.onInstanceCreated = callback; 233 return this; 234 } 235} 236 237function toArray(arr) { 238 return Array.prototype.slice.call(arr); 239} 240 241function promisifyRequest(request) { 242 return new Promise(function(resolve, reject) { 243 request.onsuccess = function() { 244 resolve(request.result); 245 }; 246 247 request.onerror = function() { 248 reject(request.error); 249 }; 250 }); 251} 252 253function promisifyRequestCall(obj, method, args) { 254 var request; 255 var p = new Promise(function(resolve, reject) { 256 request = obj[method].apply(obj, args); 257 promisifyRequest(request).then(resolve, reject); 258 }); 259 260 p.request = request; 261 return p; 262} 263 264function promisifyCursorRequestCall(obj, method, args) { 265 var p = promisifyRequestCall(obj, method, args); 266 return p.then(function(value) { 267 if (!value) return; 268 return new Cursor(value, p.request); 269 }); 270} 271 272function proxyProperties(ProxyClass, targetProp, properties) {
vendor: 4,600 bytes, lines 273-478
273 properties.forEach(function(prop) { 274 Object.defineProperty(ProxyClass.prototype, prop, { 275 get: function() { 276 return this[targetProp][prop]; 277 }, 278 set: function(val) { 279 this[targetProp][prop] = val; 280 } 281 }); 282 }); 283} 284 285function proxyRequestMethods(ProxyClass, targetProp, Constructor, properties) { 286 properties.forEach(function(prop) { 287 if (!(prop in Constructor.prototype)) return; 288 ProxyClass.prototype[prop] = function() { 289 return promisifyRequestCall(this[targetProp], prop, arguments); 290 }; 291 }); 292} 293 294function proxyMethods(ProxyClass, targetProp, Constructor, properties) { 295 properties.forEach(function(prop) { 296 if (!(prop in Constructor.prototype)) return; 297 ProxyClass.prototype[prop] = function() { 298 return this[targetProp][prop].apply(this[targetProp], arguments); 299 }; 300 }); 301} 302 303function proxyCursorRequestMethods(ProxyClass, targetProp, Constructor, properties) { 304 properties.forEach(function(prop) { 305 if (!(prop in Constructor.prototype)) return; 306 ProxyClass.prototype[prop] = function() { 307 return promisifyCursorRequestCall(this[targetProp], prop, arguments); 308 }; 309 }); 310} 311 312function Index(index) { 313 this._index = index; 314} 315 316proxyProperties(Index, '_index', [ 317 'name', 318 'keyPath', 319 'multiEntry', 320 'unique' 321]); 322 323proxyRequestMethods(Index, '_index', IDBIndex, [ 324 'get', 325 'getKey', 326 'getAll', 327 'getAllKeys', 328 'count' 329]); 330 331proxyCursorRequestMethods(Index, '_index', IDBIndex, [ 332 'openCursor', 333 'openKeyCursor' 334]); 335 336function Cursor(cursor, request) { 337 this._cursor = cursor; 338 this._request = request; 339} 340 341proxyProperties(Cursor, '_cursor', [ 342 'direction', 343 'key', 344 'primaryKey', 345 'value' 346]); 347 348proxyRequestMethods(Cursor, '_cursor', IDBCursor, [ 349 'update', 350 'delete' 351]); 352 353// proxy 'next' methods 354['advance', 'continue', 'continuePrimaryKey'].forEach(function(methodName) { 355 if (!(methodName in IDBCursor.prototype)) return; 356 Cursor.prototype[methodName] = function() { 357 var cursor = this; 358 var args = arguments; 359 return Promise.resolve().then(function() { 360 cursor._cursor[methodName].apply(cursor._cursor, args); 361 return promisifyRequest(cursor._request).then(function(value) { 362 if (!value) return; 363 return new Cursor(value, cursor._request); 364 }); 365 }); 366 }; 367}); 368 369function ObjectStore(store) { 370 this._store = store; 371} 372 373ObjectStore.prototype.createIndex = function() { 374 return new Index(this._store.createIndex.apply(this._store, arguments)); 375}; 376 377ObjectStore.prototype.index = function() { 378 return new Index(this._store.index.apply(this._store, arguments)); 379}; 380 381proxyProperties(ObjectStore, '_store', [ 382 'name', 383 'keyPath', 384 'indexNames', 385 'autoIncrement' 386]); 387 388proxyRequestMethods(ObjectStore, '_store', IDBObjectStore, [ 389 'put', 390 'add', 391 'delete', 392 'clear', 393 'get', 394 'getAll', 395 'getKey', 396 'getAllKeys', 397 'count' 398]); 399 400proxyCursorRequestMethods(ObjectStore, '_store', IDBObjectStore, [ 401 'openCursor', 402 'openKeyCursor' 403]); 404 405proxyMethods(ObjectStore, '_store', IDBObjectStore, [ 406 'deleteIndex' 407]); 408 409function Transaction(idbTransaction) { 410 this._tx = idbTransaction; 411 this.complete = new Promise(function(resolve, reject) { 412 idbTransaction.oncomplete = function() { 413 resolve(); 414 }; 415 idbTransaction.onerror = function() { 416 reject(idbTransaction.error); 417 }; 418 idbTransaction.onabort = function() { 419 reject(idbTransaction.error); 420 }; 421 }); 422} 423 424Transaction.prototype.objectStore = function() { 425 return new ObjectStore(this._tx.objectStore.apply(this._tx, arguments)); 426}; 427 428proxyProperties(Transaction, '_tx', [ 429 'objectStoreNames', 430 'mode' 431]); 432 433proxyMethods(Transaction, '_tx', IDBTransaction, [ 434 'abort' 435]); 436 437function UpgradeDB(db, oldVersion, transaction) { 438 this._db = db; 439 this.oldVersion = oldVersion; 440 this.transaction = new Transaction(transaction); 441} 442 443UpgradeDB.prototype.createObjectStore = function() { 444 return new ObjectStore(this._db.createObjectStore.apply(this._db, arguments)); 445}; 446 447proxyProperties(UpgradeDB, '_db', [ 448 'name', 449 'version', 450 'objectStoreNames' 451]); 452 453proxyMethods(UpgradeDB, '_db', IDBDatabase, [ 454 'deleteObjectStore', 455 'close' 456]); 457 458function DB(db) { 459 this._db = db; 460} 461 462DB.prototype.transaction = function() { 463 return new Transaction(this._db.transaction.apply(this._db, arguments)); 464}; 465 466proxyProperties(DB, '_db', [ 467 'name', 468 'version', 469 'objectStoreNames' 470]); 471 472proxyMethods(DB, '_db', IDBDatabase, [ 473 'close' 474]); 475 476// Add cursor iterators 477// TODO: remove this once browsers do the right thing with promises 478['openCursor', 'openKeyCursor'].forEach(function(funcName) {
479 [ObjectStore, Index].forEach(function(Constructor) { 480 // Don't create iterateKeyCursor if openKeyCursor doesn't exist. 481 if (!(funcName in Constructor.prototype)) return; 482 483 Constructor.prototype[funcName.replace('open', 'iterate')] = function() { 484 var args = toArray(arguments); 485 var callback = args[args.length - 1]; 486 var nativeObject = this._store || this._index; 487 var request = nativeObject[funcName].apply(nativeObject, args.slice(0, -1)); 488 request.onsuccess = function() { 489 callback(request.result); 490 }; 491 }; 492 }); 493}); 494 495// polyfill getAll 496[Index, ObjectStore].forEach(function(Constructor) { 497 if (Constructor.prototype.getAll) return; 498 Constructor.prototype.getAll = function(query, count) { 499 var instance = this; 500 var items = []; 501 502 return new Promise(function(resolve) { 503 instance.iterateCursor(query, function(cursor) { 504 if (!cursor) { 505 resolve(items); 506 return; 507 } 508 items.push(cursor.value); 509 510 if (count !== undefined && items.length == count) { 511 resolve(items); 512 return; 513 } 514 cursor.continue(); 515 }); 516 }); 517 }; 518}); 519 520function openDb(name, version, upgradeCallback) { 521 var p = promisifyRequestCall(indexedDB, 'open', [name, version]); 522 var request = p.request; 523 524 if (request) { 525 request.onupgradeneeded = function(event) { 526 if (upgradeCallback) { 527 upgradeCallback(new UpgradeDB(request.result, event.oldVersion, request.transaction)); 528 } 529 }; 530 } 531 532 return p.then(function(db) { 533 return new DB(db); 534 }); 535} 536 537function deleteDb(name) { 538 return promisifyRequestCall(indexedDB, 'deleteDatabase', [name]); 539} 540 541const name$1 = "@firebase/installations"; 542const version$1 = "0.5.4"; 543 544/** 545 * @license 546 * Copyright 2019 Google LLC 547 * 548 * Licensed under the Apache License, Version 2.0 (the "License"); 549 * you may not use this file except in compliance with the License. 550 * You may obtain a copy of the License at 551 * 552 * http://www.apache.org/licenses/LICENSE-2.0 553 * 554 * Unless required by applicable law or agreed to in writing, software 555 * distributed under the License is distributed on an "AS IS" BASIS, 556 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 557 * See the License for the specific language governing permissions and 558 * limitations under the License. 559 */ 560const PENDING_TIMEOUT_MS = 10000; 561const PACKAGE_VERSION = `w:${version$1}`; 562const INTERNAL_AUTH_VERSION = 'FIS_v2'; 563const INSTALLATIONS_API_URL = 'https://firebaseinstallations.googleapis.com/v1'; 564const TOKEN_EXPIRATION_BUFFER = 60 * 60 * 1000; // One hour 565const SERVICE = 'installations'; 566const SERVICE_NAME = 'Installations'; 567 568/** 569 * @license 570 * Copyright 2019 Google LLC 571 * 572 * Licensed under the Apache License, Version 2.0 (the "License"); 573 * you may not use this file except in compliance with the License. 574 * You may obtain a copy of the License at 575 * 576 * http://www.apache.org/licenses/LICENSE-2.0 577 * 578 * Unless required by applicable law or agreed to in writing, software 579 * distributed under the License is distributed on an "AS IS" BASIS, 580 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 581 * See the License for the specific language governing permissions and 582 * limitations under the License. 583 */ 584const ERROR_DESCRIPTION_MAP = { 585 ["missing-app-config-values" /* MISSING_APP_CONFIG_VALUES */]: 'Missing App configuration value: "{$valueName}"', 586 ["not-registered" /* NOT_REGISTERED */]: 'Firebase Installation is not registered.', 587 ["installation-not-found" /* INSTALLATION_NOT_FOUND */]: 'Firebase Installation not found.', 588 ["request-failed" /* REQUEST_FAILED */]: '{$requestName} request failed with error "{$serverCode} {$serverStatus}: {$serverMessage}"', 589 ["app-offline" /* APP_OFFLINE */]: 'Could not process request. Application offline.', 590 ["delete-pending-registration" /* DELETE_PENDING_REGISTRATION */]: "Can't delete installation while there is a pending registration request." 591}; 592const ERROR_FACTORY$1 = new ErrorFactory(SERVICE, SERVICE_NAME, ERROR_DESCRIPTION_MAP); 593/** Returns true if error is a FirebaseError that is based on an error from the server. */ 594function isServerError(error) { 595 return (error instanceof FirebaseError && 596 error.code.includes("request-failed" /* REQUEST_FAILED */)
vendor: 8,424 bytes, lines 596-826
596); 597} 598 599/** 600 * @license 601 * Copyright 2019 Google LLC 602 * 603 * Licensed under the Apache License, Version 2.0 (the "License"); 604 * you may not use this file except in compliance with the License. 605 * You may obtain a copy of the License at 606 * 607 * http://www.apache.org/licenses/LICENSE-2.0 608 * 609 * Unless required by applicable law or agreed to in writing, software 610 * distributed under the License is distributed on an "AS IS" BASIS, 611 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 612 * See the License for the specific language governing permissions and 613 * limitations under the License. 614 */ 615function getInstallationsEndpoint({ projectId }) { 616 return `${INSTALLATIONS_API_URL}/projects/${projectId}/installations`; 617} 618function extractAuthTokenInfoFromResponse(response) { 619 return { 620 token: response.token, 621 requestStatus: 2 /* COMPLETED */, 622 expiresIn: getExpiresInFromResponseExpiresIn(response.expiresIn), 623 creationTime: Date.now() 624 }; 625} 626async function getErrorFromResponse(requestName, response) { 627 const responseJson = await response.json(); 628 const errorData = responseJson.error; 629 return ERROR_FACTORY$1.create("request-failed" /* REQUEST_FAILED */, { 630 requestName, 631 serverCode: errorData.code, 632 serverMessage: errorData.message, 633 serverStatus: errorData.status 634 }); 635} 636function getHeaders$1({ apiKey }) { 637 return new Headers({ 638 'Content-Type': 'application/json', 639 Accept: 'application/json', 640 'x-goog-api-key': apiKey 641 }); 642} 643function getHeadersWithAuth(appConfig, { refreshToken }) { 644 const headers = getHeaders$1(appConfig); 645 headers.append('Authorization', getAuthorizationHeader(refreshToken)); 646 return headers; 647} 648/** 649 * Calls the passed in fetch wrapper and returns the response. 650 * If the returned response has a status of 5xx, re-runs the function once and 651 * returns the response. 652 */ 653async function retryIfServerError(fn) { 654 const result = await fn(); 655 if (result.status >= 500 && result.status < 600) { 656 // Internal Server Error. Retry request. 657 return fn(); 658 } 659 return result; 660} 661function getExpiresInFromResponseExpiresIn(responseExpiresIn) { 662 // This works because the server will never respond with fractions of a second. 663 return Number(responseExpiresIn.replace('s', '000')); 664} 665function getAuthorizationHeader(refreshToken) { 666 return `${INTERNAL_AUTH_VERSION} ${refreshToken}`; 667} 668 669/** 670 * @license 671 * Copyright 2019 Google LLC 672 * 673 * Licensed under the Apache License, Version 2.0 (the "License"); 674 * you may not use this file except in compliance with the License. 675 * You may obtain a copy of the License at 676 * 677 * http://www.apache.org/licenses/LICENSE-2.0 678 * 679 * Unless required by applicable law or agreed to in writing, software 680 * distributed under the License is distributed on an "AS IS" BASIS, 681 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 682 * See the License for the specific language governing permissions and 683 * limitations under the License. 684 */ 685async function createInstallationRequest(appConfig, { fid }) { 686 const endpoint = getInstallationsEndpoint(appConfig); 687 const headers = getHeaders$1(appConfig); 688 const body = { 689 fid, 690 authVersion: INTERNAL_AUTH_VERSION, 691 appId: appConfig.appId, 692 sdkVersion: PACKAGE_VERSION 693 }; 694 const request = { 695 method: 'POST', 696 headers, 697 body: JSON.stringify(body) 698 }; 699 const response = await retryIfServerError(() => fetch(endpoint, request)); 700 if (response.ok) { 701 const responseValue = await response.json(); 702 const registeredInstallationEntry = { 703 fid: responseValue.fid || fid, 704 registrationStatus: 2 /* COMPLETED */, 705 refreshToken: responseValue.refreshToken, 706 authToken: extractAuthTokenInfoFromResponse(responseValue.authToken) 707 }; 708 return registeredInstallationEntry; 709 } 710 else { 711 throw await getErrorFromResponse('Create Installation', response); 712 } 713} 714 715/** 716 * @license 717 * Copyright 2019 Google LLC 718 * 719 * Licensed under the Apache License, Version 2.0 (the "License"); 720 * you may not use this file except in compliance with the License. 721 * You may obtain a copy of the License at 722 * 723 * http://www.apache.org/licenses/LICENSE-2.0 724 * 725 * Unless required by applicable law or agreed to in writing, software 726 * distributed under the License is distributed on an "AS IS" BASIS, 727 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 728 * See the License for the specific language governing permissions and 729 * limitations under the License. 730 */ 731/** Returns a promise that resolves after given time passes. */ 732function sleep(ms) { 733 return new Promise(resolve => { 734 setTimeout(resolve, ms); 735 }); 736} 737 738/** 739 * @license 740 * Copyright 2019 Google LLC 741 * 742 * Licensed under the Apache License, Version 2.0 (the "License"); 743 * you may not use this file except in compliance with the License. 744 * You may obtain a copy of the License at 745 * 746 * http://www.apache.org/licenses/LICENSE-2.0 747 * 748 * Unless required by applicable law or agreed to in writing, software 749 * distributed under the License is distributed on an "AS IS" BASIS, 750 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 751 * See the License for the specific language governing permissions and 752 * limitations under the License. 753 */ 754function bufferToBase64UrlSafe(array) { 755 const b64 = btoa(String.fromCharCode(...array)); 756 return b64.replace(/\+/g, '-').replace(/\//g, '_'); 757} 758 759/** 760 * @license 761 * Copyright 2019 Google LLC 762 * 763 * Licensed under the Apache License, Version 2.0 (the "License"); 764 * you may not use this file except in compliance with the License. 765 * You may obtain a copy of the License at 766 * 767 * http://www.apache.org/licenses/LICENSE-2.0 768 * 769 * Unless required by applicable law or agreed to in writing, software 770 * distributed under the License is distributed on an "AS IS" BASIS, 771 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 772 * See the License for the specific language governing permissions and 773 * limitations under the License. 774 */ 775const VALID_FID_PATTERN = /^[cdef][\w-]{21}$/; 776const INVALID_FID = ''; 777/** 778 * Generates a new FID using random values from Web Crypto API. 779 * Returns an empty string if FID generation fails for any reason. 780 */ 781function generateFid() { 782 try { 783 // A valid FID has exactly 22 base64 characters, which is 132 bits, or 16.5 784 // bytes. our implementation generates a 17 byte array instead. 785 const fidByteArray = new Uint8Array(17); 786 const crypto = self.crypto || self.msCrypto; 787 crypto.getRandomValues(fidByteArray); 788 // Replace the first 4 random bits with the constant FID header of 0b0111. 789 fidByteArray[0] = 0b01110000 + (fidByteArray[0] % 0b00010000); 790 const fid = encode(fidByteArray); 791 return VALID_FID_PATTERN.test(fid) ? fid : INVALID_FID; 792 } 793 catch (_a) { 794 // FID generation errored 795 return INVALID_FID; 796 } 797} 798/** Converts a FID Uint8Array to a base64 string representation. */ 799function encode(fidByteArray) { 800 const b64String = bufferToBase64UrlSafe(fidByteArray); 801 // Remove the 23rd character that was added because of the extra 4 bits at the 802 // end of our 17 byte array, and the '=' padding. 803 return b64String.substr(0, 22); 804} 805 806/** 807 * @license 808 * Copyright 2019 Google LLC 809 * 810 * Licensed under the Apache License, Version 2.0 (the "License"); 811 * you may not use this file except in compliance with the License. 812 * You may obtain a copy of the License at 813 * 814 * http://www.apache.org/licenses/LICENSE-2.0 815 * 816 * Unless required by applicable law or agreed to in writing, software 817 * distributed under the License is distributed on an "AS IS" BASIS, 818 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 819 * See the License for the specific language governing permissions and 820 * limitations under the License. 821 */ 822/** Returns a string key that can be used to identify the app. */ 823function getKey$1(appConfig) { 824 return `${appConfig.appName}!${appConfig.appId}`; 825} 826
827/** 828 * @license 829 * Copyright 2019 Google LLC 830 * 831 * Licensed under the Apache License, Version 2.0 (the "License"); 832 * you may not use this file except in compliance with the License. 833 * You may obtain a copy of the License at 834 * 835 * http://www.apache.org/licenses/LICENSE-2.0 836 * 837 * Unless required by applicable law or agreed to in writing, software 838 * distributed under the License is distributed on an "AS IS" BASIS, 839 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 840 * See the License for the specific language governing permissions and 841 * limitations under the License. 842 */ 843const fidChangeCallbacks = new Map(); 844/** 845 * Calls the onIdChange callbacks with the new FID value, and broadcasts the 846 * change to other tabs. 847 */ 848function fidChanged(appConfig, fid) { 849 const key = getKey$1(appConfig); 850 callFidChangeCallbacks(key, fid); 851 broadcastFidChange(key, fid); 852} 853function callFidChangeCallbacks(key, fid) { 854 const callbacks = fidChangeCallbacks.get(key); 855 if (!callbacks) { 856 return; 857 } 858 for (const callback of callbacks) { 859 callback(fid); 860 } 861} 862function broadcastFidChange(key, fid) { 863 const channel = getBroadcastChannel(); 864 if (channel) { 865 channel.postMessage({ key, fid }); 866 } 867 closeBroadcastChannel(); 868} 869let broadcastChannel = null; 870/** Opens and returns a BroadcastChannel if it is supported by the browser. */ 871function getBroadcastChannel() { 872 if (!broadcastChannel && 'BroadcastChannel' in self) { 873 broadcastChannel = new BroadcastChannel('[Firebase] FID Change'); 874 broadcastChannel.onmessage = e => { 875 callFidChangeCallbacks(e.data.key, e.data.fid); 876 }; 877 } 878 return broadcastChannel; 879} 880function closeBroadcastChannel() { 881 if (fidChangeCallbacks.size === 0 && broadcastChannel) { 882 broadcastChannel.close(); 883 broadcastChannel = null; 884 } 885} 886 887/** 888 * @license 889 * Copyright 2019 Google LLC 890 * 891 * Licensed under the Apache License, Version 2.0 (the "License"); 892 * you may not use this file except in compliance with the License. 893 * You may obtain a copy of the License at 894 * 895 * http://www.apache.org/licenses/LICENSE-2.0 896 * 897 * Unless required by applicable law or agreed to in writing, software 898 * distributed under the License is distributed on an "AS IS" BASIS, 899 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 900 * See the License for the specific language governing permissions and 901 * limitations under the License. 902 */ 903const DATABASE_NAME$1 = 'firebase-installations-database'; 904const DATABASE_VERSION$1 = 1; 905const OBJECT_STORE_NAME$1 = 'firebase-installations-store'; 906let dbPromise$1 = null; 907function getDbPromise$1() { 908 if (!dbPromise$1) { 909 dbPromise$1 = openDb(DATABASE_NAME$1, DATABASE_VERSION$1, upgradeDB => { 910 // We don't use 'break' in this switch statement, the fall-through 911 // behavior is what we want, because if there are multiple versions between 912 // the old version and the current version, we want ALL the migrations 913 // that correspond to those versions to run, not only the last one. 914 // eslint-disable-next-line default-case 915 switch (upgradeDB.oldVersion) { 916 case 0: 917 upgradeDB.createObjectStore(OBJECT_STORE_NAME$1); 918 } 919 }); 920 } 921 return dbPromise$1; 922} 923/** Assigns or overwrites the record for the given key with the given value. */ 924async function set(appConfig, value) { 925 const key = getKey$1(appConfig); 926 const db = await getDbPromise$1(); 927 const tx = db.transaction(OBJECT_STORE_NAME$1, 'readwrite'); 928 const objectStore = tx.objectStore(OBJECT_STORE_NAME$1); 929 const oldValue = await objectStore.get(key); 930 await objectStore.put(value, key); 931 await tx.complete; 932 if (!oldValue || oldValue.fid !== value.fid) { 933 fidChanged(appConfig, value.fid); 934 } 935 return value; 936} 937/** Removes record(s) from the objectStore that match the given key. */ 938async function remove(appConfig) {
vendor: 6,749 bytes, lines 939-1113
939 const key = getKey$1(appConfig); 940 const db = await getDbPromise$1(); 941 const tx = db.transaction(OBJECT_STORE_NAME$1, 'readwrite'); 942 await tx.objectStore(OBJECT_STORE_NAME$1).delete(key); 943 await tx.complete; 944} 945/** 946 * Atomically updates a record with the result of updateFn, which gets 947 * called with the current value. If newValue is undefined, the record is 948 * deleted instead. 949 * @return Updated value 950 */ 951async function update(appConfig, updateFn) { 952 const key = getKey$1(appConfig); 953 const db = await getDbPromise$1(); 954 const tx = db.transaction(OBJECT_STORE_NAME$1, 'readwrite'); 955 const store = tx.objectStore(OBJECT_STORE_NAME$1); 956 const oldValue = await store.get(key); 957 const newValue = updateFn(oldValue); 958 if (newValue === undefined) { 959 await store.delete(key); 960 } 961 else { 962 await store.put(newValue, key); 963 } 964 await tx.complete; 965 if (newValue && (!oldValue || oldValue.fid !== newValue.fid)) { 966 fidChanged(appConfig, newValue.fid); 967 } 968 return newValue; 969} 970 971/** 972 * @license 973 * Copyright 2019 Google LLC 974 * 975 * Licensed under the Apache License, Version 2.0 (the "License"); 976 * you may not use this file except in compliance with the License. 977 * You may obtain a copy of the License at 978 * 979 * http://www.apache.org/licenses/LICENSE-2.0 980 * 981 * Unless required by applicable law or agreed to in writing, software 982 * distributed under the License is distributed on an "AS IS" BASIS, 983 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 984 * See the License for the specific language governing permissions and 985 * limitations under the License. 986 */ 987/** 988 * Updates and returns the InstallationEntry from the database. 989 * Also triggers a registration request if it is necessary and possible. 990 */ 991async function getInstallationEntry(appConfig) { 992 let registrationPromise; 993 const installationEntry = await update(appConfig, oldEntry => { 994 const installationEntry = updateOrCreateInstallationEntry(oldEntry); 995 const entryWithPromise = triggerRegistrationIfNecessary(appConfig, installationEntry); 996 registrationPromise = entryWithPromise.registrationPromise; 997 return entryWithPromise.installationEntry; 998 }); 999 if (installationEntry.fid === INVALID_FID) { 1000 // FID generation failed. Waiting for the FID from the server. 1001 return { installationEntry: await registrationPromise }; 1002 } 1003 return { 1004 installationEntry, 1005 registrationPromise 1006 }; 1007} 1008/** 1009 * Creates a new Installation Entry if one does not exist. 1010 * Also clears timed out pending requests. 1011 */ 1012function updateOrCreateInstallationEntry(oldEntry) { 1013 const entry = oldEntry || { 1014 fid: generateFid(), 1015 registrationStatus: 0 /* NOT_STARTED */ 1016 }; 1017 return clearTimedOutRequest(entry); 1018} 1019/** 1020 * If the Firebase Installation is not registered yet, this will trigger the 1021 * registration and return an InProgressInstallationEntry. 1022 * 1023 * If registrationPromise does not exist, the installationEntry is guaranteed 1024 * to be registered. 1025 */ 1026function triggerRegistrationIfNecessary(appConfig, installationEntry) { 1027 if (installationEntry.registrationStatus === 0 /* NOT_STARTED */) { 1028 if (!navigator.onLine) { 1029 // Registration required but app is offline. 1030 const registrationPromiseWithError = Promise.reject(ERROR_FACTORY$1.create("app-offline" /* APP_OFFLINE */)); 1031 return { 1032 installationEntry, 1033 registrationPromise: registrationPromiseWithError 1034 }; 1035 } 1036 // Try registering. Change status to IN_PROGRESS. 1037 const inProgressEntry = { 1038 fid: installationEntry.fid, 1039 registrationStatus: 1 /* IN_PROGRESS */, 1040 registrationTime: Date.now() 1041 }; 1042 const registrationPromise = registerInstallation(appConfig, inProgressEntry); 1043 return { installationEntry: inProgressEntry, registrationPromise }; 1044 } 1045 else if (installationEntry.registrationStatus === 1 /* IN_PROGRESS */) { 1046 return { 1047 installationEntry, 1048 registrationPromise: waitUntilFidRegistration(appConfig) 1049 }; 1050 } 1051 else { 1052 return { installationEntry }; 1053 } 1054} 1055/** This will be executed only once for each new Firebase Installation. */ 1056async function registerInstallation(appConfig, installationEntry) { 1057 try { 1058 const registeredInstallationEntry = await createInstallationRequest(appConfig, installationEntry); 1059 return set(appConfig, registeredInstallationEntry); 1060 } 1061 catch (e) { 1062 if (isServerError(e) && e.customData.serverCode === 409) { 1063 // Server returned a "FID can not be used" error. 1064 // Generate a new ID next time. 1065 await remove(appConfig); 1066 } 1067 else { 1068 // Registration failed. Set FID as not registered. 1069 await set(appConfig, { 1070 fid: installationEntry.fid, 1071 registrationStatus: 0 /* NOT_STARTED */ 1072 }); 1073 } 1074 throw e; 1075 } 1076} 1077/** Call if FID registration is pending in another request. */ 1078async function waitUntilFidRegistration(appConfig) { 1079 // Unfortunately, there is no way of reliably observing when a value in 1080 // IndexedDB changes (yet, see https://github.com/WICG/indexed-db-observers), 1081 // so we need to poll. 1082 let entry = await updateInstallationRequest(appConfig); 1083 while (entry.registrationStatus === 1 /* IN_PROGRESS */) { 1084 // createInstallation request still in progress. 1085 await sleep(100); 1086 entry = await updateInstallationRequest(appConfig); 1087 } 1088 if (entry.registrationStatus === 0 /* NOT_STARTED */) { 1089 // The request timed out or failed in a different call. Try again. 1090 const { installationEntry, registrationPromise } = await getInstallationEntry(appConfig); 1091 if (registrationPromise) { 1092 return registrationPromise; 1093 } 1094 else { 1095 // if there is no registrationPromise, entry is registered. 1096 return installationEntry; 1097 } 1098 } 1099 return entry; 1100} 1101/** 1102 * Called only if there is a CreateInstallation request in progress. 1103 * 1104 * Updates the InstallationEntry in the DB based on the status of the 1105 * CreateInstallation request. 1106 * 1107 * Returns the updated InstallationEntry. 1108 */ 1109function updateInstallationRequest(appConfig) { 1110 return update(appConfig, oldEntry => { 1111 if (!oldEntry) { 1112 throw ERROR_FACTORY$1.create("installation-not-found" /* INSTALLATION_NOT_FOUND */); 1113 }
1114 return clearTimedOutRequest(oldEntry); 1115 }); 1116} 1117function clearTimedOutRequest(entry) { 1118 if (hasInstallationRequestTimedOut(entry)) { 1119 return { 1120 fid: entry.fid, 1121 registrationStatus: 0 /* NOT_STARTED */ 1122 }; 1123 } 1124 return entry; 1125} 1126function hasInstallationRequestTimedOut(installationEntry) { 1127 return (installationEntry.registrationStatus === 1 /* IN_PROGRESS */ && 1128 installationEntry.registrationTime + PENDING_TIMEOUT_MS < Date.now()); 1129} 1130 1131/** 1132 * @license 1133 * Copyright 2019 Google LLC 1134 * 1135 * Licensed under the Apache License, Version 2.0 (the "License"); 1136 * you may not use this file except in compliance with the License. 1137 * You may obtain a copy of the License at 1138 * 1139 * http://www.apache.org/licenses/LICENSE-2.0 1140 * 1141 * Unless required by applicable law or agreed to in writing, software 1142 * distributed under the License is distributed on an "AS IS" BASIS, 1143 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1144 * See the License for the specific language governing permissions and 1145 * limitations under the License. 1146 */ 1147async function generateAuthTokenRequest({ appConfig, platformLoggerProvider }, installationEntry) { 1148 const endpoint = getGenerateAuthTokenEndpoint(appConfig, installationEntry); 1149 const headers = getHeadersWithAuth(appConfig, installationEntry); 1150 // If platform logger exists, add the platform info string to the header. 1151 const platformLogger = platformLoggerProvider.getImmediate({ 1152 optional: true 1153 }); 1154 if (platformLogger) { 1155 headers.append('x-firebase-client', platformLogger.getPlatformInfoString()); 1156 } 1157 const body = { 1158 installation: { 1159 sdkVersion: PACKAGE_VERSION 1160 } 1161 }; 1162 const request = { 1163 method: 'POST', 1164 headers, 1165 body: JSON.stringify(body) 1166 }; 1167 const response = await retryIfServerError(() => fetch(endpoint, request)); 1168 if (response.ok) { 1169 const responseValue = await response.json();
vendor: 4,317 bytes, lines 1170-1277
1170 const completedAuthToken = extractAuthTokenInfoFromResponse(responseValue); 1171 return completedAuthToken; 1172 } 1173 else { 1174 throw await getErrorFromResponse('Generate Auth Token', response); 1175 } 1176} 1177function getGenerateAuthTokenEndpoint(appConfig, { fid }) { 1178 return `${getInstallationsEndpoint(appConfig)}/${fid}/authTokens:generate`; 1179} 1180 1181/** 1182 * @license 1183 * Copyright 2019 Google LLC 1184 * 1185 * Licensed under the Apache License, Version 2.0 (the "License"); 1186 * you may not use this file except in compliance with the License. 1187 * You may obtain a copy of the License at 1188 * 1189 * http://www.apache.org/licenses/LICENSE-2.0 1190 * 1191 * Unless required by applicable law or agreed to in writing, software 1192 * distributed under the License is distributed on an "AS IS" BASIS, 1193 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1194 * See the License for the specific language governing permissions and 1195 * limitations under the License. 1196 */ 1197/** 1198 * Returns a valid authentication token for the installation. Generates a new 1199 * token if one doesn't exist, is expired or about to expire. 1200 * 1201 * Should only be called if the Firebase Installation is registered. 1202 */ 1203async function refreshAuthToken(installations, forceRefresh = false) { 1204 let tokenPromise; 1205 const entry = await update(installations.appConfig, oldEntry => { 1206 if (!isEntryRegistered(oldEntry)) { 1207 throw ERROR_FACTORY$1.create("not-registered" /* NOT_REGISTERED */); 1208 } 1209 const oldAuthToken = oldEntry.authToken; 1210 if (!forceRefresh && isAuthTokenValid(oldAuthToken)) { 1211 // There is a valid token in the DB. 1212 return oldEntry; 1213 } 1214 else if (oldAuthToken.requestStatus === 1 /* IN_PROGRESS */) { 1215 // There already is a token request in progress. 1216 tokenPromise = waitUntilAuthTokenRequest(installations, forceRefresh); 1217 return oldEntry; 1218 } 1219 else { 1220 // No token or token expired. 1221 if (!navigator.onLine) { 1222 throw ERROR_FACTORY$1.create("app-offline" /* APP_OFFLINE */); 1223 } 1224 const inProgressEntry = makeAuthTokenRequestInProgressEntry(oldEntry); 1225 tokenPromise = fetchAuthTokenFromServer(installations, inProgressEntry); 1226 return inProgressEntry; 1227 } 1228 }); 1229 const authToken = tokenPromise 1230 ? await tokenPromise 1231 : entry.authToken; 1232 return authToken; 1233} 1234/** 1235 * Call only if FID is registered and Auth Token request is in progress. 1236 * 1237 * Waits until the current pending request finishes. If the request times out, 1238 * tries once in this thread as well. 1239 */ 1240async function waitUntilAuthTokenRequest(installations, forceRefresh) { 1241 // Unfortunately, there is no way of reliably observing when a value in 1242 // IndexedDB changes (yet, see https://github.com/WICG/indexed-db-observers), 1243 // so we need to poll. 1244 let entry = await updateAuthTokenRequest(installations.appConfig); 1245 while (entry.authToken.requestStatus === 1 /* IN_PROGRESS */) { 1246 // generateAuthToken still in progress. 1247 await sleep(100); 1248 entry = await updateAuthTokenRequest(installations.appConfig); 1249 } 1250 const authToken = entry.authToken; 1251 if (authToken.requestStatus === 0 /* NOT_STARTED */) { 1252 // The request timed out or failed in a different call. Try again. 1253 return refreshAuthToken(installations, forceRefresh); 1254 } 1255 else { 1256 return authToken; 1257 } 1258} 1259/** 1260 * Called only if there is a GenerateAuthToken request in progress. 1261 * 1262 * Updates the InstallationEntry in the DB based on the status of the 1263 * GenerateAuthToken request. 1264 * 1265 * Returns the updated InstallationEntry. 1266 */ 1267function updateAuthTokenRequest(appConfig) { 1268 return update(appConfig, oldEntry => { 1269 if (!isEntryRegistered(oldEntry)) { 1270 throw ERROR_FACTORY$1.create("not-registered" /* NOT_REGISTERED */); 1271 } 1272 const oldAuthToken = oldEntry.authToken; 1273 if (hasAuthTokenRequestTimedOut(oldAuthToken)) { 1274 return Object.assign(Object.assign({}, oldEntry), { authToken: { requestStatus: 0 /* NOT_STARTED */ } }); 1275 } 1276 return oldEntry; 1277 });
1278} 1279async function fetchAuthTokenFromServer(installations, installationEntry) { 1280 try { 1281 const authToken = await generateAuthTokenRequest(installations, installationEntry); 1282 const updatedInstallationEntry = Object.assign(Object.assign({}, installationEntry), { authToken }); 1283 await set(installations.appConfig, updatedInstallationEntry); 1284 return authToken; 1285 } 1286 catch (e) { 1287 if (isServerError(e) && 1288 (e.customData.serverCode === 401 || e.customData.serverCode === 404)) { 1289 // Server returned a "FID not found" or a "Invalid authentication" error. 1290 // Generate a new ID next time. 1291 await remove(installations.appConfig); 1292 } 1293 else { 1294 const updatedInstallationEntry = Object.assign(Object.assign({}, installationEntry), { authToken: { requestStatus: 0 /* NOT_STARTED */ } }); 1295 await set(installations.appConfig, updatedInstallationEntry); 1296 } 1297 throw e; 1298 } 1299} 1300function isEntryRegistered(installationEntry) { 1301 return (installationEntry !== undefined && 1302 installationEntry.registrationStatus === 2 /* COMPLETED */); 1303} 1304function isAuthTokenValid(authToken) { 1305 return (authToken.requestStatus === 2 /* COMPLETED */ && 1306 !isAuthTokenExpired(authToken)); 1307} 1308function isAuthTokenExpired(authToken) { 1309 const now = Date.now(); 1310 return (now < authToken.creationTime || 1311 authToken.creationTime + authToken.expiresIn < now + TOKEN_EXPIRATION_BUFFER); 1312} 1313/** Returns an updated InstallationEntry with an InProgressAuthToken. */ 1314function makeAuthTokenRequestInProgressEntry(oldEntry) { 1315 const inProgressAuthToken = { 1316 requestStatus: 1 /* IN_PROGRESS */, 1317 requestTime: Date.now() 1318 }; 1319 return Object.assign(Object.assign({}, oldEntry), { authToken: inProgressAuthToken }); 1320} 1321function hasAuthTokenRequestTimedOut(authToken) { 1322 return (authToken.requestStatus === 1 /* IN_PROGRESS */ && 1323 authToken.requestTime + PENDING_TIMEOUT_MS < Date.now()); 1324} 1325 1326/** 1327 * @license 1328 * Copyright 2019 Google LLC 1329 * 1330 * Licensed under the Apache License, Version 2.0 (the "License"); 1331 * you may not use this file except in compliance with the License. 1332 * You may obtain a copy of the License at 1333 * 1334 * http://www.apache.org/licenses/LICENSE-2.0 1335 * 1336 * Unless required by applicable law or agreed to in writing, software 1337 * distributed under the License is distributed on an "AS IS" BASIS, 1338 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1339 * See the License for the specific language governing permissions and 1340 * limitations under the License. 1341 */ 1342/** 1343 * Creates a Firebase Installation if there isn't one for the app and 1344 * returns the Installation ID. 1345 * @param installations - The `Installations` instance. 1346 * 1347 * @public 1348 */ 1349async function getId(installations) { 1350 const installationsImpl = installations; 1351 const { installationEntry, registrationPromise } = await getInstallationEntry(installationsImpl.appConfig); 1352 if (registrationPromise) { 1353 registrationPromise.catch(console.error); 1354 } 1355 else { 1356 // If the installation is already registered, update the authentication 1357 // token if needed. 1358 refreshAuthToken(installationsImpl).catch(console.error); 1359 } 1360 return installationEntry.fid; 1361} 1362 1363/** 1364 * @license 1365 * Copyright 2019 Google LLC 1366 * 1367 * Licensed under the Apache License, Version 2.0 (the "License"); 1368 * you may not use this file except in compliance with the License. 1369 * You may obtain a copy of the License at 1370 * 1371 * http://www.apache.org/licenses/LICENSE-2.0 1372 * 1373 * Unless required by applicable law or agreed to in writing, software 1374 * distributed under the License is distributed on an "AS IS" BASIS, 1375 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1376 * See the License for the specific language governing permissions and 1377 * limitations under the License. 1378 */ 1379/** 1380 * Returns a Firebase Installations auth token, identifying the current 1381 * Firebase Installation. 1382 * @param installations - The `Installations` instance. 1383 * @param forceRefresh - Force refresh regardless of token expiration. 1384 * 1385 * @public 1386 */ 1387async function getToken$2(installations, forceRefresh = false) { 1388 const installationsImpl = installations; 1389 await completeInstallationRegistration(installationsImpl.appConfig); 1390 // At this point we either have a Registered Installation in the DB, or we've 1391 // already thrown an error. 1392 const authToken = await refreshAuthToken(installationsImpl, forceRefresh); 1393 return authToken.token; 1394} 1395async function completeInstallationRegistration(appConfig) { 1396 const { registrationPromise } = await getInstallationEntry(appConfig); 1397 if (registrationPromise) { 1398 // A createInstallation request is in progress. Wait until it finishes. 1399 await registrationPromise; 1400 } 1401} 1402 1403/** 1404 * @license 1405 * Copyright 2019 Google LLC 1406 * 1407 * Licensed under the Apache License, Version 2.0 (the "License");
1408 * you may not use this file except in compliance with the License. 1409 * You may obtain a copy of the License at 1410 * 1411 * http://www.apache.org/licenses/LICENSE-2.0 1412 * 1413 * Unless required by applicable law or agreed to in writing, software 1414 * distributed under the License is distributed on an "AS IS" BASIS, 1415 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1416 * See the License for the specific language governing permissions and 1417 * limitations under the License. 1418 */ 1419function extractAppConfig$1(app) { 1420 if (!app || !app.options) { 1421 throw getMissingValueError$1('App Configuration'); 1422 } 1423 if (!app.name) { 1424 throw getMissingValueError$1('App Name'); 1425 } 1426 // Required app config keys 1427 const configKeys = [ 1428 'projectId', 1429 'apiKey', 1430 'appId' 1431 ]; 1432 for (const keyName of configKeys) { 1433 if (!app.options[keyName]) { 1434 throw getMissingValueError$1(keyName); 1435 } 1436 } 1437 return { 1438 appName: app.name, 1439 projectId: app.options.projectId, 1440 apiKey: app.options.apiKey, 1441 appId: app.options.appId 1442 }; 1443} 1444function getMissingValueError$1(valueName) { 1445 return ERROR_FACTORY$1.create("missing-app-config-values" /* MISSING_APP_CONFIG_VALUES */, { 1446 valueName 1447 }); 1448} 1449 1450/** 1451 * @license 1452 * Copyright 2020 Google LLC 1453 * 1454 * Licensed under the Apache License, Version 2.0 (the "License"); 1455 * you may not use this file except in compliance with the License. 1456 * You may obtain a copy of the License at 1457 * 1458 * http://www.apache.org/licenses/LICENSE-2.0 1459 * 1460 * Unless required by applicable law or agreed to in writing, software 1461 * distributed under the License is distributed on an "AS IS" BASIS, 1462 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1463 * See the License for the specific language governing permissions and 1464 * limitations under the License. 1465 */ 1466const INSTALLATIONS_NAME = 'installations'; 1467const INSTALLATIONS_NAME_INTERNAL = 'installations-internal'; 1468const publicFactory = (container) => { 1469 const app = container.getProvider('app').getImmediate(); 1470 // Throws if app isn't configured properly. 1471 const appConfig = extractAppConfig$1(app); 1472 const platformLoggerProvider = _getProvider(app, 'platform-logger'); 1473 const installationsImpl = { 1474 app, 1475 appConfig, 1476 platformLoggerProvider, 1477 _delete: () => Promise.resolve() 1478 }; 1479 return installationsImpl; 1480}; 1481const internalFactory = (container) => { 1482 const app = container.getProvider('app').getImmediate(); 1483 // Internal FIS instance relies on public FIS instance. 1484 const installations = _getProvider(app, INSTALLATIONS_NAME).getImmediate(); 1485 const installationsInternal = { 1486 getId: () => getId(installations), 1487 getToken: (forceRefresh) => getToken$2(installations, forceRefresh) 1488 }; 1489 return installationsInternal; 1490}; 1491function registerInstallations() { 1492 _registerComponent(new Component(INSTALLATIONS_NAME, publicFactory, "PUBLIC" /* PUBLIC */)); 1493 _registerComponent(new Component(INSTALLATIONS_NAME_INTERNAL, internalFactory, "PRIVATE" /* PRIVATE */)); 1494} 1495 1496/** 1497 * Firebase Installations 1498 * 1499 * @packageDocumentation 1500 */ 1501registerInstallations(); 1502registerVersion(name$1, version$1); 1503// BUILD_TARGET will be replaced by values like esm5, esm2017, cjs5, etc during the compilation 1504registerVersion(name$1, version$1, 'esm2017'); 1505 1506/** 1507 * @license 1508 * Copyright 2019 Google LLC 1509 * 1510 * Licensed under the Apache License, Version 2.0 (the "License"); 1511 * you may not use this file except in compliance with the License. 1512 * You may obtain a copy of the License at 1513 * 1514 * http://www.apache.org/licenses/LICENSE-2.0 1515 * 1516 * Unless required by applicable law or agreed to in writing, software 1517 * distributed under the License is distributed on an "AS IS" BASIS, 1518 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1519 * See the License for the specific language governing permissions and 1520 * limitations under the License. 1521 */ 1522const DEFAULT_SW_PATH = '/firebase-messaging-sw.js'; 1523const DEFAULT_SW_SCOPE = '/firebase-cloud-messaging-push-scope'; 1524const DEFAULT_VAPID_KEY = 'BDOU99-h67HcA6JeFXHbSNMu7e2yNNu3RzoMj8TM4W88jITfq7ZmPvIM1Iv-4_l2LxQcYwhqby2xGpWwzjfAnG4'; 1525const ENDPOINT = 'https://fcmregistrations.googleapis.com/v1'; 1526const CONSOLE_CAMPAIGN_ID = 'google.c.a.c_id'; 1527const CONSOLE_CAMPAIGN_NAME = 'google.c.a.c_l'; 1528const CONSOLE_CAMPAIGN_TIME = 'google.c.a.ts'; 1529/** Set to '1' if Analytics is enabled for the campaign */ 1530const CONSOLE_CAMPAIGN_ANALYTICS_ENABLED = 'google.c.a.e'; 1531var MessageType$1; 1532(function (MessageType) { 1533 MessageType[MessageType["DATA_MESSAGE"] = 1] = "DATA_MESSAGE"; 1534 MessageType[MessageType["DISPLAY_NOTIFICATION"] = 3] = "DISPLAY_NOTIFICATION"; 1535})(MessageType$1 || (MessageType$1 = {})); 1536 1537/** 1538 * @license 1539 * Copyright 2018 Google LLC 1540 * 1541 * Licensed under the Apache License, Version 2.0 (the "License");
1541 you may not use this file except 1542 * in compliance with the License. You may obtain a copy of the License at 1543 * 1544 * http://www.apache.org/licenses/LICENSE-2.0 1545 * 1546 * Unless required by applicable law or agreed to in writing, software distributed under the License 1547 * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express 1548 * or implied. See the License for the specific language governing permissions and limitations under 1549 * the License. 1550 */ 1551var MessageType; 1552(function (MessageType) { 1553 MessageType["PUSH_RECEIVED"] = "push-received"; 1554 MessageType["NOTIFICATION_CLICKED"] = "notification-clicked"; 1555})(MessageType || (MessageType = {})); 1556 1557/** 1558 * @license 1559 * Copyright 2017 Google LLC 1560 * 1561 * Licensed under the Apache License, Version 2.0 (the "License"); 1562 * you may not use this file except in compliance with the License. 1563 * You may obtain a copy of the License at 1564 * 1565 * http://www.apache.org/licenses/LICENSE-2.0 1566 * 1567 * Unless required by applicable law or agreed to in writing, software 1568 * distributed under the License is distributed on an "AS IS" BASIS, 1569 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1570 * See the License for the specific language governing permissions and 1571 * limitations under the License. 1572 */ 1573function arrayToBase64(array) { 1574 const uint8Array = new Uint8Array(array); 1575 const base64String = btoa(String.fromCharCode(...uint8Array)); 1576 return base64String.replace(/=/g, '').replace(/\+/g, '-').replace(/\//g, '_'); 1577} 1578function base64ToArray(base64String) { 1579 const padding = '='.repeat((4 - (base64String.length % 4)) % 4); 1580 const base64 = (base64String + padding) 1581 .replace(/\-/g, '+') 1582 .replace(/_/g, '/'); 1583 const rawData = atob(base64); 1584 const outputArray = new Uint8Array(rawData.length); 1585 for (let i = 0; i < rawData.length; ++i) { 1586 outputArray[i] = rawData.charCodeAt(i); 1587 } 1588 return outputArray; 1589} 1590 1591/** 1592 * @license 1593 * Copyright 2019 Google LLC 1594 * 1595 * Licensed under the Apache License, Version 2.0 (the "License"); 1596 * you may not use this file except in compliance with the License. 1597 * You may obtain a copy of the License at 1598 * 1599 * http://www.apache.org/licenses/LICENSE-2.0 1600 * 1601 * Unless required by applicable law or agreed to in writing, software 1602 * distributed under the License is distributed on an "AS IS" BASIS, 1603 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1604 * See the License for the specific language governing permissions and 1605 * limitations under the License. 1606 */ 1607const OLD_DB_NAME = 'fcm_token_details_db'; 1608/** 1609 * The last DB version of 'fcm_token_details_db' was 4. This is one higher, so that the upgrade 1610 * callback is called for all versions of the old DB. 1611 */ 1612const OLD_DB_VERSION = 5; 1613const OLD_OBJECT_STORE_NAME = 'fcm_token_object_Store'; 1614async function migrateOldDatabase(senderId) { 1615 if ('databases' in indexedDB) { 1616 // indexedDb.databases() is an IndexedDB v3 API and does not exist in all browsers. TODO: Remove 1617 // typecast when it lands in TS types. 1618 const databases = await indexedDB.databases(); 1619 const dbNames = databases.map(db => db.name); 1620 if (!dbNames.includes(OLD_DB_NAME)) { 1621 // old DB didn't exist, no need to open. 1622 return null; 1623 } 1624 } 1625 let tokenDetails = null; 1626 const db = await openDb(OLD_DB_NAME, OLD_DB_VERSION, async (db) => { 1627 var _a; 1628 if (db.oldVersion < 2) { 1629 // Database too old, skip migration. 1630 return; 1631 } 1632 if (!db.objectStoreNames.contains(OLD_OBJECT_STORE_NAME)) { 1633 // Database did not exist. Nothing to do. 1634 return; 1635 } 1636 const objectStore = db.transaction.objectStore(OLD_OBJECT_STORE_NAME); 1637 const value = await objectStore.index('fcmSenderId').get(senderId); 1638 await objectStore.clear(); 1639 if (!value) { 1640 // No entry in the database, nothing to migrate. 1641 return; 1642 } 1643 if (db.oldVersion === 2) { 1644 const oldDetails = value; 1645 if (!oldDetails.auth || !oldDetails.p256dh || !oldDetails.endpoint) { 1646 return; 1647 } 1648 tokenDetails = { 1649 token: oldDetails.fcmToken, 1650 createTime: (_a = oldDetails.createTime) !== null && _a !== void 0 ? _a : Date.now(), 1651 subscriptionOptions: { 1652 auth: oldDetails.auth, 1653 p256dh: oldDetails.p256dh, 1654 endpoint: oldDetails.endpoint, 1655 swScope: oldDetails.swScope, 1656 vapidKey: typeof oldDetails.vapidKey === 'string' 1657 ? oldDetails.vapidKey 1658 : arrayToBase64(oldDetails.vapidKey) 1659 } 1660 }; 1661 } 1662 else if (db.oldVersion === 3) { 1663 const oldDetails = value; 1664 tokenDetails = { 1665 token: oldDetails.fcmToken, 1666 createTime: oldDetails.createTime, 1667 subscriptionOptions: { 1668 auth: arrayToBase64(oldDetails.auth), 1669 p256dh: arrayToBase64(oldDetails.p256dh), 1670 endpoint: oldDetails.endpoint, 1671 swScope: oldDetails.swScope, 1672 vapidKey: arrayToBase64(oldDetails.vapidKey) 1673 } 1674 }; 1675 } 1676 else if (db.oldVersion === 4) { 1677 const oldDetails = value; 1678 tokenDetails = { 1679 token: oldDetails.fcmToken, 1680 createTime: oldDetails.createTime, 1681 subscriptionOptions: { 1682 auth: arrayToBase64(oldDetails.auth), 1683 p256dh: arrayToBase64(oldDetails.p256dh), 1684 endpoint: oldDetails.endpoint, 1685 swScope: oldDetails.swScope, 1686 vapidKey: arrayToBase64(oldDetails.vapidKey) 1687 } 1688 }; 1689 } 1690 });
1691 db.close(); 1692 // Delete all old databases. 1693 await deleteDb(OLD_DB_NAME); 1694 await deleteDb('fcm_vapid_details_db'); 1695 await deleteDb('undefined'); 1696 return checkTokenDetails(tokenDetails) ? tokenDetails : null; 1697} 1698function checkTokenDetails(tokenDetails) { 1699 if (!tokenDetails || !tokenDetails.subscriptionOptions) { 1700 return false; 1701 } 1702 const { subscriptionOptions } = tokenDetails; 1703 return (typeof tokenDetails.createTime === 'number' && 1704 tokenDetails.createTime > 0 && 1705 typeof tokenDetails.token === 'string' && 1706 tokenDetails.token.length > 0 && 1707 typeof subscriptionOptions.auth === 'string' && 1708 subscriptionOptions.auth.length > 0 && 1709 typeof subscriptionOptions.p256dh === 'string' && 1710 subscriptionOptions.p256dh.length > 0 && 1711 typeof subscriptionOptions.endpoint === 'string' && 1712 subscriptionOptions.endpoint.length > 0 && 1713 typeof subscriptionOptions.swScope === 'string' && 1714 subscriptionOptions.swScope.length > 0 && 1715 typeof subscriptionOptions.vapidKey === 'string' && 1716 subscriptionOptions.vapidKey.length > 0); 1717} 1718 1719/** 1720 * @license 1721 * Copyright 2019 Google LLC 1722 * 1723 * Licensed under the Apache License, Version 2.0 (the "License"); 1724 * you may not use this file except in compliance with the License. 1725 * You may obtain a copy of the License at 1726 * 1727 * http://www.apache.org/licenses/LICENSE-2.0 1728 * 1729 * Unless required by applicable law or agreed to in writing, software 1730 * distributed under the License is distributed on an "AS IS" BASIS, 1731 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1732 * See the License for the specific language governing permissions and 1733 * limitations under the License. 1734 */ 1735// Exported for tests. 1736const DATABASE_NAME = 'firebase-messaging-database'; 1737const DATABASE_VERSION = 1; 1738const OBJECT_STORE_NAME = 'firebase-messaging-store'; 1739let dbPromise = null; 1740function getDbPromise() { 1741 if (!dbPromise) { 1742 dbPromise = openDb(DATABASE_NAME, DATABASE_VERSION, upgradeDb => { 1743 // We don't use 'break' in this switch statement, the fall-through behavior is what we want, 1744 // because if there are multiple versions between the old version and the current version, we 1745 // want ALL the migrations that correspond to those versions to run, not only the last one. 1746 // eslint-disable-next-line default-case 1747 switch (upgradeDb.oldVersion) { 1748 case 0: 1749 upgradeDb.createObjectStore(OBJECT_STORE_NAME); 1750 } 1751 }); 1752 } 1753 return dbPromise; 1754} 1755/** Gets record(s) from the objectStore that match the given key. */ 1756async function dbGet(firebaseDependencies) { 1757 const key = getKey(firebaseDependencies); 1758 const db = await getDbPromise(); 1759 const tokenDetails = await db 1760 .transaction(OBJECT_STORE_NAME) 1761 .objectStore(OBJECT_STORE_NAME) 1762 .get(key); 1763 if (tokenDetails) { 1764 return tokenDetails; 1765 } 1766 else { 1767 // Check if there is a tokenDetails object in the old DB. 1768 const oldTokenDetails = await migrateOldDatabase(firebaseDependencies.appConfig.senderId); 1769 if (oldTokenDetails) { 1770 await dbSet(firebaseDependencies, oldTokenDetails); 1771 return oldTokenDetails; 1772 } 1773 } 1774} 1775/** Assigns or overwrites the record for the given key with the given value. */ 1776async function dbSet(firebaseDependencies, tokenDetails) { 1777 const key = getKey(firebaseDependencies); 1778 const db = await getDbPromise(); 1779 const tx = db.transaction(OBJECT_STORE_NAME, 'readwrite'); 1780 await tx.objectStore(OBJECT_STORE_NAME).put(tokenDetails, key); 1781 await tx.complete; 1782 return tokenDetails; 1783} 1784/** Removes record(s) from the objectStore that match the given key. */ 1785async function dbRemove(firebaseDependencies) { 1786 const key = getKey(firebaseDependencies); 1787 const db = await getDbPromise(); 1788 const tx = db.transaction(OBJECT_STORE_NAME, 'readwrite'); 1789 await tx.objectStore(OBJECT_STORE_NAME).delete(key); 1790 await tx.complete; 1791} 1792function getKey({ appConfig }) { 1793 return appConfig.appId; 1794} 1795 1796/** 1797 * @license 1798 * Copyright 2017 Google LLC 1799 * 1800 * Licensed under the Apache License, Version 2.0 (the "License");
1801 * you may not use this file except in compliance with the License. 1802 * You may obtain a copy of the License at 1803 * 1804 * http://www.apache.org/licenses/LICENSE-2.0 1805 * 1806 * Unless required by applicable law or agreed to in writing, software 1807 * distributed under the License is distributed on an "AS IS" BASIS, 1808 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1809 * See the License for the specific language governing permissions and 1810 * limitations under the License. 1811 */ 1812const ERROR_MAP = { 1813 ["missing-app-config-values" /* MISSING_APP_CONFIG_VALUES */]: 'Missing App configuration value: "{$valueName}"', 1814 ["only-available-in-window" /* AVAILABLE_IN_WINDOW */]: 'This method is available in a Window context.', 1815 ["only-available-in-sw" /* AVAILABLE_IN_SW */]: 'This method is available in a service worker context.', 1816 ["permission-default" /* PERMISSION_DEFAULT */]: 'The notification permission was not granted and dismissed instead.', 1817 ["permission-blocked" /* PERMISSION_BLOCKED */]: 'The notification permission was not granted and blocked instead.', 1818 ["unsupported-browser" /* UNSUPPORTED_BROWSER */]: "This browser doesn't support the API's required to use the Firebase SDK.", 1819 ["indexed-db-unsupported" /* INDEXED_DB_UNSUPPORTED */]: "This browser doesn't support indexedDb.open() (ex. Safari iFrame, Firefox Private Browsing, etc)", 1820 ["failed-service-worker-registration" /* FAILED_DEFAULT_REGISTRATION */]: 'We are unable to register the default service worker. {$browserErrorMessage}', 1821 ["token-subscribe-failed" /* TOKEN_SUBSCRIBE_FAILED */]: 'A problem occurred while subscribing the user to FCM: {$errorInfo}', 1822 ["token-subscribe-no-token" /* TOKEN_SUBSCRIBE_NO_TOKEN */]: 'FCM returned no token when subscribing the user to push.', 1823 ["token-unsubscribe-failed" /* TOKEN_UNSUBSCRIBE_FAILED */]: 'A problem occurred while unsubscribing the ' + 1824 'user from FCM: {$errorInfo}', 1825 ["token-update-failed" /* TOKEN_UPDATE_FAILED */]: 'A problem occurred while updating the user from FCM: {$errorInfo}', 1826 ["token-update-no-token" /* TOKEN_UPDATE_NO_TOKEN */]: 'FCM returned no token when updating the user to push.', 1827 ["use-sw-after-get-token" /* USE_SW_AFTER_GET_TOKEN */]: 'The useServiceWorker() method may only be called once and must be ' + 1828 'called before calling getToken() to ensure your service worker is used.', 1829 ["invalid-sw-registration" /* INVALID_SW_REGISTRATION */]: 'The input to useServiceWorker() must be a ServiceWorkerRegistration.', 1830 ["invalid-bg-handler" /* INVALID_BG_HANDLER */]: 'The input to setBackgroundMessageHandler() must be a function.', 1831 ["invalid-vapid-key" /* INVALID_VAPID_KEY */]: 'The public VAPID key must be a string.', 1832 ["use-vapid-key-after-get-token" /* USE_VAPID_KEY_AFTER_GET_TOKEN */]: 'The usePublicVapidKey() method may only be called once and must be ' + 1833 'called before calling getToken() to ensure your VAPID key is used.' 1834}; 1835const ERROR_FACTORY = new ErrorFactory('messaging', 'Messaging', ERROR_MAP); 1836 1837/** 1838 * @license 1839 * Copyright 2019 Google LLC 1840 * 1841 * Licensed under the Apache License, Version 2.0 (the "License"); 1842 * you may not use this file except in compliance with the License. 1843 * You may obtain a copy of the License at 1844 * 1845 * http://www.apache.org/licenses/LICENSE-2.0 1846 * 1847 * Unless required by applicable law or agreed to in writing, software 1848 * distributed under the License is distributed on an "AS IS" BASIS, 1849 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1850 * See the License for the specific language governing permissions and 1851 * limitations under the License. 1852 */ 1853async function requestGetToken(firebaseDependencies, subscriptionOptions) { 1854 const headers = await getHeaders(firebaseDependencies); 1855 const body = getBody(subscriptionOptions); 1856 const subscribeOptions = { 1857 method: 'POST', 1858 headers, 1859 body: JSON.stringify(body) 1860 }; 1861 let responseData; 1862 try { 1863 const response = await fetch(getEndpoint(firebaseDependencies.appConfig), subscribeOptions); 1864 responseData = await response.json(); 1865 } 1866 catch (err) { 1867 throw ERROR_FACTORY.create("token-subscribe-failed" /* TOKEN_SUBSCRIBE_FAILED */, { 1868 errorInfo: err 1869 }); 1870 } 1871 if (responseData.error) { 1872 const message = responseData.error.message; 1873 throw ERROR_FACTORY.create("token-subscribe-failed" /* TOKEN_SUBSCRIBE_FAILED */, { 1874 errorInfo: message 1875 }); 1876 } 1877 if (!responseData.token) { 1878 throw ERROR_FACTORY.create("token-subscribe-no-token" /* TOKEN_SUBSCRIBE_NO_TOKEN */); 1879 } 1880 return responseData.token; 1881} 1882async function requestUpdateToken(firebaseDependencies, tokenDetails) { 1883 const headers = await getHeaders(firebaseDependencies); 1884 const body = getBody(tokenDetails.subscriptionOptions); 1885 const updateOptions = { 1886 method: 'PATCH', 1887 headers, 1888 body: JSON.stringify(body) 1889 }; 1890 let responseData; 1891 try { 1892 const response = await fetch(`${getEndpoint(firebaseDependencies.appConfig)}
1892/${tokenDetails.token}`, updateOptions); 1893 responseData = await response.json(); 1894 } 1895 catch (err) { 1896 throw ERROR_FACTORY.create("token-update-failed" /* TOKEN_UPDATE_FAILED */, { 1897 errorInfo: err 1898 }); 1899 } 1900 if (responseData.error) { 1901 const message = responseData.error.message; 1902 throw ERROR_FACTORY.create("token-update-failed" /* TOKEN_UPDATE_FAILED */, { 1903 errorInfo: message 1904 }); 1905 } 1906 if (!responseData.token) { 1907 throw ERROR_FACTORY.create("token-update-no-token" /* TOKEN_UPDATE_NO_TOKEN */); 1908 } 1909 return responseData.token; 1910} 1911async function requestDeleteToken(firebaseDependencies, token) { 1912 const headers = await getHeaders(firebaseDependencies); 1913 const unsubscribeOptions = { 1914 method: 'DELETE', 1915 headers 1916 }; 1917 try { 1918 const response = await fetch(`${getEndpoint(firebaseDependencies.appConfig)}/${token}`, unsubscribeOptions); 1919 const responseData = await response.json(); 1920 if (responseData.error) { 1921 const message = responseData.error.message; 1922 throw ERROR_FACTORY.create("token-unsubscribe-failed" /* TOKEN_UNSUBSCRIBE_FAILED */, { 1923 errorInfo: message 1924 }); 1925 } 1926 } 1927 catch (err) { 1928 throw ERROR_FACTORY.create("token-unsubscribe-failed" /* TOKEN_UNSUBSCRIBE_FAILED */, { 1929 errorInfo: err 1930 }); 1931 } 1932} 1933function getEndpoint({ projectId }) { 1934 return `${ENDPOINT}/projects/${projectId}/registrations`; 1935} 1936async function getHeaders({ appConfig, installations }) { 1937 const authToken = await installations.getToken(); 1938 return new Headers({ 1939 'Content-Type': 'application/json', 1940 Accept: 'application/json', 1941 'x-goog-api-key': appConfig.apiKey, 1942 'x-goog-firebase-installations-auth': `FIS ${authToken}` 1943 }); 1944} 1945function getBody({ p256dh, auth, endpoint, vapidKey }) { 1946 const body = { 1947 web: { 1948 endpoint, 1949 auth, 1950 p256dh 1951 } 1952 }; 1953 if (vapidKey !== DEFAULT_VAPID_KEY) { 1954 body.web.applicationPubKey = vapidKey; 1955 } 1956 return body; 1957} 1958 1959/** 1960 * @license 1961 * Copyright 2019 Google LLC 1962 * 1963 * Licensed under the Apache License, Version 2.0 (the "License"); 1964 * you may not use this file except in compliance with the License. 1965 * You may obtain a copy of the License at 1966 * 1967 * http://www.apache.org/licenses/LICENSE-2.0 1968 * 1969 * Unless required by applicable law or agreed to in writing, software 1970 * distributed under the License is distributed on an "AS IS" BASIS, 1971 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1972 * See the License for the specific language governing permissions and 1973 * limitations under the License. 1974 */ 1975// UpdateRegistration will be called once every week. 1976const TOKEN_EXPIRATION_MS = 7 * 24 * 60 * 60 * 1000; // 7 days 1977async function getTokenInternal(messaging) { 1978 const pushSubscription = await getPushSubscription(messaging.swRegistration, messaging.vapidKey); 1979 const subscriptionOptions = { 1980 vapidKey: messaging.vapidKey, 1981 swScope: messaging.swRegistration.scope, 1982 endpoint: pushSubscription.endpoint, 1983 auth: arrayToBase64(pushSubscription.getKey('auth')), 1984 p256dh: arrayToBase64(pushSubscription.getKey('p256dh')) 1985 }; 1986 const tokenDetails = await dbGet(messaging.firebaseDependencies); 1987 if (!tokenDetails) { 1988 // No token, get a new one. 1989 return getNewToken(messaging.firebaseDependencies, subscriptionOptions); 1990 } 1991 else if (!isTokenValid(tokenDetails.subscriptionOptions, subscriptionOptions)) { 1992 // Invalid token, get a new one. 1993 try { 1994 await requestDeleteToken(messaging.firebaseDependencies, tokenDetails.token); 1995 } 1996 catch (e) { 1997 // Suppress errors because of #2364 1998 console.warn(e); 1999 } 2000 return getNewToken(messaging.firebaseDependencies, subscriptionOptions); 2001 } 2002 else if (Date.now() >= tokenDetails.createTime + TOKEN_EXPIRATION_MS) { 2003 // Weekly token refresh 2004 return updateToken(messaging, { 2005 token: tokenDetails.token, 2006 createTime: Date.now(), 2007 subscriptionOptions 2008 }); 2009 } 2010 else { 2011 // Valid token, nothing to do. 2012 return tokenDetails.token; 2013 } 2014} 2015/** 2016 * This method deletes the token from the database, unsubscribes the token from FCM, and unregisters 2017 * the push subscription if it exists. 2018 */ 2019async function deleteTokenInternal(messaging) { 2020 const tokenDetails = await dbGet(messaging.firebaseDependencies); 2021 if (tokenDetails) { 2022 await requestDeleteToken(messaging.firebaseDependencies, tokenDetails.token); 2023 await dbRemove(messaging.firebaseDependencies); 2024 } 2025 // Unsubscribe from the push subscription. 2026 const pushSubscription = await messaging.swRegistration.pushManager.getSubscription(); 2027 if (pushSubscription) { 2028 return pushSubscription.unsubscribe(); 2029 } 2030 // If there's no SW, consider it a success. 2031 return true; 2032} 2033async function updateToken(messaging, tokenDetails) { 2034 try { 2035 const updatedToken = await requestUpdateToken(messaging.firebaseDependencies, tokenDetails); 2036 const updatedTokenDetails = Object.assign(Object.assign({}, tokenDetails), { token: updatedToken, createTime: Date.now() }); 2037 await dbSet(messaging.firebaseDependencies, updatedTokenDetails); 2038 return updatedToken; 2039 } 2040 catch (e) { 2041 await deleteTokenInternal(messaging); 2042 throw e; 2043 } 2044} 2045async function getNewToken(firebaseDependencies, subscriptionOptions) { 2046 const token = await requestGetToken(firebaseDependencies, subscriptionOptions); 2047 const tokenDetails = { 2048 token, 2049 createTime: Date.now(), 2050 subscriptionOptions 2051 }; 2052 await dbSet(firebaseDependencies, tokenDetails); 2053 return tokenDetails.token; 2054} 2055/** 2056 * Gets a PushSubscription for the current user. 2057 */ 2058async function getPushSubscription(swRegistration, vapidKey) { 2059 const subscription = await swRegistration.pushManager.getSubscription(); 2060 if (subscription) { 2061 return subscription; 2062 } 2063 return swRegistration.pushManager.subscribe({ 2064 userVisibleOnly: true, 2065 // Chrome <= 75 doesn't support base64-encoded VAPID key. For backward compatibility, VAPID key 2066 // submitted to pushManager#subscribe must be of type Uint8Array. 2067 applicationServerKey: base64ToArray(vapidKey) 2068 });
vendor: 4,100 bytes, lines 2069-2181
2069} 2070/** 2071 * Checks if the saved tokenDetails object matches the configuration provided. 2072 */ 2073function isTokenValid(dbOptions, currentOptions) { 2074 const isVapidKeyEqual = currentOptions.vapidKey === dbOptions.vapidKey; 2075 const isEndpointEqual = currentOptions.endpoint === dbOptions.endpoint; 2076 const isAuthEqual = currentOptions.auth === dbOptions.auth; 2077 const isP256dhEqual = currentOptions.p256dh === dbOptions.p256dh; 2078 return isVapidKeyEqual && isEndpointEqual && isAuthEqual && isP256dhEqual; 2079} 2080 2081/** 2082 * @license 2083 * Copyright 2020 Google LLC 2084 * 2085 * Licensed under the Apache License, Version 2.0 (the "License"); 2086 * you may not use this file except in compliance with the License. 2087 * You may obtain a copy of the License at 2088 * 2089 * http://www.apache.org/licenses/LICENSE-2.0 2090 * 2091 * Unless required by applicable law or agreed to in writing, software 2092 * distributed under the License is distributed on an "AS IS" BASIS, 2093 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2094 * See the License for the specific language governing permissions and 2095 * limitations under the License. 2096 */ 2097function externalizePayload(internalPayload) { 2098 const payload = { 2099 from: internalPayload.from, 2100 // eslint-disable-next-line camelcase 2101 collapseKey: internalPayload.collapse_key, 2102 // eslint-disable-next-line camelcase 2103 messageId: internalPayload.fcm_message_id 2104 }; 2105 propagateNotificationPayload(payload, internalPayload); 2106 propagateDataPayload(payload, internalPayload); 2107 propagateFcmOptions(payload, internalPayload); 2108 return payload; 2109} 2110function propagateNotificationPayload(payload, messagePayloadInternal) { 2111 if (!messagePayloadInternal.notification) { 2112 return; 2113 } 2114 payload.notification = {}; 2115 const title = messagePayloadInternal.notification.title; 2116 if (!!title) { 2117 payload.notification.title = title; 2118 } 2119 const body = messagePayloadInternal.notification.body; 2120 if (!!body) { 2121 payload.notification.body = body; 2122 } 2123 const image = messagePayloadInternal.notification.image; 2124 if (!!image) { 2125 payload.notification.image = image; 2126 } 2127} 2128function propagateDataPayload(payload, messagePayloadInternal) { 2129 if (!messagePayloadInternal.data) { 2130 return; 2131 } 2132 payload.data = messagePayloadInternal.data; 2133} 2134function propagateFcmOptions(payload, messagePayloadInternal) { 2135 if (!messagePayloadInternal.fcmOptions) { 2136 return; 2137 } 2138 payload.fcmOptions = {}; 2139 const link = messagePayloadInternal.fcmOptions.link; 2140 if (!!link) { 2141 payload.fcmOptions.link = link; 2142 } 2143 // eslint-disable-next-line camelcase 2144 const analyticsLabel = messagePayloadInternal.fcmOptions.analytics_label; 2145 if (!!analyticsLabel) { 2146 payload.fcmOptions.analyticsLabel = analyticsLabel; 2147 } 2148} 2149 2150/** 2151 * @license 2152 * Copyright 2019 Google LLC 2153 * 2154 * Licensed under the Apache License, Version 2.0 (the "License"); 2155 * you may not use this file except in compliance with the License. 2156 * You may obtain a copy of the License at 2157 * 2158 * http://www.apache.org/licenses/LICENSE-2.0 2159 * 2160 * Unless required by applicable law or agreed to in writing, software 2161 * distributed under the License is distributed on an "AS IS" BASIS, 2162 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2163 * See the License for the specific language governing permissions and 2164 * limitations under the License. 2165 */ 2166function isConsoleMessage(data) { 2167 // This message has a campaign ID, meaning it was sent using the Firebase Console. 2168 return typeof data === 'object' && !!data && CONSOLE_CAMPAIGN_ID in data; 2169} 2170 2171/** 2172 * @license 2173 * Copyright 2019 Google LLC 2174 * 2175 * Licensed under the Apache License, Version 2.0 (the "License"); 2176 * you may not use this file except in compliance with the License. 2177 * You may obtain a copy of the License at 2178 * 2179 * http://www.apache.org/licenses/LICENSE-2.0 2180 * 2181 * Unless required by applicable law or agreed to in writing, softw
2181are 2182 * distributed under the License is distributed on an "AS IS" BASIS, 2183 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2184 * See the License for the specific language governing permissions and 2185 * limitations under the License. 2186 */ 2187_mergeStrings('hts/frbslgigp.ogepscmv/ieo/eaylg', 'tp:/ieaeogn-agolai.o/1frlglgc/o'); 2188_mergeStrings('AzSCbw63g1R0nCw85jG8', 'Iaya3yLKwmgvh7cF0q4'); 2189function _mergeStrings(s1, s2) { 2190 const resultArray = []; 2191 for (let i = 0; i < s1.length; i++) { 2192 resultArray.push(s1.charAt(i)); 2193 if (i < s2.length) { 2194 resultArray.push(s2.charAt(i)); 2195 } 2196 } 2197 return resultArray.join(''); 2198} 2199 2200/** 2201 * @license 2202 * Copyright 2019 Google LLC 2203 * 2204 * Licensed under the Apache License, Version 2.0 (the "License"); 2205 * you may not use this file except in compliance with the License. 2206 * You may obtain a copy of the License at 2207 * 2208 * http://www.apache.org/licenses/LICENSE-2.0 2209 * 2210 * Unless required by applicable law or agreed to in writing, software 2211 * distributed under the License is distributed on an "AS IS" BASIS, 2212 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2213 * See the License for the specific language governing permissions and 2214 * limitations under the License. 2215 */ 2216function extractAppConfig(app) { 2217 if (!app || !app.options) { 2218 throw getMissingValueError('App Configuration Object'); 2219 } 2220 if (!app.name) { 2221 throw getMissingValueError('App Name'); 2222 } 2223 // Required app config keys 2224 const configKeys = [ 2225 'projectId', 2226 'apiKey', 2227 'appId', 2228 'messagingSenderId' 2229 ]; 2230 const { options } = app; 2231 for (const keyName of configKeys) { 2232 if (!options[keyName]) { 2233 throw getMissingValueError(keyName); 2234 } 2235 } 2236 return { 2237 appName: app.name, 2238 projectId: options.projectId, 2239 apiKey: options.apiKey, 2240 appId: options.appId, 2241 senderId: options.messagingSenderId 2242 }; 2243} 2244function getMissingValueError(valueName) { 2245 return ERROR_FACTORY.create("missing-app-config-values" /* MISSING_APP_CONFIG_VALUES */, { 2246 valueName 2247 }); 2248} 2249 2250/** 2251 * @license 2252 * Copyright 2020 Google LLC 2253 * 2254 * Licensed under the Apache License, Version 2.0 (the "License"); 2255 * you may not use this file except in compliance with the License. 2256 * You may obtain a copy of the License at 2257 * 2258 * http://www.apache.org/licenses/LICENSE-2.0 2259 * 2260 * Unless required by applicable law or agreed to in writing, software 2261 * distributed under the License is distributed on an "AS IS" BASIS, 2262 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2263 * See the License for the specific language governing permissions and 2264 * limitations under the License. 2265 */ 2266class MessagingService { 2267 constructor(app, installations, analyticsProvider) { 2268 // logging is only done with end user consent. Default to false. 2269 this.deliveryMetricsExportedToBigQueryEnabled = false; 2270 this.onBackgroundMessageHandler = null; 2271 this.onMessageHandler = null; 2272 this.logEvents = []; 2273 this.isLogServiceStarted = false; 2274 const appConfig = extractAppConfig(app); 2275 this.firebaseDependencies = { 2276 app, 2277 appConfig, 2278 installations, 2279 analyticsProvider 2280 }; 2281 } 2282 _delete() { 2283 return Promise.resolve(); 2284 } 2285} 2286 2287/** 2288 * @license 2289 * Copyright 2020 Google LLC 2290 * 2291 * Licensed under the Apache License, Version 2.0 (the "License"); 2292 * you may not use this file except in compliance with the License. 2293 * You may obtain a copy of the License at 2294 * 2295 * http://www.apache.org/licenses/LICENSE-2.0 2296 * 2297 * Unless required by applicable law or agreed to in writing, software 2298 * distributed under the License is distributed on an "AS IS" BASIS, 2299 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2300 * See the License for the specific language governing permissions and 2301 * limitations under the License. 2302 */ 2303async function registerDefaultSw(messaging) { 2304 try { 2305 messaging.swRegistration = await navigator.serviceWorker.register(DEFAULT_SW_PATH, { 2306 scope: DEFAULT_SW_SCOPE 2307 }); 2308 // The timing when browser updates sw when sw has an update is unreliable from experiment. It 2309 // leads to version conflict when the SDK upgrades to a newer version in the main page, but sw 2310 // is stuck with the old version. For example, 2311 // https://github.com/firebase/firebase-js-sdk/issues/2590 The following line reliably updates 2312 // sw if there was an update. 2313 messaging.swRegistration.update().catch(() => { 2314 /* it is non blocking and we don't care if it failed */ 2315 }); 2316 } 2317 catch (e) { 2318 throw ERROR_FACTORY.create("failed-service-worker-registration" /* FAILED_DEFAULT_REGISTRATION */, { 2319 browserErrorMessage: e.message 2320 }); 2321 } 2322} 2323 2324/** 2325 * @license 2326 * Copyright 2020 Google LLC 2327 * 2328 * Licensed under the Apache License, Version 2.0 (the "License");
2329 * you may not use this file except in compliance with the License. 2330 * You may obtain a copy of the License at 2331 * 2332 * http://www.apache.org/licenses/LICENSE-2.0 2333 * 2334 * Unless required by applicable law or agreed to in writing, software 2335 * distributed under the License is distributed on an "AS IS" BASIS, 2336 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2337 * See the License for the specific language governing permissions and 2338 * limitations under the License. 2339 */ 2340async function updateSwReg(messaging, swRegistration) { 2341 if (!swRegistration && !messaging.swRegistration) { 2342 await registerDefaultSw(messaging); 2343 } 2344 if (!swRegistration && !!messaging.swRegistration) { 2345 return; 2346 } 2347 if (!(swRegistration instanceof ServiceWorkerRegistration)) { 2348 throw ERROR_FACTORY.create("invalid-sw-registration" /* INVALID_SW_REGISTRATION */); 2349 } 2350 messaging.swRegistration = swRegistration; 2351} 2352 2353/** 2354 * @license 2355 * Copyright 2020 Google LLC 2356 * 2357 * Licensed under the Apache License, Version 2.0 (the "License"); 2358 * you may not use this file except in compliance with the License. 2359 * You may obtain a copy of the License at 2360 * 2361 * http://www.apache.org/licenses/LICENSE-2.0 2362 * 2363 * Unless required by applicable law or agreed to in writing, software 2364 * distributed under the License is distributed on an "AS IS" BASIS, 2365 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2366 * See the License for the specific language governing permissions and 2367 * limitations under the License. 2368 */ 2369async function updateVapidKey(messaging, vapidKey) { 2370 if (!!vapidKey) { 2371 messaging.vapidKey = vapidKey; 2372 } 2373 else if (!messaging.vapidKey) { 2374 messaging.vapidKey = DEFAULT_VAPID_KEY; 2375 } 2376} 2377 2378/** 2379 * @license 2380 * Copyright 2020 Google LLC 2381 * 2382 * Licensed under the Apache License, Version 2.0 (the "License"); 2383 * you may not use this file except in compliance with the License. 2384 * You may obtain a copy of the License at 2385 * 2386 * http://www.apache.org/licenses/LICENSE-2.0 2387 * 2388 * Unless required by applicable law or agreed to in writing, software 2389 * distributed under the License is distributed on an "AS IS" BASIS, 2390 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2391 * See the License for the specific language governing permissions and 2392 * limitations under the License. 2393 */ 2394async function getToken$1(messaging, options) { 2395 if (!navigator) { 2396 throw ERROR_FACTORY.create("only-available-in-window" /* AVAILABLE_IN_WINDOW */); 2397 } 2398 if (Notification.permission === 'default') { 2399 await Notification.requestPermission(); 2400 } 2401 if (Notification.permission !== 'granted') { 2402 throw ERROR_FACTORY.create("permission-blocked" /* PERMISSION_BLOCKED */); 2403 } 2404 await updateVapidKey(messaging, options === null || options === void 0 ? void 0 : options.vapidKey); 2405 await updateSwReg(messaging, options === null || options === void 0 ? void 0 : options.serviceWorkerRegistration); 2406 return getTokenInternal(messaging); 2407} 2408 2409/** 2410 * @license 2411 * Copyright 2019 Google LLC 2412 * 2413 * Licensed under the Apache License, Version 2.0 (the "License"); 2414 * you may not use this file except in compliance with the License. 2415 * You may obtain a copy of the License at 2416 * 2417 * http://www.apache.org/licenses/LICENSE-2.0 2418 * 2419 * Unless required by applicable law or agreed to in writing, software 2420 * distributed under the License is distributed on an "AS IS" BASIS, 2421 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2422 * See the License for the specific language governing permissions and 2423 * limitations under the License. 2424 */ 2425async function logToScion(messaging, messageType, data) { 2426 const eventType = getEventType(messageType); 2427 const analytics = await messaging.firebaseDependencies.analyticsProvider.get(); 2428 analytics.logEvent(eventType, { 2429 /* eslint-disable camelcase */ 2430 message_id: data[CONSOLE_CAMPAIGN_ID], 2431 message_name: data[CONSOLE_CAMPAIGN_NAME], 2432 message_time: data[CONSOLE_CAMPAIGN_TIME], 2433 message_device_time: Math.floor(Date.now() / 1000) 2434 /* eslint-enable camelcase */ 2435 });
2436} 2437function getEventType(messageType) { 2438 switch (messageType) { 2439 case MessageType.NOTIFICATION_CLICKED: 2440 return 'notification_open'; 2441 case MessageType.PUSH_RECEIVED: 2442 return 'notification_foreground'; 2443 default: 2444 throw new Error(); 2445 } 2446} 2447 2448/** 2449 * @license 2450 * Copyright 2017 Google LLC 2451 * 2452 * Licensed under the Apache License, Version 2.0 (the "License"); 2453 * you may not use this file except in compliance with the License. 2454 * You may obtain a copy of the License at 2455 * 2456 * http://www.apache.org/licenses/LICENSE-2.0 2457 * 2458 * Unless required by applicable law or agreed to in writing, software 2459 * distributed under the License is distributed on an "AS IS" BASIS, 2460 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2461 * See the License for the specific language governing permissions and 2462 * limitations under the License. 2463 */ 2464async function messageEventListener(messaging, event) { 2465 const internalPayload = event.data; 2466 if (!internalPayload.isFirebaseMessaging) { 2467 return; 2468 } 2469 if (messaging.onMessageHandler && 2470 internalPayload.messageType === MessageType.PUSH_RECEIVED) { 2471 if (typeof messaging.onMessageHandler === 'function') { 2472 messaging.onMessageHandler(externalizePayload(internalPayload)); 2473 } 2474 else { 2475 messaging.onMessageHandler.next(externalizePayload(internalPayload)); 2476 } 2477 } 2478 // Log to Scion if applicable 2479 const dataPayload = internalPayload.data; 2480 if (isConsoleMessage(dataPayload) && 2481 dataPayload[CONSOLE_CAMPAIGN_ANALYTICS_ENABLED] === '1') { 2482 await logToScion(messaging, internalPayload.messageType, dataPayload); 2483 } 2484} 2485 2486const name = "@firebase/messaging"; 2487const version = "0.9.4"; 2488 2489/** 2490 * @license 2491 * Copyright 2020 Google LLC 2492 * 2493 * Licensed under the Apache License, Version 2.0 (the "License"); 2494 * you may not use this file except in compliance with the License. 2495 * You may obtain a copy of the License at 2496 * 2497 * http://www.apache.org/licenses/LICENSE-2.0 2498 * 2499 * Unless required by applicable law or agreed to in writing, software 2500 * distributed under the License is distributed on an "AS IS" BASIS, 2501 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2502 * See the License for the specific language governing permissions and 2503 * limitations under the License. 2504 */ 2505const WindowMessagingFactory = (container) => { 2506 const messaging = new MessagingService(container.getProvider('app').getImmediate(), container.getProvider('installations-internal').getImmediate(), container.getProvider('analytics-internal')); 2507 navigator.serviceWorker.addEventListener('message', e => messageEventListener(messaging, e)); 2508 return messaging; 2509}; 2510const WindowMessagingInternalFactory = (container) => { 2511 const messaging = container 2512 .getProvider('messaging') 2513 .getImmediate(); 2514 const messagingInternal = { 2515 getToken: (options) => getToken$1(messaging, options) 2516 }; 2517 return messagingInternal; 2518}; 2519function registerMessagingInWindow() { 2520 _registerComponent(new Component('messaging', WindowMessagingFactory, "PUBLIC" /* PUBLIC */)); 2521 _registerComponent(new Component('messaging-internal', WindowMessagingInternalFactory, "PRIVATE" /* PRIVATE */)); 2522 registerVersion(name, version); 2523 // BUILD_TARGET will be replaced by values like esm5, esm2017, cjs5, etc during the compilation 2524 registerVersion(name, version, 'esm2017'); 2525} 2526 2527/** 2528 * @license 2529 * Copyright 2020 Google LLC 2530 * 2531 * Licensed under the Apache License, Version 2.0 (the "License"); 2532 * you may not use this file except in compliance with the License. 2533 * You may obtain a copy of the License at 2534 * 2535 * http://www.apache.org/licenses/LICENSE-2.0 2536 * 2537 * Unless required by applicable law or agreed to in writing, software 2538 * distributed under the License is distributed on an "AS IS" BASIS, 2539 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2540 * See the License for the specific language governing permissions and 2541 * limitations under the License. 2542 */ 2543/** 2544 * Checks if all required APIs exist in the browser. 2545 * @returns a Promise that resolves to a boolean. 2546 * 2547 * @public 2548 */ 2549async function isWindowSupported() { 2550 // firebase-js-sdk/issues/2393 reveals that idb#open in Safari iframe and Firefox private browsing 2551 // might be prohibited to run. In these contexts, an error would be thrown during the messaging 2552 // instantiating phase, informing the developers to import/call isSupported for special handling. 2553 return (typeof window !== 'undefined' && 2554 isIndexedDBAvailable() && 2555 (await validateIndexedDBOpenable()) && 2556 areCookiesEnabled() && 2557 'serviceWorker' in navigator && 2558 'PushManager' in window &&
vendor: 5,918 bytes, lines 2559-2716
2559 'Notification' in window && 2560 'fetch' in window && 2561 ServiceWorkerRegistration.prototype.hasOwnProperty('showNotification') && 2562 PushSubscription.prototype.hasOwnProperty('getKey')); 2563} 2564 2565/** 2566 * @license 2567 * Copyright 2020 Google LLC 2568 * 2569 * Licensed under the Apache License, Version 2.0 (the "License"); 2570 * you may not use this file except in compliance with the License. 2571 * You may obtain a copy of the License at 2572 * 2573 * http://www.apache.org/licenses/LICENSE-2.0 2574 * 2575 * Unless required by applicable law or agreed to in writing, software 2576 * distributed under the License is distributed on an "AS IS" BASIS, 2577 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2578 * See the License for the specific language governing permissions and 2579 * limitations under the License. 2580 */ 2581async function deleteToken$1(messaging) { 2582 if (!navigator) { 2583 throw ERROR_FACTORY.create("only-available-in-window" /* AVAILABLE_IN_WINDOW */); 2584 } 2585 if (!messaging.swRegistration) { 2586 await registerDefaultSw(messaging); 2587 } 2588 return deleteTokenInternal(messaging); 2589} 2590 2591/** 2592 * @license 2593 * Copyright 2020 Google LLC 2594 * 2595 * Licensed under the Apache License, Version 2.0 (the "License"); 2596 * you may not use this file except in compliance with the License. 2597 * You may obtain a copy of the License at 2598 * 2599 * http://www.apache.org/licenses/LICENSE-2.0 2600 * 2601 * Unless required by applicable law or agreed to in writing, software 2602 * distributed under the License is distributed on an "AS IS" BASIS, 2603 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2604 * See the License for the specific language governing permissions and 2605 * limitations under the License. 2606 */ 2607function onMessage$1(messaging, nextOrObserver) { 2608 if (!navigator) { 2609 throw ERROR_FACTORY.create("only-available-in-window" /* AVAILABLE_IN_WINDOW */); 2610 } 2611 messaging.onMessageHandler = nextOrObserver; 2612 return () => { 2613 messaging.onMessageHandler = null; 2614 }; 2615} 2616 2617/** 2618 * @license 2619 * Copyright 2017 Google LLC 2620 * 2621 * Licensed under the Apache License, Version 2.0 (the "License"); 2622 * you may not use this file except in compliance with the License. 2623 * You may obtain a copy of the License at 2624 * 2625 * http://www.apache.org/licenses/LICENSE-2.0 2626 * 2627 * Unless required by applicable law or agreed to in writing, software 2628 * distributed under the License is distributed on an "AS IS" BASIS, 2629 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 2630 * See the License for the specific language governing permissions and 2631 * limitations under the License. 2632 */ 2633/** 2634 * Retrieves a Firebase Cloud Messaging instance. 2635 * 2636 * @returns The Firebase Cloud Messaging instance associated with the provided firebase app. 2637 * 2638 * @public 2639 */ 2640function getMessagingInWindow(app = getApp()) { 2641 // Conscious decision to make this async check non-blocking during the messaging instance 2642 // initialization phase for performance consideration. An error would be thrown latter for 2643 // developer's information. Developers can then choose to import and call `isSupported` for 2644 // special handling. 2645 isWindowSupported().then(isSupported => { 2646 // If `isWindowSupported()` resolved, but returned false. 2647 if (!isSupported) { 2648 throw ERROR_FACTORY.create("unsupported-browser" /* UNSUPPORTED_BROWSER */); 2649 } 2650 }, _ => { 2651 // If `isWindowSupported()` rejected. 2652 throw ERROR_FACTORY.create("indexed-db-unsupported" /* INDEXED_DB_UNSUPPORTED */); 2653 }); 2654 return _getProvider(getModularInstance(app), 'messaging').getImmediate(); 2655} 2656/** 2657 * Subscribes the {@link Messaging} instance to push notifications. Returns an Firebase Cloud 2658 * Messaging registration token that can be used to send push messages to that {@link Messaging} 2659 * instance. 2660 * 2661 * If a notification permission isn't already granted, this method asks the user for permission. The 2662 * returned promise rejects if the user does not allow the app to show notifications. 2663 * 2664 * @param messaging - The {@link Messaging} instance. 2665 * @param options - Provides an optional vapid key and an optinoal service worker registration 2666 * 2667 * @returns The promise resolves with an FCM registration token. 2668 * 2669 * @public 2670 */ 2671async function getToken(messaging, options) { 2672 messaging = getModularInstance(messaging); 2673 return getToken$1(messaging, options); 2674} 2675/** 2676 * Deletes the registration token associated with this {@link Messaging} instance and unsubscribes 2677 * the {@link Messaging} instance from the push subscription. 2678 * 2679 * @param messaging - The {@link Messaging} instance. 2680 * 2681 * @returns The promise resolves when the token has been successfully deleted. 2682 * 2683 * @public 2684 */ 2685function deleteToken(messaging) { 2686 messaging = getModularInstance(messaging); 2687 return deleteToken$1(messaging); 2688} 2689/** 2690 * When a push message is received and the user is currently on a page for your origin, the 2691 * message is passed to the page and an `onMessage()` event is dispatched with the payload of 2692 * the push message. 2693 * 2694 * 2695 * @param messaging - The {@link Messaging} instance. 2696 * @param nextOrObserver - This function, or observer object with `next` defined, 2697 * is called when a message is received and the user is currently viewing your page. 2698 * @returns To stop listening for messages execute this returned function. 2699 * 2700 * @public 2701 */ 2702function onMessage(messaging, nextOrObserver) { 2703 messaging = getModularInstance(messaging); 2704 return onMessage$1(messaging, nextOrObserver); 2705} 2706 2707/** 2708 * Firebase Cloud Messaging 2709 * 2710 * @packageDocumentation 2711 */ 2712registerMessagingInWindow(); 2713 2714export { deleteToken, getMessagingInWindow as getMessaging, getToken, isWindowSupported as isSupported, onMessage }; 2715 2716//# sourceMappingURL=firebase-messaging.js.map
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.