├── test ├── appInitialize.ts ├── import-to-firestore.json ├── serviceAccount.ts ├── firebase.spec.ts ├── realtime.spec.ts └── firestore.spec.ts ├── dist ├── index.js.map ├── index.d.ts ├── index.js ├── realtime.d.ts ├── realtime.js ├── firebase.d.ts ├── firebase.js ├── realtime.js.map ├── firebase.js.map ├── firestore.js ├── firestore.d.ts └── firestore.js.map ├── env.test.sh.dist ├── src ├── index.ts ├── realtime.ts ├── firebase.ts └── firestore.ts ├── tsconfig.json ├── .github └── FUNDING.yml ├── .travis.yml ├── LICENSE ├── .gitignore ├── package.json ├── docs ├── realtime.md ├── firebase.md └── firestore.md ├── README.md ├── CHANGELOG.md ├── tslint.json └── yarn.lock /test/appInitialize.ts: -------------------------------------------------------------------------------- 1 | import { firebaseHelper } from '../dist/index'; 2 | import { serviceAccount } from './serviceAccount'; 3 | 4 | export const app = firebaseHelper.initializeApp(serviceAccount); 5 | -------------------------------------------------------------------------------- /dist/index.js.map: -------------------------------------------------------------------------------- 1 | {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;AAAA,yCAA4C;AAC5C,2CAA8C;AAC9C,yCAA4C;AAE5C,MAAM,cAAc,GAAmB,IAAI,yBAAc,EAAE,CAAC;AAInD,wCAAc;AAHvB,MAAM,eAAe,GAAoB,IAAI,2BAAe,EAAE,CAAC;AAGtC,0CAAe;AAFxC,MAAM,cAAc,GAAmB,IAAI,yBAAc,EAAE,CAAC;AAElB,wCAAc"} -------------------------------------------------------------------------------- /env.test.sh.dist: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | export TYPE="" 4 | export PROJECT_ID="" 5 | export PRIVATE_KEY_ID="" 6 | export PRIVATE_KEY="" 7 | export CLIENT_EMAIL="" 8 | export CLIENT_ID="" 9 | export AUTH_URI="" 10 | export TOKEN_URI="" 11 | export AUTH_PROVIDER_X509_CERT_URL="" 12 | export CLIENT_X509_CERT_URL="" 13 | export DATABASE_URL="" 14 | -------------------------------------------------------------------------------- /dist/index.d.ts: -------------------------------------------------------------------------------- 1 | import { FirebaseHelper } from './firebase'; 2 | import { FirestoreHelper } from './firestore'; 3 | import { RealtimeHelper } from './realtime'; 4 | declare const firebaseHelper: FirebaseHelper; 5 | declare const firestoreHelper: FirestoreHelper; 6 | declare const realtimeHelper: RealtimeHelper; 7 | export { firebaseHelper, firestoreHelper, realtimeHelper }; 8 | -------------------------------------------------------------------------------- /src/index.ts: -------------------------------------------------------------------------------- 1 | import { FirebaseHelper } from './firebase'; 2 | import { FirestoreHelper } from './firestore'; 3 | import { RealtimeHelper } from './realtime'; 4 | 5 | const firebaseHelper: FirebaseHelper = new FirebaseHelper(); 6 | const firestoreHelper: FirestoreHelper = new FirestoreHelper(); 7 | const realtimeHelper: RealtimeHelper = new RealtimeHelper(); 8 | 9 | export { firebaseHelper, firestoreHelper, realtimeHelper }; 10 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "lib": ["es2017"], 4 | "module": "commonjs", 5 | "noImplicitAny": false, 6 | "noImplicitReturns": true, 7 | "resolveJsonModule": true, 8 | "outDir": "dist", 9 | "sourceMap": true, 10 | "target": "es6", 11 | "esModuleInterop": true, 12 | "types": [ "mocha", "chai", "node" ], 13 | "declaration": true 14 | }, 15 | "compileOnSave": true, 16 | "include": [ 17 | "src" 18 | ] 19 | } 20 | -------------------------------------------------------------------------------- /test/import-to-firestore.json: -------------------------------------------------------------------------------- 1 | { 2 | "test" : { 3 | "first-key" : { 4 | "email" : "dungnq@itbox4vn.com", 5 | "website" : "dalenguyen.me", 6 | "custom" : { 7 | "firstName" : "Dale", 8 | "lastName" : "Nguyen" 9 | } 10 | }, 11 | "second-key" : { 12 | "email" : "test@dalenguyen.me", 13 | "website" : "google.com", 14 | "custom" : { 15 | "firstName" : "Harry", 16 | "lastName" : "Potter" 17 | } 18 | } 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /dist/index.js: -------------------------------------------------------------------------------- 1 | "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.realtimeHelper=exports.firestoreHelper=exports.firebaseHelper=void 0;const firebase_1=require("./firebase");const firestore_1=require("./firestore");const realtime_1=require("./realtime");const firebaseHelper=new firebase_1.FirebaseHelper();exports.firebaseHelper=firebaseHelper;const firestoreHelper=new firestore_1.FirestoreHelper();exports.firestoreHelper=firestoreHelper;const realtimeHelper=new realtime_1.RealtimeHelper();exports.realtimeHelper=realtimeHelper; -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # These are supported funding model platforms 2 | 3 | github: dalenguyen # Replace with up to 4 GitHub Sponsors-enabled usernames e.g., [user1, user2] 4 | patreon: # Replace with a single Patreon username 5 | open_collective: # Replace with a single Open Collective username 6 | ko_fi: dalenguyen # Replace with a single Ko-fi username 7 | tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel 8 | community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry 9 | liberapay: # Replace with a single Liberapay username 10 | issuehunt: # Replace with a single IssueHunt username 11 | otechie: # Replace with a single Otechie username 12 | custom: # Replace with up to 4 custom sponsorship URLs e.g., ['link1', 'link2'] 13 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: node_js 2 | node_js: 3 | - '10' 4 | deploy: 5 | provider: npm 6 | email: dungnq@itbox4vn.com 7 | api_key: 8 | secure: BSjy5UrLZOgrTnaA9mzufR3WgE2EAl1aeZMi7FAz2ymlTNAd2k4fZ0VgccEaI1g7zNvESwECgY5gpQNuPXuDU2c5kJPRXh1eu7NlLaXHlhc80faVvFEeYqhETuAvP/q9/WjabgjeoZtZT9yx2pC3MSWm65eGuJYWIXxh3uGSmLtj8kbdWoBfBodET3XGb+FNHWDSg/P49oxq/CDAVnCfZg0PlV9CI8YyxyJ3ha/Ws+YXk1O3EOwNwMv0SvKqyy62IO+wipJE+qqtwAQeFmyiWnCuXirdwD9yZclLe3R4w1HqEa5SaHpm6eyYSvzU59ZX6wV4qUSPLPdEGFhDS6NEQaOLyHGmtkq7DCR0/r4kwN5QUMwsmQJMp+LeRRwMRJlsmzM7oakhn1VS7Asnlbi1XxtAktJmgkCLoKUP0U+KuZ838iZkj4NEnGjUIdPEDHU56IycoE4zQSOXQeR55CxtcqvQli3DRk1/uh8cYkK2W3Chi2sfnpuZ45CO4Qn/hgFhIzVzt7p7fW97GZ9AODJFGm4G7RC6tTbYoIPCU1euc4+yUx8FVmVjcwWqM25OmHPNVK1Y+o41MgwWZcITzWxY8Zcgk6mVMq8C3pJ1Lfm03d8qxhd331Y6+vXtiCjKlAT+1Ve4nhGOXJVNNH+rK29qHQuDDbCg/6nyRQS+W3brDAE= 9 | on: 10 | branch: master 11 | tags: true 12 | -------------------------------------------------------------------------------- /test/serviceAccount.ts: -------------------------------------------------------------------------------- 1 | const serviceAccountJson = process.env.TYPE === undefined ? require('./serviceAccountKey.json') : {}; 2 | 3 | // console.log(process.env.PRIVATE_KEY.substr(0,50)); 4 | // console.log(process.env.PRIVATE_KEY.replace(/\\n/g, '\n').substr(0,50)); 5 | 6 | // Windows doesn't recognize source command for setting environment 7 | export const serviceAccount = process.env.TYPE === undefined ? serviceAccountJson : { 8 | "type": process.env.TYPE, 9 | "projectId": process.env.PROJECT_ID, 10 | "privateKeyId": process.env.PRIVATE_KEY_ID, 11 | "privateKey": process.env.PRIVATE_KEY.replace(/\\n/g, '\n'), 12 | "clientEmail": process.env.CLIENT_EMAIL, 13 | "clientId": process.env.CLIENT_ID, 14 | "authURI": process.env.AUTH_URI, 15 | "tokenURI": process.env.TOKEN_URI, 16 | "authProviderX509CertURL": process.env.AUTH_PROVIDER_X509_CERT_URL, 17 | "clientX509CertURL": process.env.CLIENT_X509_CERT_URL, 18 | "databaseURL": process.env.DATABASE_URL 19 | } 20 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 Dale Nguyen 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /dist/realtime.d.ts: -------------------------------------------------------------------------------- 1 | export declare class RealtimeHelper { 2 | /** 3 | * Get realtime database from path 4 | * 5 | * @param {*} db 6 | * @param {string} path 7 | * @returns {Promise} 8 | * @memberof RealtimeHelper 9 | */ 10 | getData(db: any, path: string): Promise; 11 | /** 12 | * Save data to realtime database 13 | * 14 | * @param {*} db 15 | * @param {string} path 16 | * @param {Object} data 17 | * @param {boolean} [remove=true] 18 | * @returns {Promise} 19 | * @memberof RealtimeHelper 20 | */ 21 | saveData(db: any, path: string, data: Object, remove?: boolean): Promise; 22 | /** 23 | * Update existing data 24 | * 25 | * @param {*} db 26 | * @param {string} path 27 | * @param {Object} data 28 | * @returns {Promise} 29 | * @memberof RealtimeHelper 30 | */ 31 | updateData(db: any, path: string, data: Object): Promise; 32 | /** 33 | * Delete data 34 | * 35 | * @param {*} db 36 | * @param {string} path 37 | * @returns {Promise} 38 | * @memberof RealtimeHelper 39 | */ 40 | deleteData(db: any, path: string): Promise; 41 | } 42 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | 8 | # Runtime data 9 | pids 10 | *.pid 11 | *.seed 12 | *.pid.lock 13 | 14 | # Directory for instrumented libs generated by jscoverage/JSCover 15 | lib-cov 16 | 17 | # Coverage directory used by tools like istanbul 18 | coverage 19 | 20 | # nyc test coverage 21 | .nyc_output 22 | 23 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) 24 | .grunt 25 | 26 | # Bower dependency directory (https://bower.io/) 27 | bower_components 28 | 29 | # node-waf configuration 30 | .lock-wscript 31 | 32 | # Compiled binary addons (https://nodejs.org/api/addons.html) 33 | build/Release 34 | 35 | # Dependency directories 36 | node_modules/ 37 | jspm_packages/ 38 | 39 | # TypeScript v1 declaration files 40 | typings/ 41 | 42 | # Optional npm cache directory 43 | .npm 44 | 45 | # Optional eslint cache 46 | .eslintcache 47 | 48 | # Optional REPL history 49 | .node_repl_history 50 | 51 | # Output of 'npm pack' 52 | *.tgz 53 | 54 | # Yarn Integrity file 55 | .yarn-integrity 56 | 57 | # dotenv environment variables file 58 | .env 59 | 60 | # next.js build output 61 | .next 62 | 63 | # Test files 64 | test/serviceAccountKey.json 65 | 66 | # Intellij IDEA Files 67 | .idea/ 68 | 69 | # Test environment variable 70 | env.test.sh 71 | -------------------------------------------------------------------------------- /dist/realtime.js: -------------------------------------------------------------------------------- 1 | "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.RealtimeHelper=void 0;class RealtimeHelper{getData(db,path){const ref=db.ref(path);return new Promise((resolve,reject)=>{ref.once('value',function(snapshot){const data=snapshot.val();if(data){if(data[0]===undefined){data.splice&&data.splice(0,1);} 2 | resolve(data);} 3 | else{reject('Data can\'t be found!');}});});} 4 | saveData(db,path,data,remove=true){const ref=db.ref(path);return new Promise((resolve,reject)=>{if(remove){ref.set(data,(error)=>{if(error){reject({status:false,message:error});} 5 | else{resolve({status:true,message:'Data saved succesfully!'});}});} 6 | else{const errorList=[];for(const key in data){if(data.hasOwnProperty(key)){ref.child(key).set(data[key],error=>{errorList.push(error);});}} 7 | if(errorList.length>0){reject({status:false,message:errorList});} 8 | else{resolve({status:true,message:'Data saved succesfully!'});}}});} 9 | updateData(db,path,data){const ref=db.ref(path);return new Promise((resolve,reject)=>{ref.update(data,error=>{if(error){reject({status:false,message:error});} 10 | else{resolve({status:true,message:'Data updated succesfully!'});}});});} 11 | deleteData(db,path){const ref=db.ref(path);return new Promise((resolve,reject)=>{ref.set(null,(error)=>{if(error){reject({status:false,message:error});} 12 | else{resolve({status:true,message:'Data deleted succesfully!'});}});});}} 13 | exports.RealtimeHelper=RealtimeHelper; -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "firebase-functions-helper", 3 | "version": "0.12.0", 4 | "description": "A helper NPM package for Firebase Cloud Functions", 5 | "author": { 6 | "name": "Dale Nguyen", 7 | "email": "dungnq@itbox4vn.com", 8 | "url": "http://dalenguyen.me" 9 | }, 10 | "homepage": "https://github.com/dalenguyen/firebase-functions-helper#readme", 11 | "bugs": { 12 | "url": "https://github.com/dalenguyen/firebase-functions-helper/issues" 13 | }, 14 | "keywords": [ 15 | "firebase", 16 | "cloud", 17 | "functions", 18 | "functions", 19 | "helper" 20 | ], 21 | "main": "dist/index.js", 22 | "types": "dist/index.d.ts", 23 | "scripts": { 24 | "lint": "tslint --project tsconfig.json", 25 | "package:check": "ncu", 26 | "build": "tsc && npm run minify", 27 | "minify": "jsmin -o dist/firebase.js dist/firebase.js && jsmin -o dist/firestore.js dist/firestore.js && jsmin -o dist/realtime.js dist/realtime.js && jsmin -o dist/index.js dist/index.js", 28 | "test:local": "source env.test.sh && mocha --timeout 99999999 --exit -r ts-node/register test/**/*.spec.ts", 29 | "test": "mocha --timeout 99999999 --exit -r ts-node/register test/**/*.spec.ts", 30 | "prod:local": "rm dist/* && npm run lint && npm run build && npm run test:local", 31 | "prod": "npm run lint && npm run build && npm run test" 32 | }, 33 | "dependencies": { 34 | "firebase-admin": "^9.8.0", 35 | "firestore-export-import": "^0.15.0" 36 | }, 37 | "deprecated": false, 38 | "devDependencies": { 39 | "@types/chai": "^4.2.18", 40 | "@types/mocha": "^8.2.2", 41 | "chai": "^4.3.4", 42 | "jsmin": "^1.0.1", 43 | "mocha": "^8.4.0", 44 | "ts-node": "^9.1.1", 45 | "tslint": "^6.1.3", 46 | "typescript": "^4.2.4" 47 | }, 48 | "engines": { 49 | "node": ">=10" 50 | }, 51 | "license": "MIT", 52 | "repository": { 53 | "type": "git", 54 | "url": "git+https://github.com/dalenguyen/firebase-functions-helper.git" 55 | }, 56 | "publishConfig": { 57 | "access": "public" 58 | } 59 | } 60 | -------------------------------------------------------------------------------- /docs/realtime.md: -------------------------------------------------------------------------------- 1 | # Realtime Database | Firebase Functions Helper 2 | 3 | Before starting with Realtime Database, we have to initialize Firebase App and get Realtime Database. 4 | 5 | ```sh 6 | const { firebaseHelper, realtimeHelper } = require('firebase-functions-helper'); 7 | const serviceAccount = require('./serviceAccountKey.json'); 8 | 9 | // Initialize Firebase App 10 | const app = firebaseHelper.initializeApp(serviceAccount, databaseURL); 11 | 12 | // Get Realtime Database 13 | const db = app.realtime; 14 | ``` 15 | 16 | ## 1. Get Data 17 | 18 | The result will be a Promise of an array or an object of data. 19 | 20 | ```sh 21 | realtimeHelper 22 | .getData(db, 'data-path') 23 | .then(data => console.log(data);) 24 | ``` 25 | 26 | ## 2. Save Data 27 | 28 | You will have two options that help to replace entire data path or keep and replace the data. This function will return a Promise: **{status: boolean, message: string}** 29 | 30 | ```sh 31 | const data = { 32 | td: { 33 | name: 'Toronto-Dominion Bank' 34 | }, 35 | rbc: { 36 | name: 'RBC Royal Bank' 37 | } 38 | } 39 | 40 | // Remove everything and add new data 41 | realtimeHelper 42 | .saveData(db, 'data-path', data, true); 43 | 44 | // Replace or add new data without remove the old data 45 | realtimeHelper 46 | .saveData(db, 'data-path', data, false); 47 | ``` 48 | 49 | ## 3. Updated Saved Data 50 | 51 | This function will have you to add extra information to an existing data. If the path in data is incorrect, it will create a new data. This function will return a Promise: **{status: boolean, message: string}** 52 | 53 | ```sh 54 | const updatedData = { 55 | 'td/location': 'Toronto', 56 | 'rbc/location': 'Toronto' 57 | } 58 | 59 | // Add location info to td and rbc 60 | realtimeHelper 61 | .updateData(db, 'banks', updatedData); 62 | ``` 63 | 64 | ## 4. Delete Data 65 | 66 | This function will delete all data under a path. It will return a Promise: **{status: boolean, message: string}** 67 | 68 | ```sh 69 | realtimeHelper 70 | .deleteData(db, 'data-path'); 71 | ``` 72 | -------------------------------------------------------------------------------- /dist/firebase.d.ts: -------------------------------------------------------------------------------- 1 | import * as admin from 'firebase-admin'; 2 | interface UserRecord { 3 | status: boolean; 4 | data: admin.auth.UserRecord; 5 | } 6 | export declare class FirebaseHelper { 7 | /** 8 | * Initialize Firebase App 9 | * 10 | * @param {admin.AppOptions} serviceAccount 11 | */ 12 | initializeApp(serviceAccount: admin.AppOptions): { 13 | firestore: FirebaseFirestore.Firestore; 14 | realtime: admin.database.Database; 15 | }; 16 | /** 17 | * Get User Info though UserId 18 | * 19 | * @param {string} userId 20 | * @returns {Promise} 21 | */ 22 | getUserById(userId: string): Promise; 23 | /** 24 | * Get User Info though email 25 | * 26 | * @param {string} email 27 | * @returns {Promise} 28 | * @memberof FirebaseHelper 29 | */ 30 | getUserByEmail(email: string): Promise; 31 | /** 32 | * Get User Info though phone number 33 | * 34 | * @param {string} phone 35 | * @returns {Promise} 36 | * @memberof FirebaseHelper 37 | */ 38 | getUserByPhone(phone: string): Promise; 39 | /** 40 | * Delete a user 41 | * 42 | * @param {string} userId 43 | * @memberof FirebaseHelper 44 | */ 45 | deleteUser(userId: string): Promise; 46 | /** 47 | * Delete user from an Array of User Ids 48 | * 49 | * @param {Array} userIds 50 | * @memberof FirebaseHelper 51 | */ 52 | deleteUsers(userIds: Array): void; 53 | /** 54 | * Create a new user 55 | * 56 | * @param {Object} userInfo 57 | * @returns {Promise} 58 | * @memberof FirebaseHelper 59 | */ 60 | createUser(userInfo: Object): Promise; 61 | /** 62 | * Update user Info though userId 63 | * 64 | * @param {string} userId 65 | * @param {Object} userInfo 66 | * @memberof FirebaseHelper 67 | */ 68 | updateUser(userId: string, userInfo: Object): Promise; 69 | /** 70 | * Get a list of users 71 | * 72 | * @param {number} [maxResults=1000] 73 | * @returns {Promise} 74 | * @memberof FirebaseHelper 75 | */ 76 | getAllUsers(maxResults?: number): Promise; 77 | /** 78 | * Auth function from Firebase Admin SDK 79 | */ 80 | auth(): admin.auth.Auth; 81 | } 82 | export {}; 83 | -------------------------------------------------------------------------------- /dist/firebase.js: -------------------------------------------------------------------------------- 1 | "use strict";var __createBinding=(this&&this.__createBinding)||(Object.create?(function(o,m,k,k2){if(k2===undefined)k2=k;Object.defineProperty(o,k2,{enumerable:true,get:function(){return m[k];}});}):(function(o,m,k,k2){if(k2===undefined)k2=k;o[k2]=m[k];}));var __setModuleDefault=(this&&this.__setModuleDefault)||(Object.create?(function(o,v){Object.defineProperty(o,"default",{enumerable:true,value:v});}):function(o,v){o["default"]=v;});var __importStar=(this&&this.__importStar)||function(mod){if(mod&&mod.__esModule)return mod;var result={};if(mod!=null)for(var k in mod)if(k!=="default"&&Object.prototype.hasOwnProperty.call(mod,k))__createBinding(result,mod,k);__setModuleDefault(result,mod);return result;};Object.defineProperty(exports,"__esModule",{value:true});exports.FirebaseHelper=void 0;const admin=__importStar(require("firebase-admin"));class FirebaseHelper{initializeApp(serviceAccount){admin.initializeApp({credential:admin.credential.cert(serviceAccount),databaseURL:serviceAccount.databaseURL,});return{firestore:admin.firestore(),realtime:admin.database()};} 2 | getUserById(userId){return admin.auth().getUser(userId).then((user)=>user).catch((error)=>console.log(error));} 3 | getUserByEmail(email){return admin.auth().getUserByEmail(email).then((user)=>user).catch((error)=>console.log(error));} 4 | getUserByPhone(phone){return admin.auth().getUserByPhoneNumber(phone).then((user)=>user).catch((error)=>console.log(error));} 5 | deleteUser(userId){return new Promise((resolve)=>{admin.auth().deleteUser(userId).then(()=>{resolve(true);}).catch((error)=>{console.log(error);resolve(false);});});} 6 | deleteUsers(userIds){userIds.map((userId)=>{this.deleteUser(userId).then(()=>{console.log('Successfully deleted user: ',userId);}).catch((error)=>console.log(error));});} 7 | createUser(userInfo){return new Promise((resolve)=>{admin.auth().createUser(userInfo).then((userRecord)=>{resolve({status:true,data:userRecord,});}).catch((error)=>{resolve({status:false,data:error.message,});});});} 8 | updateUser(userId,userInfo){return new Promise((resolve)=>{admin.auth().updateUser(userId,userInfo).then((userRecord)=>{resolve({status:true,data:userRecord,});}).catch((error)=>{resolve({status:false,data:error.message,});});});} 9 | getAllUsers(maxResults=1000){return admin.auth().listUsers(maxResults).then((listUsersResult)=>listUsersResult.users).catch((error)=>{console.log('Error listing users:',error);});} 10 | auth(){return admin.auth();}} 11 | exports.FirebaseHelper=FirebaseHelper; -------------------------------------------------------------------------------- /dist/realtime.js.map: -------------------------------------------------------------------------------- 1 | {"version":3,"file":"realtime.js","sourceRoot":"","sources":["../src/realtime.ts"],"names":[],"mappings":"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"} -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # firebase-functions-helper 2 | 3 | [![GitHub version](https://badge.fury.io/gh/dalenguyen%2Ffirebase-functions-helper.svg)](https://badge.fury.io/gh/dalenguyen%2Ffirebase-functions-helper) [![Build Status](https://travis-ci.org/dalenguyen/firebase-functions-helper.svg?branch=master)](https://travis-ci.org/dalenguyen/firebase-functions-helper) 4 | 5 | A helper NPM package for Firebase Cloud Functions 6 | 7 | ## Tables of Contents 8 | 9 | - [Installation](#installation) 10 | - [Get Google Cloud Account Credentials from Firebase](#get-google-cloud-account-credentials-from-firebase) 11 | - [Usage](#usage) 12 | - [Contributions](#contributions) 13 | 14 | ## Installation 15 | 16 | Install using [**npm**](https://www.npmjs.com/). 17 | 18 | ```sh 19 | npm install firebase-functions-helper 20 | ``` 21 | 22 | ## Get Google Cloud Account Credentials from Firebase 23 | 24 | You can **Generate New Private Key** from Project Settings from [Firebase Console](https://console.firebase.google.com). 25 | 26 | After that you need to copy the **databaseURL** for initiating the App. 27 | 28 | ## Usage 29 | 30 | ### Examples 31 | 32 | This is the first step that you need to do before doing any other actions. You still can use the other methods from firebase helpers if you initialize the app by using other methods from Firebase docs. 33 | 34 | ```sh 35 | const { firebaseHelper } = require('firebase-functions-helper'); 36 | const serviceAccount = require('./serviceAccountKey.json'); 37 | 38 | // Initialize Firebase App 39 | firebaseHelper.initializeApp(serviceAccount); 40 | ``` 41 | 42 | If you want to use this package in _TypeScript_. Please follow this instruction: 43 | 44 | ```sh 45 | import { firebaseHelper } from 'firebase-functions-helper'; 46 | import * as serviceAccount from './serviceAccountKey.json'; 47 | 48 | // Initialize Firebase App 49 | firebaseHelper.initializeApp(serviceAccount); 50 | 51 | ``` 52 | 53 | In order to import JSON, you need to create a **typings.d.ts** in your project 54 | 55 | ```sh 56 | // typings.d.ts 57 | declare module "*.json" { 58 | const value: any; 59 | export default value; 60 | } 61 | ``` 62 | 63 | ### [Working with Firebase](docs/firebase.md) 64 | 65 | ### [Working with Firestore](docs/firestore.md) 66 | 67 | ### [Working with Realtime Database](docs/realtime.md) 68 | 69 | ## Contributions 70 | 71 | This project is based on [firebase-functions-snippets](https://github.com/dalenguyen/firebase-functions-snippets), feel free to report bugs and make feature requests in the [Issue Tracker](https://github.com/dalenguyen/firebase-functions-helper/issues), fork and create pull requests! 72 | -------------------------------------------------------------------------------- /dist/firebase.js.map: -------------------------------------------------------------------------------- 1 | {"version":3,"file":"firebase.js","sourceRoot":"","sources":["../src/firebase.ts"],"names":[],"mappings":"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"} -------------------------------------------------------------------------------- /test/firebase.spec.ts: -------------------------------------------------------------------------------- 1 | import { expect } from 'chai'; 2 | import { firebaseHelper } from '../dist/index.js'; 3 | 4 | // const { firebaseHelper } = require('../dist'); 5 | 6 | describe('Test firebase functions:', async () => { 7 | const now = new Date().getTime(); 8 | const email = `user+${now}@dalenguyen.me`; 9 | const phone = `+1${now.toString().substr(3)}`; 10 | const userInfo = { 11 | email: email, 12 | emailVerified: false, 13 | phoneNumber: phone, 14 | password: 'secretPassword', 15 | displayName: 'Dale Nguyen', 16 | photoURL: 'http://www.example.com/12345678/photo.png', 17 | disabled: false, 18 | }; 19 | const newDisplayName = 'Yen Nguyen'; 20 | let userId; 21 | // const db = app.firestore; 22 | 23 | it('Create a new user', async () => { 24 | // Create a new user 25 | const createAUserResult = await firebaseHelper.createUser(userInfo); 26 | userId = createAUserResult.data.uid; 27 | expect(createAUserResult.status).to.equal(true); 28 | 29 | // User is already existed 30 | firebaseHelper.createUser(userInfo).then((res) => { 31 | expect(res.status).to.equal(false); 32 | }); 33 | }); 34 | 35 | it('Update a user', async () => { 36 | userInfo.displayName = newDisplayName; 37 | const updateAUserResult = await firebaseHelper.updateUser(userId, userInfo); 38 | expect(updateAUserResult.status).to.equal(true); 39 | expect(updateAUserResult.data.displayName).to.equal(newDisplayName); 40 | }); 41 | 42 | it('Get all users', async () => { 43 | const getAllUsersResult = await firebaseHelper.getAllUsers(10); 44 | expect(typeof getAllUsersResult).to.equal('object'); 45 | expect(getAllUsersResult.length).to.be.above(0); 46 | }); 47 | 48 | it('Get user by id', async () => { 49 | const getUserByIdResult = await firebaseHelper.getUserById(userId); 50 | expect(getUserByIdResult.uid).to.equal(userId); 51 | expect(getUserByIdResult.displayName).to.equal(newDisplayName); 52 | }); 53 | 54 | it('Get user by email', async () => { 55 | const getUserByEmailResult = await firebaseHelper.getUserByEmail(email); 56 | expect(getUserByEmailResult.uid).to.equal(userId); 57 | expect(getUserByEmailResult.displayName).to.equal(newDisplayName); 58 | }); 59 | 60 | it('Get user by phone', async () => { 61 | const getUserByPhoneResult = await firebaseHelper.getUserByPhone(phone); 62 | expect(getUserByPhoneResult.uid).to.equal(userId); 63 | expect(getUserByPhoneResult.displayName).to.equal(newDisplayName); 64 | }); 65 | 66 | it('Delete a user', async () => { 67 | const deconsteAUserResult = await firebaseHelper.deleteUser(userId); 68 | expect(deconsteAUserResult).to.equal(true); 69 | }); 70 | 71 | it('Auth function', () => { 72 | firebaseHelper 73 | .auth() 74 | .verifyIdToken('123') 75 | .catch(function (error) { 76 | // Handle error 77 | expect(error.message).to.contain('Decoding Firebase ID token failed'); 78 | }); 79 | }); 80 | }); 81 | -------------------------------------------------------------------------------- /test/realtime.spec.ts: -------------------------------------------------------------------------------- 1 | import { expect } from 'chai'; 2 | import { realtimeHelper } from '../dist/index.js'; 3 | import { app } from './appInitialize'; 4 | 5 | const db = app.realtime; 6 | 7 | describe('Test realtime functions:', () => { 8 | it('Get valid data', async () => { 9 | let data; 10 | try { 11 | data = await realtimeHelper.getData(db, 'users/1'); 12 | } catch (error) { 13 | console.log(error); 14 | } 15 | expect(typeof data).to.equal('object'); 16 | expect(Object.keys(data).length).to.greaterThan(0, `Data is empty!`); 17 | }); 18 | 19 | it('Get invalid data', async () => { 20 | let errorMessage; 21 | try { 22 | const data = await realtimeHelper.getData(db, 'invalid-path'); 23 | } catch (error) { 24 | errorMessage = error; 25 | } 26 | expect(errorMessage).to.equal( 27 | `Data can't be found!`, 28 | `Please use an invalid path!` 29 | ); 30 | }); 31 | 32 | it('Save new data and replace everything', async () => { 33 | const data = { 34 | td: { 35 | name: 'Toronto-Dominion Bank', 36 | }, 37 | rbc: { 38 | name: 'RBC Royal Bank', 39 | }, 40 | }; 41 | 42 | let result; 43 | try { 44 | result = await realtimeHelper.saveData(db, 'banks', data, true); 45 | } catch (error) { 46 | console.log(error); 47 | } 48 | 49 | expect(result.status, `${result.message}`).to.be.true; 50 | }); 51 | 52 | it('Save or replace only new data', async () => { 53 | const data = { 54 | td: { 55 | name: 'Toronto-Dominion Bank', 56 | }, 57 | nb: { 58 | name: 'National Bank', 59 | }, 60 | }; 61 | 62 | let result; 63 | try { 64 | result = await realtimeHelper.saveData(db, 'banks', data, false); 65 | } catch (error) { 66 | console.log(error); 67 | } 68 | 69 | expect(result.status, `${result.message}`).to.be.true; 70 | }); 71 | 72 | it('Update saved data', async () => { 73 | const data = { 74 | 'td/location': 'Toronto', 75 | 'rbc/location': 'Toronto', 76 | }; 77 | 78 | let result1; 79 | try { 80 | result1 = await realtimeHelper.updateData(db, 'banks', data); 81 | } catch (error) { 82 | console.log(error); 83 | } 84 | 85 | expect(result1.status, `${result1.message}`).to.be.true; 86 | 87 | let result2; 88 | try { 89 | result2 = await realtimeHelper.getData(db, 'banks/td/location'); 90 | } catch (error) { 91 | console.log(error); 92 | } 93 | 94 | expect(result2).to.equal('Toronto', `Data cannot be updated`); 95 | }); 96 | 97 | it('Delete data', async () => { 98 | let result; 99 | try { 100 | result = await realtimeHelper.deleteData(db, 'banks'); 101 | } catch (error) { 102 | console.log(error); 103 | } 104 | 105 | expect(result.status, `${result.message}`).to.be.true; 106 | }); 107 | }); 108 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | # Change log 2 | 3 | > **Tags:** 4 | > 5 | > - :boom: [Breaking Change] 6 | > - :eyeglasses: [Spec Compliancy] 7 | > - :rocket: [New Feature] 8 | > - :bug: [Bug Fix] 9 | > - :memo: [Documentation] 10 | > - :nail_care: [Polish] 11 | 12 | --- 13 | 14 | ## [0.12.0] - 2021-05-14 15 | 16 | #### - :nail_care: [Polish] 17 | 18 | - Update packages & document 19 | 20 | ## [0.11.0] - 2021-03-10 21 | 22 | #### - :nail_care: [Polish] 23 | 24 | - Update packages 25 | 26 | ## [0.10.0] - 2020-11-21 27 | 28 | #### - :boom: [Breaking Change] 29 | 30 | - Utilized backup & restore from (firestore-export-import)[https://www.npmjs.com/package/firestore-export-import] 31 | - Import separate features rather entire package (please read the docs & test files) 32 | 33 | ## [0.9.0] - 2020-11-21 34 | 35 | #### - :nail_care: [Polish] 36 | 37 | - Update packages 38 | 39 | ## [0.8.0] - 2020-08-02 40 | 41 | #### :rocket: New Feature 42 | 43 | - Query data from firestore with pagination 44 | 45 | #### - :nail_care: [Polish] 46 | 47 | - Update packages 48 | 49 | ## [0.7.5] - 2019-1-2 50 | 51 | #### - :nail_care: [Polish] 52 | 53 | - Update packages 54 | 55 | ## [0.7.4] - 2019-10-05 56 | 57 | #### - :nail_care: [Polish] 58 | 59 | - Update packages 60 | 61 | ## [0.7.3] - 2019-7-20 62 | 63 | #### :rocket: New Feature 64 | 65 | - Added support for auth() #20 66 | - Added declarative types 67 | 68 | ## [0.7.2] - 2019-7-20 69 | 70 | #### - :nail_care: [Polish] 71 | 72 | - Update packages 73 | 74 | ## [0.7.1] - 2019-5-31 75 | 76 | #### - :nail_care: [Polish] 77 | 78 | - Update packages and minify js files 79 | 80 | #### - :bug: [Bug Fix] 81 | 82 | - Fixed Error in Backup method to get subCollections #16 83 | - Fixed Wrong status when deleting document has error #17 84 | 85 | ## [0.7.0] - 2019-3-31 86 | 87 | #### :rocket: New Feature 88 | 89 | - Support Realtime Database features 90 | 91 | ## [0.6.5] - 2019-3-30 92 | 93 | #### :memo: Documentation 94 | 95 | - Updated changelog.md 96 | 97 | ## [0.6.4] - 2019-3-2 98 | 99 | #### :boom: Breaking Change 100 | 101 | - Suport multi parameters for query #11 102 | 103 | ## [0.6.3] - 2019-3-2 104 | 105 | #### :rocket: New Feature 106 | 107 | - Added orderBy support for querying data #6 108 | 109 | ## [0.5.9] - 2018-7-31 110 | 111 | #### :nail_care: Polish 112 | 113 | - Update firebase-admin version and firestore settings 114 | 115 | ## [0.5.8] - 2018-6-27 116 | 117 | #### :memo: Documentation 118 | 119 | - Edit documents 120 | 121 | #### :nail_care: Polish 122 | 123 | - Change query results to an object 124 | 125 | ## [0.5.7] - 2018-5-31 126 | 127 | #### :rocket: New Feature 128 | 129 | - Add get users feature 130 | - Delete users in bulk feature 131 | 132 | ## [0.5.6] - 2018-5-31 133 | 134 | #### :rocket: New Feature 135 | 136 | - Add firebase functions such as create user, delete user, update user... 137 | - Restructure firebase features 138 | 139 | ## [0.4.6] - 2018-5-30 140 | 141 | #### :nail_care: Polish 142 | 143 | - Improve document exists method 144 | 145 | ## [0.4.4] - 2018-5-25 146 | 147 | #### :nail_care: Polish 148 | 149 | - Restructure firestore functions 150 | 151 | ## [0.4.2] - 2018-5-17 152 | 153 | #### :rocket: New Feature 154 | 155 | - Add firestore query feature 156 | -------------------------------------------------------------------------------- /docs/firebase.md: -------------------------------------------------------------------------------- 1 | # Firebase | Firebase Functions Helper 2 | 3 | In this part, you will have the ability to initialize your Firebase App and work on other firebase stuff. 4 | 5 | ## 1. Initialize Firebase App 6 | 7 | This should be the first step before you do anything else on your project 8 | 9 | ```sh 10 | const { firebaseHelper } = require('firebase-functions-helper'); 11 | const serviceAccount = require('./serviceAccountKey.json'); 12 | 13 | // Initialize Firebase App 14 | firebaseHelper.initializeApp(serviceAccount, databaseURL); 15 | ``` 16 | 17 | ## 2. Get user though userId 18 | 19 | You will find this user Id from **Authentication** tab in Firebase Console. This will return an object of Firebase user. 20 | 21 | ```sh 22 | firebaseHelper 23 | .getUserbyId('user-id') 24 | .then(user => console.log(user)); 25 | ``` 26 | 27 | ## 3. Get user through email 28 | 29 | This will return an object of Firebase user. 30 | 31 | ```sh 32 | firebaseHelper 33 | .getUserbyEmail('email') 34 | .then(user => console.log(user)); 35 | ``` 36 | 37 | ## 4. Get user through phone number 38 | 39 | This will also return an object of Firebase user. 40 | 41 | ```sh 42 | firebaseHelper 43 | .getUserbyPhone('phone-number') 44 | .then(user => console.log(user)); 45 | ``` 46 | 47 | ## 5. Delete a user by user id 48 | 49 | ```sh 50 | firebaseHelper 51 | .deleteUser(userId) 52 | .then(res => console.log(res)); 53 | ``` 54 | 55 | This will return a Promise. 56 | 57 | ## 6. Delete users through an Array of User Ids 58 | 59 | ```sh 60 | let userList = ['userid-1', 'userid-2'] 61 | firebaseHelper 62 | .deleteUsers(userList); 63 | ``` 64 | 65 | ## 7. Create a new Firebase user 66 | 67 | ```sh 68 | let userInfo = { 69 | email: "user@dalenguyen.me", 70 | emailVerified: false, 71 | phoneNumber: "+11234567890", 72 | password: "secretPassword", 73 | displayName: "Dale Nguyen", 74 | photoURL: "http://www.example.com/12345678/photo.png", 75 | disabled: false 76 | }; 77 | 78 | firebaseHelper 79 | .createUser(userInfo) 80 | .then(res => console.log(res)); 81 | ``` 82 | 83 | This will return a Promise: 84 | 85 | ```sh 86 | { 87 | status: true/false 88 | data: userInfo/Error message 89 | } 90 | ``` 91 | 92 | ## 8. Update a user though user Id 93 | 94 | ```sh 95 | let userInfo = { 96 | email: "test@dalenguyen.me", 97 | emailVerified: false, 98 | phoneNumber: "+11234567899", 99 | password: "secretPassword", 100 | displayName: "Dale Nguyen", 101 | photoURL: "http://www.example.com/12345678/photo.png", 102 | disabled: false 103 | }; 104 | 105 | firebaseHelper 106 | .updateUser('user-id', userInfo); 107 | ``` 108 | 109 | ## 9. Get a list of users 110 | 111 | This will return an array of users. If you don't pass the max-number-of-user, the default is 1000. 112 | 113 | ```sh 114 | firebaseHelper 115 | .getAllUsers('max-number-of-users - optional') 116 | .then(users => console.log(users)); 117 | ``` 118 | 119 | From this, you can delete users in bulk by combining two methods. 120 | 121 | ```sh 122 | // Get all users 123 | firebaseHelper 124 | .getAllUsers('max-number-of-users - optional') 125 | .then(users => { 126 | users.map(user => { 127 | firebaseHelper 128 | .deleteUsers([user.uid]); 129 | }) 130 | }) 131 | ``` 132 | -------------------------------------------------------------------------------- /dist/firestore.js: -------------------------------------------------------------------------------- 1 | "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.FirestoreHelper=void 0;const firestore_export_import_1=require("firestore-export-import");class FirestoreHelper{createDocumentWithID(db,collectionName,docId,data){return db.collection(collectionName).doc(docId).set(data).then(()=>true).catch(function(error){return false;});} 2 | createNewDocument(db,collectionName,data){return db.collection(collectionName).add(data).then(function(docRef){return docRef;}).catch(function(error){return error;});} 3 | updateDocument(db,collectionName,docId,data){return db.collection(collectionName).doc(docId).update(data).then(()=>true).catch((err)=>err);} 4 | deleteDocument(db,collectionName,docId){return db.collection(collectionName).doc(docId).delete().then(()=>{return{status:true,message:docId+' successfully deleted!'};}).catch((error)=>{return{status:false,message:error};});} 5 | deleteDocumentFromSubcollection(db,collectionName,docId,collectionNameTwo,docIdTwo){db.collection(collectionName).doc(docId).collection(collectionNameTwo).doc(docIdTwo).delete().then(()=>{console.log(docIdTwo+' successfully deleted!');}).catch((error)=>{console.error('Error removing document: ',error);});} 6 | checkDocumentExists(db,collectionName,docId){const dbRef=db.collection(collectionName).doc(docId);return dbRef.get().then((doc)=>{if(!doc.exists){return{exists:false,};} 7 | else{return{exists:true,data:doc.data(),};}}).catch((err)=>{console.log('Error getting document',err);});} 8 | getDocument(db,collectionName,documentId){const docRef=db.collection(collectionName).doc(documentId);return docRef.get().then(function(doc){if(doc.exists){return doc.data();} 9 | else{console.log('No such document!');return false;}}).catch(function(error){console.log('Error getting document:',error);});} 10 | queryData(db,collectionName,queryArray,orderBy=null){return new Promise((resolve,reject)=>{const dataRef=db.collection(collectionName);let queryRef=dataRef;queryArray.forEach((query)=>{queryRef=queryRef.where(query[0],query[1],query[2]);});if(orderBy!==null){if(typeof orderBy[1]===undefined){orderBy[1]='asc';} 11 | queryRef=queryRef.orderBy(orderBy[0],orderBy[1]);} 12 | const results={};queryRef.get().then((snapshot)=>{snapshot.forEach((doc)=>{results[doc.id]=doc.data();});if(Object.keys(results).length>0){resolve(results);} 13 | else{resolve('No such document!');}}).catch((err)=>{reject(false);console.log('Error getting documents',err);});});} 14 | queryDataWithPagiation(dbp,collectionName,queryArray,orderBy,page,size){return new Promise((resolve,reject)=>{const dataRef=dbp.collection(collectionName);const limit=size||10;const offset=(page-1)*limit;console.log('Limit is '+limit+' offset is: '+offset);let queryRef=dataRef;queryArray.forEach((query)=>{queryRef=queryRef.where(query[0],query[1],query[2]);});if(orderBy!==null){if(typeof orderBy[1]===undefined){orderBy[1]='asc';} 15 | queryRef=queryRef.orderBy(orderBy[0],orderBy[1]);} 16 | const results={};queryRef.limit(limit).offset(offset).get().then((snapshot)=>{snapshot.forEach((doc)=>{results[doc.id]=doc.data();});if(Object.keys(results).length>0){resolve(results);} 17 | else{resolve('No such document!');}}).catch((err)=>{reject(false);console.log('Error getting documents',err);});});} 18 | backup(collectionName){return firestore_export_import_1.backup(collectionName);} 19 | addSubCollection(db,key,subData,collectionName,subCollection){return new Promise((resolve,reject)=>{db.collection(collectionName).doc(key).collection(subCollection).get().then((snapshot)=>{snapshot.forEach((subDoc)=>{subData[subDoc.id]=subDoc.data();resolve('Added data');});}).catch((error)=>{reject(false);console.log(error);});});} 20 | restore(fileName,options){return firestore_export_import_1.restore(fileName,options);}} 21 | exports.FirestoreHelper=FirestoreHelper; -------------------------------------------------------------------------------- /src/realtime.ts: -------------------------------------------------------------------------------- 1 | export class RealtimeHelper { 2 | /** 3 | * Get realtime database from path 4 | * 5 | * @param {*} db 6 | * @param {string} path 7 | * @returns {Promise} 8 | * @memberof RealtimeHelper 9 | */ 10 | getData(db: any, path: string): Promise { 11 | const ref = db.ref(path); 12 | return new Promise((resolve, reject) => { 13 | ref.once('value', function(snapshot) { 14 | const data = snapshot.val(); 15 | if (data) { 16 | if (data[0] === undefined) { // remove first empty item 17 | data.splice && data.splice(0, 1); 18 | } 19 | resolve(data); 20 | } else { 21 | reject('Data can\'t be found!') 22 | } 23 | }); 24 | }) 25 | } 26 | 27 | /** 28 | * Save data to realtime database 29 | * 30 | * @param {*} db 31 | * @param {string} path 32 | * @param {Object} data 33 | * @param {boolean} [remove=true] 34 | * @returns {Promise} 35 | * @memberof RealtimeHelper 36 | */ 37 | saveData(db: any, path: string, data: Object, remove: boolean = true): Promise { 38 | const ref = db.ref(path); 39 | return new Promise((resolve, reject) => { 40 | if (remove) { 41 | ref.set(data, (error) => { 42 | if (error) { 43 | reject({status: false, message: error}); 44 | } else { 45 | resolve({status: true, message: 'Data saved succesfully!'}) 46 | } 47 | }); 48 | } else { // replace entire data 49 | const errorList = []; 50 | for (const key in data) { 51 | if (data.hasOwnProperty(key)) { 52 | ref.child(key).set(data[key], error => { 53 | errorList.push(error); 54 | }); 55 | } 56 | } 57 | 58 | if (errorList.length > 0) { 59 | reject({status: false, message: errorList}); 60 | } else { 61 | resolve({status: true, message: 'Data saved succesfully!'}) 62 | } 63 | } 64 | }) 65 | } 66 | 67 | /** 68 | * Update existing data 69 | * 70 | * @param {*} db 71 | * @param {string} path 72 | * @param {Object} data 73 | * @returns {Promise} 74 | * @memberof RealtimeHelper 75 | */ 76 | updateData(db: any, path: string, data: Object): Promise { 77 | const ref = db.ref(path); 78 | return new Promise((resolve, reject) => { 79 | ref.update(data, error => { 80 | if (error) { 81 | reject({status: false, message: error}); 82 | } else { 83 | resolve({status: true, message: 'Data updated succesfully!'}) 84 | } 85 | }); 86 | }) 87 | } 88 | 89 | /** 90 | * Delete data 91 | * 92 | * @param {*} db 93 | * @param {string} path 94 | * @returns {Promise} 95 | * @memberof RealtimeHelper 96 | */ 97 | deleteData(db: any, path: string): Promise { 98 | const ref = db.ref(path); 99 | return new Promise((resolve, reject) => { 100 | ref.set(null, (error) => { 101 | if (error) { 102 | reject({status: false, message: error}); 103 | } else { 104 | resolve({status: true, message: 'Data deleted succesfully!'}) 105 | } 106 | }); 107 | }) 108 | } 109 | } -------------------------------------------------------------------------------- /dist/firestore.d.ts: -------------------------------------------------------------------------------- 1 | import { IImportOptions } from 'firestore-export-import/dist/helper'; 2 | export declare class FirestoreHelper { 3 | /** 4 | *Create a document with id in firestore 5 | * 6 | * @param {*} db 7 | * @param {string} collectionName 8 | * @param {string} docId 9 | * @param {Object} data 10 | * @returns {Promise} 11 | * @memberof FirestoreHelper 12 | */ 13 | createDocumentWithID(db: any, collectionName: string, docId: string, data: Object): Promise; 14 | /** 15 | * Create a document without an ID 16 | * 17 | * @param {*} db 18 | * @param {string} collectionName 19 | * @param {Object} data 20 | * @returns 21 | * @memberof FirestoreHelper 22 | */ 23 | createNewDocument(db: any, collectionName: string, data: Object): Promise; 24 | /** 25 | * Create a document with id in firestore 26 | * 27 | * @param {any} db 28 | * @param {any} collectionName 29 | * @param {any} docID 30 | * @param {any} collectionNameTwo 31 | * @param {any} docIDTwo 32 | * @param {any} data 33 | * @returns 34 | */ 35 | /** 36 | * Update a document 37 | * 38 | * @param {*} db 39 | * @param {string} collectionName 40 | * @param {string} docId 41 | * @param {Object} data 42 | * @returns {Promise} 43 | * @memberof FirestoreHelper 44 | */ 45 | updateDocument(db: any, collectionName: string, docId: string, data: Object): Promise; 46 | /** 47 | * Delete a document 48 | * 49 | * @param {*} db 50 | * @param {string} collectionName 51 | * @param {string} docId 52 | * @returns {Promise} 53 | * @memberof FirestoreHelper 54 | */ 55 | deleteDocument(db: any, collectionName: string, docId: string): Promise; 56 | /** 57 | * Delete a document from Sub Collection 58 | * 59 | * @param {any} db 60 | * @param {any} collectionName 61 | * @param {any} docId 62 | * @param {any} collectionNameTwo 63 | * @param {any} docIdTwo 64 | */ 65 | deleteDocumentFromSubcollection(db: any, collectionName: string, docId: string, collectionNameTwo: string, docIdTwo: string): void; 66 | /** 67 | * Check where a document exists or not 68 | * 69 | * @param {any} db 70 | * @param {string} collectionName 71 | * @param {string} docId 72 | * @returns {Promise} 73 | * @memberof FirestoreHelper 74 | */ 75 | checkDocumentExists(db: any, collectionName: string, docId: string): Promise; 76 | /** 77 | * Get a document from document Id 78 | * 79 | * @param {any} db 80 | * @param {string} collectionName 81 | * @param {string} documentId 82 | * @returns {Promise} 83 | * @memberof FirestoreHelper 84 | */ 85 | getDocument(db: any, collectionName: string, documentId: string): Promise; 86 | /** 87 | * Query data from Firestore 88 | * 89 | * @param {*} db 90 | * @param {string} collectionName 91 | * @param {Array} queryArray 92 | * @param {Array} orderBy 93 | * @returns {Promise} 94 | * @memberof FirestoreHelper 95 | */ 96 | queryData(db: any, collectionName: string, queryArray: Array, orderBy?: Array): Promise; 97 | /** 98 | * Query data from Firestore with Pagination. 99 | * 100 | * @param {*} db 101 | * @param {string} collectionName 102 | * @param {Array} queryArray 103 | * @param {Array} orderBy 104 | * @param {number} page 105 | * @param {number} size 106 | * @returns {Promise} 107 | * @memberof FirestoreHelper 108 | */ 109 | queryDataWithPagiation(dbp: any, collectionName: string, queryArray: Array, orderBy: Array, page: number, size: number): Promise; 110 | /** 111 | * Backup data from Firestore 112 | * 113 | * @param {string} collectionName 114 | * @return {json} 115 | */ 116 | backup(collectionName: string): Promise; 117 | /** 118 | * Add sub collection to data Object if possible 119 | * 120 | * @param {any} db 121 | * @param {any} key 122 | * @param {any} subData 123 | * @param {any} collectionName 124 | * @param {any} subCollection 125 | * @returns 126 | */ 127 | addSubCollection(db: any, key: string, subData: Object, collectionName: string, subCollection: string): Promise; 128 | /** 129 | *Restore data to Firestore 130 | * 131 | * @param {*} fileName 132 | * @returns {Promise} 133 | * @memberof FirestoreHelper 134 | */ 135 | restore(fileName: any, options?: IImportOptions): Promise; 136 | } 137 | -------------------------------------------------------------------------------- /src/firebase.ts: -------------------------------------------------------------------------------- 1 | import * as admin from 'firebase-admin'; 2 | 3 | interface UserRecord { 4 | status: boolean; 5 | data: admin.auth.UserRecord; 6 | } 7 | 8 | export class FirebaseHelper { 9 | /** 10 | * Initialize Firebase App 11 | * 12 | * @param {admin.AppOptions} serviceAccount 13 | */ 14 | initializeApp(serviceAccount: admin.AppOptions) { 15 | admin.initializeApp({ 16 | credential: admin.credential.cert(serviceAccount), 17 | databaseURL: serviceAccount.databaseURL, 18 | }); 19 | return { firestore: admin.firestore(), realtime: admin.database() }; 20 | } 21 | 22 | /** 23 | * Get User Info though UserId 24 | * 25 | * @param {string} userId 26 | * @returns {Promise} 27 | */ 28 | getUserById(userId: string): Promise { 29 | return admin 30 | .auth() 31 | .getUser(userId) 32 | .then((user) => user) 33 | .catch((error) => console.log(error)); 34 | } 35 | 36 | /** 37 | * Get User Info though email 38 | * 39 | * @param {string} email 40 | * @returns {Promise} 41 | * @memberof FirebaseHelper 42 | */ 43 | getUserByEmail(email: string): Promise { 44 | return admin 45 | .auth() 46 | .getUserByEmail(email) 47 | .then((user) => user) 48 | .catch((error) => console.log(error)); 49 | } 50 | 51 | /** 52 | * Get User Info though phone number 53 | * 54 | * @param {string} phone 55 | * @returns {Promise} 56 | * @memberof FirebaseHelper 57 | */ 58 | getUserByPhone(phone: string): Promise { 59 | return admin 60 | .auth() 61 | .getUserByPhoneNumber(phone) 62 | .then((user) => user) 63 | .catch((error) => console.log(error)); 64 | } 65 | 66 | /** 67 | * Delete a user 68 | * 69 | * @param {string} userId 70 | * @memberof FirebaseHelper 71 | */ 72 | deleteUser(userId: string): Promise { 73 | return new Promise((resolve) => { 74 | admin 75 | .auth() 76 | .deleteUser(userId) 77 | .then(() => { 78 | resolve(true); 79 | }) 80 | .catch((error) => { 81 | console.log(error); 82 | resolve(false); 83 | }); 84 | }); 85 | } 86 | 87 | /** 88 | * Delete user from an Array of User Ids 89 | * 90 | * @param {Array} userIds 91 | * @memberof FirebaseHelper 92 | */ 93 | deleteUsers(userIds: Array): void { 94 | userIds.map((userId) => { 95 | this.deleteUser(userId) 96 | .then(() => { 97 | console.log('Successfully deleted user: ', userId); 98 | }) 99 | .catch((error) => console.log(error)); 100 | }); 101 | } 102 | 103 | /** 104 | * Create a new user 105 | * 106 | * @param {Object} userInfo 107 | * @returns {Promise} 108 | * @memberof FirebaseHelper 109 | */ 110 | createUser(userInfo: Object): Promise { 111 | return new Promise((resolve) => { 112 | admin 113 | .auth() 114 | .createUser(userInfo) 115 | .then((userRecord) => { 116 | resolve({ 117 | status: true, 118 | data: userRecord, 119 | }); 120 | }) 121 | .catch((error) => { 122 | resolve({ 123 | status: false, 124 | data: error.message, 125 | }); 126 | }); 127 | }); 128 | } 129 | 130 | /** 131 | * Update user Info though userId 132 | * 133 | * @param {string} userId 134 | * @param {Object} userInfo 135 | * @memberof FirebaseHelper 136 | */ 137 | updateUser(userId: string, userInfo: Object): Promise { 138 | return new Promise((resolve) => { 139 | admin 140 | .auth() 141 | .updateUser(userId, userInfo) 142 | .then((userRecord) => { 143 | resolve({ 144 | status: true, 145 | data: userRecord, 146 | }); 147 | }) 148 | .catch((error) => { 149 | resolve({ 150 | status: false, 151 | data: error.message, 152 | }); 153 | }); 154 | }); 155 | } 156 | 157 | /** 158 | * Get a list of users 159 | * 160 | * @param {number} [maxResults=1000] 161 | * @returns {Promise} 162 | * @memberof FirebaseHelper 163 | */ 164 | getAllUsers(maxResults: number = 1000): Promise { 165 | return admin 166 | .auth() 167 | .listUsers(maxResults) 168 | .then((listUsersResult) => listUsersResult.users) 169 | .catch((error) => { 170 | console.log('Error listing users:', error); 171 | }); 172 | } 173 | 174 | /** 175 | * Auth function from Firebase Admin SDK 176 | */ 177 | auth(): admin.auth.Auth { 178 | return admin.auth(); 179 | } 180 | } 181 | -------------------------------------------------------------------------------- /tslint.json: -------------------------------------------------------------------------------- 1 | { 2 | "rules": { 3 | // -- Strict errors -- 4 | // These lint rules are likely always a good idea. 5 | 6 | // Force function overloads to be declared together. This ensures readers understand APIs. 7 | "adjacent-overload-signatures": true, 8 | 9 | // Do not allow the subtle/obscure comma operator. 10 | "ban-comma-operator": true, 11 | 12 | // Do not allow internal modules or namespaces . These are deprecated in favor of ES6 modules. 13 | "no-namespace": true, 14 | 15 | // Do not allow parameters to be reassigned. To avoid bugs, developers should instead assign new values to new vars. 16 | "no-parameter-reassignment": true, 17 | 18 | // Force the use of ES6-style imports instead of /// imports. 19 | "no-reference": true, 20 | 21 | // Do not allow type assertions that do nothing. This is a big warning that the developer may not understand the 22 | // code currently being edited (they may be incorrectly handling a different type case that does not exist). 23 | "no-unnecessary-type-assertion": true, 24 | 25 | // Disallow nonsensical label usage. 26 | "label-position": true, 27 | 28 | // Disallows the (often typo) syntax if (var1 = var2). Replace with if (var2) { var1 = var2 }. 29 | "no-conditional-assignment": true, 30 | 31 | // Disallows constructors for primitive types (e.g. new Number('123'), though Number('123') is still allowed). 32 | "no-construct": true, 33 | 34 | // Do not allow super() to be called twice in a constructor. 35 | "no-duplicate-super": true, 36 | 37 | // Do not allow the same case to appear more than once in a switch block. 38 | "no-duplicate-switch-case": true, 39 | 40 | // Do not allow a variable to be declared more than once in the same block. Consider function parameters in this 41 | // rule. 42 | "no-duplicate-variable": [true, "check-parameters"], 43 | 44 | // Disallows a variable definition in an inner scope from shadowing a variable in an outer scope. Developers should 45 | // instead use a separate variable name. 46 | "no-shadowed-variable": true, 47 | 48 | // Empty blocks are almost never needed. Allow the one general exception: empty catch blocks. 49 | "no-empty": [true, "allow-empty-catch"], 50 | 51 | // Functions must either be handled directly (e.g. with a catch() handler) or returned to another function. 52 | // This is a major source of errors in Cloud Functions and the team strongly recommends leaving this rule on. 53 | "no-floating-promises": true, 54 | 55 | // Do not allow any imports for modules that are not in package.json. These will almost certainly fail when 56 | // deployed. 57 | "no-implicit-dependencies": true, 58 | 59 | // The 'this' keyword can only be used inside of classes. 60 | "no-invalid-this": true, 61 | 62 | // Do not allow strings to be thrown because they will not include stack traces. Throw Errors instead. 63 | "no-string-throw": true, 64 | 65 | // Disallow control flow statements, such as return, continue, break, and throw in finally blocks. 66 | "no-unsafe-finally": true, 67 | 68 | // Do not allow variables to be used before they are declared. 69 | "no-use-before-declare": true, 70 | 71 | // Expressions must always return a value. Avoids common errors like const myValue = functionReturningVoid(); 72 | "no-void-expression": [true, "ignore-arrow-function-shorthand"], 73 | 74 | // Disallow duplicate imports in the same file. 75 | "no-duplicate-imports": true, 76 | 77 | 78 | // -- Strong Warnings -- 79 | // These rules should almost never be needed, but may be included due to legacy code. 80 | // They are left as a warning to avoid frustration with blocked deploys when the developer 81 | // understand the warning and wants to deploy anyway. 82 | 83 | // Warn when an empty interface is defined. These are generally not useful. 84 | "no-empty-interface": {"severity": "warning"}, 85 | 86 | // Warn when an import will have side effects. 87 | "no-import-side-effect": {"severity": "warning"}, 88 | 89 | // Warn when variables are defined with var. Var has subtle meaning that can lead to bugs. Strongly prefer const for 90 | // most values and let for values that will change. 91 | "no-var-keyword": {"severity": "warning"}, 92 | 93 | // Prefer === and !== over == and !=. The latter operators support overloads that are often accidental. 94 | "triple-equals": {"severity": "warning"}, 95 | 96 | // Warn when using deprecated APIs. 97 | "deprecation": {"severity": "warning"}, 98 | 99 | // -- Light Warnigns -- 100 | // These rules are intended to help developers use better style. Simpler code has fewer bugs. These would be "info" 101 | // if TSLint supported such a level. 102 | 103 | // prefer for( ... of ... ) to an index loop when the index is only used to fetch an object from an array. 104 | // (Even better: check out utils like .map if transforming an array!) 105 | "prefer-for-of": {"severity": "warning"}, 106 | 107 | // Warns if function overloads could be unified into a single function with optional or rest parameters. 108 | "unified-signatures": {"severity": "warning"}, 109 | 110 | // Prefer const for values that will not change. This better documents code. 111 | "prefer-const": {"severity": "warning"}, 112 | 113 | // Multi-line object liiterals and function calls should have a trailing comma. This helps avoid merge conflicts. 114 | "trailing-comma": {"severity": "warning"} 115 | }, 116 | 117 | "defaultSeverity": "error" 118 | } 119 | -------------------------------------------------------------------------------- /docs/firestore.md: -------------------------------------------------------------------------------- 1 | # Firestore | Firebase Functions Helper 2 | 3 | Before starting with Firestore, we have to initialize Firebase App and get Firestore DB. 4 | 5 | ```sh 6 | const {firebaseHelper, firestoreHelper} = require('firebase-functions-helper'); 7 | const serviceAccount = require('./serviceAccountKey.json'); 8 | 9 | // Initialize Firebase App 10 | const app = firebaseHelper.initializeApp(serviceAccount, databaseURL); 11 | 12 | // Get Firestore DB 13 | const db = app.firestore; 14 | db.settings({ timestampsInSnapshots: true }); 15 | ``` 16 | 17 | ## 1. Get a Document 18 | 19 | The result will be a Promise that returns _content of a document_ or _false_ if document doesn't exist. 20 | 21 | ```sh 22 | firestoreHelper 23 | .getDocument(db, 'collection-name', 'document-id') 24 | .then(doc => console.log(doc)); 25 | ``` 26 | 27 | ## 2. Get Firestore Collection with Sub Collection 28 | 29 | Backup feature use the package (firestore-export-import)[https://www.npmjs.com/package/firestore-export-import] 30 | 31 | ```sh 32 | // Start exporting your collection 33 | firestoreHelper 34 | .backup('collection-name') 35 | .then(data => console.log(JSON.stringify(data))) 36 | ``` 37 | 38 | With this feature you can get and loop through all of your documents from a collection 39 | 40 | ```sh 41 | firestoreHelper 42 | .backup('collection-name'); 43 | .then(data => { 44 | let docs = data['collection-name']; 45 | for (const key in docs) { 46 | if (docs.hasOwnProperty(key)) { 47 | console.log('Doc id: ', key); 48 | console.log('Document data: ', docs[key]) 49 | } 50 | } 51 | }) 52 | ``` 53 | 54 | ## 3. Import data to firestore 55 | 56 | This code will help you to import data from a JSON file to firestore. 57 | 58 | Restore feature use the package (firestore-export-import)[https://www.npmjs.com/package/firestore-export-import] 59 | 60 | ```sh 61 | // Start exporting your data 62 | firestoreHelper.restore('your-file-path.json'); 63 | ``` 64 | 65 | This will return a Promise<{status: boolean, message: string}>. 66 | 67 | The JSON is formated as below. The collection name is **test**. **first-key** and **second-key** are document ids. 68 | 69 | ```sh 70 | { 71 | "test" : { 72 | "first-key" : { 73 | "email" : "dungnq@itbox4vn.com", 74 | "website" : "dalenguyen.me", 75 | "custom" : { 76 | "firstName" : "Dale", 77 | "lastName" : "Nguyen" 78 | } 79 | }, 80 | "second-key" : { 81 | "email" : "test@dalenguyen.me", 82 | "website" : "google.com", 83 | "custom" : { 84 | "firstName" : "Harry", 85 | "lastName" : "Potter" 86 | } 87 | } 88 | } 89 | } 90 | ``` 91 | 92 | ## 4. Create a document with id in firestore 93 | 94 | ```sh 95 | firestoreHelper 96 | .createDocumentWithID(db, 'collection-name', 'document-id', data); 97 | ``` 98 | 99 | This will return a Promise. 100 | 101 | ## 5. Create a new document without an ID 102 | 103 | ```sh 104 | firestoreHelper 105 | .createNewDocument(db, 'collection-name', data) 106 | .then(docRef => console.log(docRef.id)); 107 | ``` 108 | 109 | This will return a Promise. You can get the document id from that. 110 | 111 | ## 6. Update a document 112 | 113 | This action will only update the current key inside the document, if the data doesn't exist, it will create a new one. However, it will not create a new document if the document doesn't exist in the first place. 114 | 115 | ```sh 116 | let data = {key: value}; 117 | firestoreHelper 118 | .updateDocument(db, 'collection-name', 'document-id', data); 119 | ``` 120 | 121 | This will return a Promise. True if success and will throw an error if fail. 122 | 123 | ## 7. Delete a document 124 | 125 | ```sh 126 | firestoreHelper 127 | .deleteDocument(db, 'collection-name', 'document-id'); 128 | ``` 129 | 130 | This will return a Promise<{status: bolean, message: string}> 131 | 132 | ## 8. Check whether a document exists 133 | 134 | This will return a Promise and the document data if possible 135 | 136 | ```sh 137 | firestoreHelper 138 | .checkDocumentExists(db, 'collection-name', 'document-id') 139 | .then(result => { 140 | // Boolean value of the result 141 | console.log( result.exists ); // will return true or false 142 | // If the document exist, you can get the document content 143 | console.log( JSON.stringify(result.data) ); // return an object of or document 144 | }); 145 | ``` 146 | 147 | ## 9. Query data from firestore 148 | 149 | This will return a Promise of documents. 150 | 151 | The orderBy parameter is OPTIONAL. 152 | 153 | ```sh 154 | // Search for data ( <, <=, ==, >, or >= ) 155 | const queryArray = [['website', '==', 'dalenguyen.me'], ['email', '==', 'dungnq@itbox4vn.com']]; 156 | const orderBy = ['email', 'desc']; 157 | 158 | firestoreHelper 159 | .queryData(db, 'collection-name', queryArray, orderby) 160 | .then(docs => console.log(docs)); 161 | ``` 162 | 163 | ## 10. Query data from firestore with pagination. 164 | 165 | This will return a Promise of documents. 166 | 167 | The orderBy parameter is OPTIONAL. 168 | 169 | ```sh 170 | // Search for data ( <, <=, ==, >, or >= ) 171 | const queryArray = [['website', '==', 'dalenguyen.me'], ['email', '==', 'dungnq@itbox4vn.com']]; 172 | const orderBy = ['email', 'desc']; 173 | const size = 10; 174 | const page = 1; 175 | 176 | firestoreHelper 177 | .queryDataWithPagiation(db, 'collection-name', queryArray, orderby, page, size) 178 | .then(docs => console.log(docs)); 179 | ``` 180 | 181 | ## 11. Next Steps 182 | 183 | If you want to add more features, please make a request in the [Issue Tracker](https://github.com/dalenguyen/firebase-functions-helper/issues) 184 | -------------------------------------------------------------------------------- /dist/firestore.js.map: -------------------------------------------------------------------------------- 1 | {"version":3,"file":"firestore.js","sourceRoot":"","sources":["../src/firestore.ts"],"names":[],"mappings":"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"} -------------------------------------------------------------------------------- /test/firestore.spec.ts: -------------------------------------------------------------------------------- 1 | import { expect } from 'chai'; 2 | import { firestoreHelper } from '../dist/index'; 3 | import { app } from './appInitialize'; 4 | 5 | // const { firestoreHelper } = require('../dist/index'); 6 | 7 | const db = app.firestore; 8 | db.settings({ timestampsInSnapshots: true }); 9 | 10 | describe('Test firestore functions:', () => { 11 | const collectionName = 'test'; 12 | it('Restore', async () => { 13 | try { 14 | const result = await firestoreHelper.restore( 15 | 'test/import-to-firestore.json' 16 | ); 17 | expect(result.status).to.equal(true); 18 | } catch (error) { 19 | console.log(error); 20 | } 21 | }); 22 | it('Backup Success', async () => { 23 | let result; 24 | try { 25 | result = await firestoreHelper.backup(collectionName); 26 | } catch (error) { 27 | console.log(error); 28 | } 29 | expect(result).to.have.property(collectionName); 30 | 31 | // result.then(data => console.log(JSON.stringify(data))) 32 | }); 33 | it('Create document with ID', async () => { 34 | let result; 35 | try { 36 | result = await firestoreHelper.createDocumentWithID( 37 | db, 38 | collectionName, 39 | '1', 40 | { test: true } 41 | ); 42 | } catch (error) { 43 | console.log(error); 44 | } 45 | expect(result).to.equal(true); 46 | }); 47 | it('Create new document without an ID', async () => { 48 | let result; 49 | try { 50 | result = await firestoreHelper.createNewDocument(db, collectionName, { 51 | test: true, 52 | }); 53 | } catch (error) { 54 | console.log(error); 55 | } 56 | expect(typeof result.id).to.equal('string'); 57 | expect(result.id.length).to.equal(20); 58 | }); 59 | it('Update a document', async () => { 60 | let result; 61 | try { 62 | result = await firestoreHelper.updateDocument(db, collectionName, '1', { 63 | test: false, 64 | }); 65 | } catch (error) { 66 | console.log(error); 67 | } 68 | expect(result).to.equal(true); 69 | }); 70 | it('Delete a document', async () => { 71 | let result; 72 | try { 73 | result = await firestoreHelper.updateDocument(db, collectionName, '1', { 74 | test: false, 75 | }); 76 | } catch (error) { 77 | console.log(error); 78 | } 79 | expect(result).to.equal(true); 80 | }); 81 | it('Check if document exists: True', async () => { 82 | let result; 83 | try { 84 | result = await firestoreHelper.checkDocumentExists( 85 | db, 86 | collectionName, 87 | 'first-key' 88 | ); 89 | } catch (error) { 90 | console.log(error); 91 | } 92 | expect(result.exists).to.equal(true); 93 | }); 94 | it('Check if document exists: False', async () => { 95 | let result; 96 | try { 97 | result = await firestoreHelper.checkDocumentExists( 98 | db, 99 | collectionName, 100 | 'no-key' 101 | ); 102 | } catch (error) { 103 | console.log(error); 104 | } 105 | expect(result.exists).to.equal(false); 106 | }); 107 | it('Get a valid document', async () => { 108 | let result; 109 | try { 110 | result = await firestoreHelper.getDocument( 111 | db, 112 | collectionName, 113 | 'first-key' 114 | ); 115 | } catch (error) { 116 | console.log(error); 117 | } 118 | expect(result.website).to.equal('dalenguyen.me'); 119 | }); 120 | it('Get a invalid document', async () => { 121 | let result; 122 | try { 123 | result = await firestoreHelper.getDocument(db, collectionName, 'no-key'); 124 | } catch (error) { 125 | console.log(error); 126 | } 127 | expect(result).to.equal(false); 128 | }); 129 | it('Query Data without order', async () => { 130 | const query = [['website', '==', 'dalenguyen.me']]; 131 | let result; 132 | try { 133 | result = await firestoreHelper.queryData(db, collectionName, query); 134 | } catch (error) { 135 | console.log(error); 136 | } 137 | expect(typeof result['first-key']).to.equal('object'); 138 | }); 139 | it('Query Data with order', async () => { 140 | const query = [['website', '==', 'dalenguyen.me']]; 141 | const orderBy = ['email', 'desc']; 142 | let result; 143 | try { 144 | result = await firestoreHelper.queryData( 145 | db, 146 | collectionName, 147 | query, 148 | orderBy 149 | ); 150 | } catch (error) { 151 | console.log(error); 152 | } 153 | expect(typeof result['first-key']).to.equal('object'); 154 | }); 155 | it('Query Data with multi queries', async () => { 156 | const query = [ 157 | ['website', '==', 'dalenguyen.me'], 158 | ['email', '==', 'dungnq@itbox4vn.com'], 159 | ]; 160 | let result; 161 | try { 162 | result = await firestoreHelper.queryData(db, collectionName, query); 163 | } catch (error) { 164 | console.log(error); 165 | } 166 | expect(typeof result['first-key']).to.equal('object'); 167 | }); 168 | it('Query Data with multi pagination', async () => { 169 | const queryArray = [ 170 | ['website', '==', 'dalenguyen.me'], 171 | // ['email', '==', 'dungnq@itbox4vn.com'], 172 | ]; 173 | const orderBy = ['email', 'desc']; 174 | const size = 10; 175 | const page = 1; 176 | let result; 177 | try { 178 | result = await firestoreHelper.queryDataWithPagiation( 179 | db, 180 | collectionName, 181 | queryArray, 182 | orderBy, 183 | page, 184 | size 185 | ); 186 | } catch (error) { 187 | console.log(error); 188 | } 189 | expect(typeof result['first-key']).to.equal('object'); 190 | }); 191 | it('Delete a document with document id', async () => { 192 | let result; 193 | try { 194 | result = await firestoreHelper.deleteDocument(db, collectionName, '1'); 195 | } catch (error) { 196 | console.log(error); 197 | } 198 | expect(result.status).to.equal(true); 199 | expect(result.message).to.include('1 successfully deleted!'); 200 | }); 201 | }); 202 | -------------------------------------------------------------------------------- /src/firestore.ts: -------------------------------------------------------------------------------- 1 | import { backup, restore } from 'firestore-export-import'; 2 | import { IImportOptions } from 'firestore-export-import/dist/helper'; 3 | 4 | export class FirestoreHelper { 5 | /** 6 | *Create a document with id in firestore 7 | * 8 | * @param {*} db 9 | * @param {string} collectionName 10 | * @param {string} docId 11 | * @param {Object} data 12 | * @returns {Promise} 13 | * @memberof FirestoreHelper 14 | */ 15 | createDocumentWithID( 16 | db: any, 17 | collectionName: string, 18 | docId: string, 19 | data: Object 20 | ): Promise { 21 | return db 22 | .collection(collectionName) 23 | .doc(docId) 24 | .set(data) 25 | .then(() => true) 26 | .catch(function (error) { 27 | return false; 28 | }); 29 | } 30 | 31 | /** 32 | * Create a document without an ID 33 | * 34 | * @param {*} db 35 | * @param {string} collectionName 36 | * @param {Object} data 37 | * @returns 38 | * @memberof FirestoreHelper 39 | */ 40 | createNewDocument( 41 | db: any, 42 | collectionName: string, 43 | data: Object 44 | ): Promise { 45 | return db 46 | .collection(collectionName) 47 | .add(data) 48 | .then(function (docRef) { 49 | return docRef; 50 | }) 51 | .catch(function (error) { 52 | return error; 53 | }); 54 | } 55 | 56 | /** 57 | * Create a document with id in firestore 58 | * 59 | * @param {any} db 60 | * @param {any} collectionName 61 | * @param {any} docID 62 | * @param {any} collectionNameTwo 63 | * @param {any} docIDTwo 64 | * @param {any} data 65 | * @returns 66 | */ 67 | // createSubcollectionWithDocument (db: any, collectionName: string, docId: string, collectionNameTwo: string, docIdTwo: string, data: Object): void { 68 | // db.collection(collectionName).doc(docId).collection(collectionNameTwo).doc(docIdTwo)).set(data) 69 | // .then(res => console.log(`${JSON.stringify(data)} is added to ${collectionNameTwo} collection`)) 70 | // .catch(err => console.log('Error: ', err)) 71 | // } 72 | 73 | /** 74 | * Update a document 75 | * 76 | * @param {*} db 77 | * @param {string} collectionName 78 | * @param {string} docId 79 | * @param {Object} data 80 | * @returns {Promise} 81 | * @memberof FirestoreHelper 82 | */ 83 | updateDocument( 84 | db: any, 85 | collectionName: string, 86 | docId: string, 87 | data: Object 88 | ): Promise { 89 | return db 90 | .collection(collectionName) 91 | .doc(docId) 92 | .update(data) 93 | .then(() => true) 94 | .catch((err) => err); 95 | } 96 | 97 | /** 98 | * Delete a document 99 | * 100 | * @param {*} db 101 | * @param {string} collectionName 102 | * @param {string} docId 103 | * @returns {Promise} 104 | * @memberof FirestoreHelper 105 | */ 106 | deleteDocument( 107 | db: any, 108 | collectionName: string, 109 | docId: string 110 | ): Promise { 111 | return db 112 | .collection(collectionName) 113 | .doc(docId) 114 | .delete() 115 | .then(() => { 116 | return { status: true, message: docId + ' successfully deleted!' }; 117 | }) 118 | .catch((error) => { 119 | return { status: false, message: error }; 120 | }); 121 | } 122 | 123 | /** 124 | * Delete a document from Sub Collection 125 | * 126 | * @param {any} db 127 | * @param {any} collectionName 128 | * @param {any} docId 129 | * @param {any} collectionNameTwo 130 | * @param {any} docIdTwo 131 | */ 132 | deleteDocumentFromSubcollection( 133 | db: any, 134 | collectionName: string, 135 | docId: string, 136 | collectionNameTwo: string, 137 | docIdTwo: string 138 | ) { 139 | db.collection(collectionName) 140 | .doc(docId) 141 | .collection(collectionNameTwo) 142 | .doc(docIdTwo) 143 | .delete() 144 | .then(() => { 145 | console.log(docIdTwo + ' successfully deleted!'); 146 | }) 147 | .catch((error) => { 148 | console.error('Error removing document: ', error); 149 | }); 150 | } 151 | 152 | /** 153 | * Check where a document exists or not 154 | * 155 | * @param {any} db 156 | * @param {string} collectionName 157 | * @param {string} docId 158 | * @returns {Promise} 159 | * @memberof FirestoreHelper 160 | */ 161 | 162 | checkDocumentExists( 163 | db: any, 164 | collectionName: string, 165 | docId: string 166 | ): Promise { 167 | const dbRef = db.collection(collectionName).doc(docId); 168 | return dbRef 169 | .get() 170 | .then((doc) => { 171 | if (!doc.exists) { 172 | return { 173 | exists: false, 174 | }; 175 | } else { 176 | return { 177 | exists: true, 178 | data: doc.data(), 179 | }; 180 | } 181 | }) 182 | .catch((err) => { 183 | console.log('Error getting document', err); 184 | }); 185 | } 186 | 187 | /** 188 | * Get a document from document Id 189 | * 190 | * @param {any} db 191 | * @param {string} collectionName 192 | * @param {string} documentId 193 | * @returns {Promise} 194 | * @memberof FirestoreHelper 195 | */ 196 | getDocument( 197 | db: any, 198 | collectionName: string, 199 | documentId: string 200 | ): Promise { 201 | const docRef = db.collection(collectionName).doc(documentId); 202 | return docRef 203 | .get() 204 | .then(function (doc) { 205 | if (doc.exists) { 206 | return doc.data(); 207 | } else { 208 | // doc.data() will be undefined in this case 209 | console.log('No such document!'); 210 | return false; 211 | } 212 | }) 213 | .catch(function (error) { 214 | console.log('Error getting document:', error); 215 | }); 216 | } 217 | 218 | /** 219 | * Query data from Firestore 220 | * 221 | * @param {*} db 222 | * @param {string} collectionName 223 | * @param {Array} queryArray 224 | * @param {Array} orderBy 225 | * @returns {Promise} 226 | * @memberof FirestoreHelper 227 | */ 228 | queryData( 229 | db: any, 230 | collectionName: string, 231 | queryArray: Array, 232 | orderBy: Array = null 233 | ): Promise { 234 | return new Promise((resolve, reject) => { 235 | const dataRef = db.collection(collectionName); 236 | 237 | let queryRef = dataRef; 238 | queryArray.forEach((query) => { 239 | queryRef = queryRef.where(query[0], query[1], query[2]); 240 | }); 241 | 242 | if (orderBy !== null) { 243 | if (typeof orderBy[1] === undefined) { 244 | orderBy[1] = 'asc'; 245 | } 246 | queryRef = queryRef.orderBy(orderBy[0], orderBy[1]); 247 | } 248 | 249 | const results = {}; 250 | 251 | queryRef 252 | .get() 253 | .then((snapshot) => { 254 | snapshot.forEach((doc) => { 255 | results[doc.id] = doc.data(); 256 | }); 257 | if (Object.keys(results).length > 0) { 258 | resolve(results); 259 | } else { 260 | resolve('No such document!'); 261 | } 262 | }) 263 | .catch((err) => { 264 | reject(false); 265 | console.log('Error getting documents', err); 266 | }); 267 | }); 268 | } 269 | 270 | /** 271 | * Query data from Firestore with Pagination. 272 | * 273 | * @param {*} db 274 | * @param {string} collectionName 275 | * @param {Array} queryArray 276 | * @param {Array} orderBy 277 | * @param {number} page 278 | * @param {number} size 279 | * @returns {Promise} 280 | * @memberof FirestoreHelper 281 | */ 282 | queryDataWithPagiation( 283 | dbp: any, 284 | collectionName: string, 285 | queryArray: Array, 286 | orderBy: Array, 287 | page: number, 288 | size: number 289 | ): Promise { 290 | return new Promise((resolve, reject) => { 291 | const dataRef = dbp.collection(collectionName); 292 | const limit = size || 10; 293 | const offset = (page - 1) * limit; 294 | console.log('Limit is ' + limit + ' offset is: ' + offset); 295 | let queryRef = dataRef; 296 | queryArray.forEach((query) => { 297 | queryRef = queryRef.where(query[0], query[1], query[2]); 298 | }); 299 | 300 | if (orderBy !== null) { 301 | if (typeof orderBy[1] === undefined) { 302 | orderBy[1] = 'asc'; 303 | } 304 | queryRef = queryRef.orderBy(orderBy[0], orderBy[1]); 305 | } 306 | 307 | const results: { [k: string]: any } = {}; 308 | 309 | queryRef 310 | .limit(limit) 311 | .offset(offset) 312 | .get() 313 | .then((snapshot: any) => { 314 | snapshot.forEach((doc: any) => { 315 | results[doc.id] = doc.data(); 316 | }); 317 | if (Object.keys(results).length > 0) { 318 | resolve(results); 319 | } else { 320 | resolve('No such document!'); 321 | } 322 | }) 323 | .catch((err: any) => { 324 | reject(false); 325 | console.log('Error getting documents', err); 326 | }); 327 | }); 328 | } 329 | 330 | /** 331 | * Backup data from Firestore 332 | * 333 | * @param {string} collectionName 334 | * @return {json} 335 | */ 336 | backup(collectionName: string): Promise { 337 | return backup(collectionName); 338 | } 339 | 340 | /** 341 | * Add sub collection to data Object if possible 342 | * 343 | * @param {any} db 344 | * @param {any} key 345 | * @param {any} subData 346 | * @param {any} collectionName 347 | * @param {any} subCollection 348 | * @returns 349 | */ 350 | addSubCollection( 351 | db: any, 352 | key: string, 353 | subData: Object, 354 | collectionName: string, 355 | subCollection: string 356 | ) { 357 | return new Promise((resolve, reject) => { 358 | db.collection(collectionName) 359 | .doc(key) 360 | .collection(subCollection) 361 | .get() 362 | .then((snapshot) => { 363 | snapshot.forEach((subDoc) => { 364 | subData[subDoc.id] = subDoc.data(); 365 | resolve('Added data'); 366 | }); 367 | }) 368 | .catch((error) => { 369 | reject(false); 370 | console.log(error); 371 | }); 372 | }); 373 | } 374 | 375 | /** 376 | *Restore data to Firestore 377 | * 378 | * @param {*} fileName 379 | * @returns {Promise} 380 | * @memberof FirestoreHelper 381 | */ 382 | restore(fileName, options?: IImportOptions): Promise { 383 | return restore(fileName, options); 384 | } 385 | } 386 | -------------------------------------------------------------------------------- /yarn.lock: -------------------------------------------------------------------------------- 1 | # THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. 2 | # yarn lockfile v1 3 | 4 | 5 | "@babel/code-frame@^7.0.0": 6 | version "7.10.4" 7 | resolved "https://registry.yarnpkg.com/@babel/code-frame/-/code-frame-7.10.4.tgz#168da1a36e90da68ae8d49c0f1b48c7c6249213a" 8 | integrity sha512-vG6SvB6oYEhvgisZNFRmRCUkLz11c7rp+tbNTynGqc6mS1d5ATd/sGyV6W0KZZnXRKMTzZDRgQT3Ou9jhpAfUg== 9 | dependencies: 10 | "@babel/highlight" "^7.10.4" 11 | 12 | "@babel/helper-validator-identifier@^7.10.4": 13 | version "7.10.4" 14 | resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.10.4.tgz#a78c7a7251e01f616512d31b10adcf52ada5e0d2" 15 | integrity sha512-3U9y+43hz7ZM+rzG24Qe2mufW5KhvFg/NhnNph+i9mgCtdTCtMJuI1TMkrIUiK7Ix4PYlRF9I5dhqaLYA/ADXw== 16 | 17 | "@babel/highlight@^7.10.4": 18 | version "7.10.4" 19 | resolved "https://registry.yarnpkg.com/@babel/highlight/-/highlight-7.10.4.tgz#7d1bdfd65753538fabe6c38596cdb76d9ac60143" 20 | integrity sha512-i6rgnR/YgPEQzZZnbTHHuZdlE8qyoBNalD6F+q4vAFlcMEcqmkoG+mPqJYJCo63qPf74+Y1UZsl3l6f7/RIkmA== 21 | dependencies: 22 | "@babel/helper-validator-identifier" "^7.10.4" 23 | chalk "^2.0.0" 24 | js-tokens "^4.0.0" 25 | 26 | "@firebase/app-types@0.6.2": 27 | version "0.6.2" 28 | resolved "https://registry.yarnpkg.com/@firebase/app-types/-/app-types-0.6.2.tgz#8578cb1061a83ced4570188be9e225d54e0f27fb" 29 | integrity sha512-2VXvq/K+n8XMdM4L2xy5bYp2ZXMawJXluUIDzUBvMthVR+lhxK4pfFiqr1mmDbv9ydXvEAuFsD+6DpcZuJcSSw== 30 | 31 | "@firebase/auth-interop-types@0.1.6": 32 | version "0.1.6" 33 | resolved "https://registry.yarnpkg.com/@firebase/auth-interop-types/-/auth-interop-types-0.1.6.tgz#5ce13fc1c527ad36f1bb1322c4492680a6cf4964" 34 | integrity sha512-etIi92fW3CctsmR9e3sYM3Uqnoq861M0Id9mdOPF6PWIg38BXL5k4upCNBggGUpLIS0H1grMOvy/wn1xymwe2g== 35 | 36 | "@firebase/component@0.5.0": 37 | version "0.5.0" 38 | resolved "https://registry.yarnpkg.com/@firebase/component/-/component-0.5.0.tgz#f5b577d6c6f78d0f12fdc45046108921507f49c9" 39 | integrity sha512-v18csWtXb0ri+3m7wuGLY/UDgcb89vuMlZGQ//+7jEPLIQeLbylvZhol1uzW9WzoOpxMxOS2W5qyVGX36wZvEA== 40 | dependencies: 41 | "@firebase/util" "1.1.0" 42 | tslib "^2.1.0" 43 | 44 | "@firebase/database-types@0.7.2", "@firebase/database-types@^0.7.2": 45 | version "0.7.2" 46 | resolved "https://registry.yarnpkg.com/@firebase/database-types/-/database-types-0.7.2.tgz#449c4b36ec59a1ad9089797b540e2ba1c0d4fcbf" 47 | integrity sha512-cdAd/dgwvC0r3oLEDUR+ULs1vBsEvy0b27nlzKhU6LQgm9fCDzgaH9nFGv8x+S9dly4B0egAXkONkVoWcOAisg== 48 | dependencies: 49 | "@firebase/app-types" "0.6.2" 50 | 51 | "@firebase/database@^0.10.0": 52 | version "0.10.1" 53 | resolved "https://registry.yarnpkg.com/@firebase/database/-/database-0.10.1.tgz#1e8c64519552f225a4a88e7dae09ecf29447f2be" 54 | integrity sha512-umT0kynJKc5VpVBOg3+YTDzdJORssh+QqPjoHfbSvtmgZizNiV8mgmKRcDhlVM6CisPb6v5xBn9l8JbK/WRQ1Q== 55 | dependencies: 56 | "@firebase/auth-interop-types" "0.1.6" 57 | "@firebase/component" "0.5.0" 58 | "@firebase/database-types" "0.7.2" 59 | "@firebase/logger" "0.2.6" 60 | "@firebase/util" "1.1.0" 61 | faye-websocket "0.11.3" 62 | tslib "^2.1.0" 63 | 64 | "@firebase/logger@0.2.6": 65 | version "0.2.6" 66 | resolved "https://registry.yarnpkg.com/@firebase/logger/-/logger-0.2.6.tgz#3aa2ca4fe10327cabf7808bd3994e88db26d7989" 67 | integrity sha512-KIxcUvW/cRGWlzK9Vd2KB864HlUnCfdTH0taHE0sXW5Xl7+W68suaeau1oKNEqmc3l45azkd4NzXTCWZRZdXrw== 68 | 69 | "@firebase/util@1.1.0": 70 | version "1.1.0" 71 | resolved "https://registry.yarnpkg.com/@firebase/util/-/util-1.1.0.tgz#add2d57d0b2307a932520abdee303b66be0ac8b0" 72 | integrity sha512-lfuSASuPKNdfebuFR8rjFamMQUPH9iiZHcKS755Rkm/5gRT0qC7BMhCh3ZkHf7NVbplzIc/GhmX2jM+igDRCag== 73 | dependencies: 74 | tslib "^2.1.0" 75 | 76 | "@google-cloud/common@^3.3.0": 77 | version "3.5.0" 78 | resolved "https://registry.yarnpkg.com/@google-cloud/common/-/common-3.5.0.tgz#0959e769e8075a06eb0823cc567eef00fd0c2d02" 79 | integrity sha512-10d7ZAvKhq47L271AqvHEd8KzJqGU45TY+rwM2Z3JHuB070FeTi7oJJd7elfrnKaEvaktw3hH2wKnRWxk/3oWQ== 80 | dependencies: 81 | "@google-cloud/projectify" "^2.0.0" 82 | "@google-cloud/promisify" "^2.0.0" 83 | arrify "^2.0.1" 84 | duplexify "^4.1.1" 85 | ent "^2.2.0" 86 | extend "^3.0.2" 87 | google-auth-library "^6.1.1" 88 | retry-request "^4.1.1" 89 | teeny-request "^7.0.0" 90 | 91 | "@google-cloud/firestore@^4.5.0": 92 | version "4.7.1" 93 | resolved "https://registry.yarnpkg.com/@google-cloud/firestore/-/firestore-4.7.1.tgz#d170c72ecda6286ebab460765511103362da7b21" 94 | integrity sha512-Qici+WKB6uRdDS1S3CaxGrIaCl4Bck70DYSzA5dZFkTU03Jj5DKXC4PYeUkfCAiB4haj7tzx+2ye7rhLxPclhQ== 95 | dependencies: 96 | fast-deep-equal "^3.1.1" 97 | functional-red-black-tree "^1.0.1" 98 | google-gax "^2.9.2" 99 | 100 | "@google-cloud/paginator@^3.0.0": 101 | version "3.0.5" 102 | resolved "https://registry.yarnpkg.com/@google-cloud/paginator/-/paginator-3.0.5.tgz#9d6b96c421a89bd560c1bc2c197c7611ef21db6c" 103 | integrity sha512-N4Uk4BT1YuskfRhKXBs0n9Lg2YTROZc6IMpkO/8DIHODtm5s3xY8K5vVBo23v/2XulY3azwITQlYWgT4GdLsUw== 104 | dependencies: 105 | arrify "^2.0.0" 106 | extend "^3.0.2" 107 | 108 | "@google-cloud/projectify@^2.0.0": 109 | version "2.0.1" 110 | resolved "https://registry.yarnpkg.com/@google-cloud/projectify/-/projectify-2.0.1.tgz#13350ee609346435c795bbfe133a08dfeab78d65" 111 | integrity sha512-ZDG38U/Yy6Zr21LaR3BTiiLtpJl6RkPS/JwoRT453G+6Q1DhlV0waNf8Lfu+YVYGIIxgKnLayJRfYlFJfiI8iQ== 112 | 113 | "@google-cloud/promisify@^2.0.0": 114 | version "2.0.3" 115 | resolved "https://registry.yarnpkg.com/@google-cloud/promisify/-/promisify-2.0.3.tgz#f934b5cdc939e3c7039ff62b9caaf59a9d89e3a8" 116 | integrity sha512-d4VSA86eL/AFTe5xtyZX+ePUjE8dIFu2T8zmdeNBSa5/kNgXPCx/o/wbFNHAGLJdGnk1vddRuMESD9HbOC8irw== 117 | 118 | "@google-cloud/storage@^5.3.0": 119 | version "5.5.0" 120 | resolved "https://registry.yarnpkg.com/@google-cloud/storage/-/storage-5.5.0.tgz#6b3513b1e05534da04c26313af5a59b84bba5cb6" 121 | integrity sha512-Pat83kHNnKJpEHUirtQtCoAJ2K3OlEo2ZcSlPjierJnEKnhbIQPyJ6mAbs/ovm3K3QDQhouKJ9QSONkFPEwQuA== 122 | dependencies: 123 | "@google-cloud/common" "^3.3.0" 124 | "@google-cloud/paginator" "^3.0.0" 125 | "@google-cloud/promisify" "^2.0.0" 126 | arrify "^2.0.0" 127 | compressible "^2.0.12" 128 | date-and-time "^0.14.0" 129 | duplexify "^4.0.0" 130 | extend "^3.0.2" 131 | gaxios "^4.0.0" 132 | gcs-resumable-upload "^3.1.0" 133 | get-stream "^6.0.0" 134 | hash-stream-validation "^0.2.2" 135 | mime "^2.2.0" 136 | mime-types "^2.0.8" 137 | onetime "^5.1.0" 138 | p-limit "^3.0.1" 139 | pumpify "^2.0.0" 140 | snakeize "^0.1.0" 141 | stream-events "^1.0.1" 142 | xdg-basedir "^4.0.0" 143 | 144 | "@grpc/grpc-js@~1.1.1": 145 | version "1.1.8" 146 | resolved "https://registry.yarnpkg.com/@grpc/grpc-js/-/grpc-js-1.1.8.tgz#2845f0fc3d1bfbb150ed7a78a76bdf41b126d367" 147 | integrity sha512-64hg5rmEm6F/NvlWERhHmmgxbWU8nD2TMWE+9TvG7/WcOrFT3fzg/Uu631pXRFwmJ4aWO/kp9vVSlr8FUjBDLA== 148 | dependencies: 149 | "@grpc/proto-loader" "^0.6.0-pre14" 150 | "@types/node" "^12.12.47" 151 | google-auth-library "^6.0.0" 152 | semver "^6.2.0" 153 | 154 | "@grpc/proto-loader@^0.5.1": 155 | version "0.5.5" 156 | resolved "https://registry.yarnpkg.com/@grpc/proto-loader/-/proto-loader-0.5.5.tgz#6725e7a1827bdf8e92e29fbf4e9ef0203c0906a9" 157 | integrity sha512-WwN9jVNdHRQoOBo9FDH7qU+mgfjPc8GygPYms3M+y3fbQLfnCe/Kv/E01t7JRgnrsOHH8euvSbed3mIalXhwqQ== 158 | dependencies: 159 | lodash.camelcase "^4.3.0" 160 | protobufjs "^6.8.6" 161 | 162 | "@grpc/proto-loader@^0.6.0-pre14": 163 | version "0.6.0-pre9" 164 | resolved "https://registry.yarnpkg.com/@grpc/proto-loader/-/proto-loader-0.6.0-pre9.tgz#0c6fe42f6c5ef9ce1b3cef7be64d5b09d6fe4d6d" 165 | integrity sha512-oM+LjpEjNzW5pNJjt4/hq1HYayNeQT+eGrOPABJnYHv7TyNPDNzkQ76rDYZF86X5swJOa4EujEMzQ9iiTdPgww== 166 | dependencies: 167 | "@types/long" "^4.0.1" 168 | lodash.camelcase "^4.3.0" 169 | long "^4.0.0" 170 | protobufjs "^6.9.0" 171 | yargs "^15.3.1" 172 | 173 | "@panva/asn1.js@^1.0.0": 174 | version "1.0.0" 175 | resolved "https://registry.yarnpkg.com/@panva/asn1.js/-/asn1.js-1.0.0.tgz#dd55ae7b8129e02049f009408b97c61ccf9032f6" 176 | integrity sha512-UdkG3mLEqXgnlKsWanWcgb6dOjUzJ+XC5f+aWw30qrtjxeNUSfKX1cd5FBzOaXQumoe9nIqeZUvrRJS03HCCtw== 177 | 178 | "@protobufjs/aspromise@^1.1.1", "@protobufjs/aspromise@^1.1.2": 179 | version "1.1.2" 180 | resolved "https://registry.yarnpkg.com/@protobufjs/aspromise/-/aspromise-1.1.2.tgz#9b8b0cc663d669a7d8f6f5d0893a14d348f30fbf" 181 | integrity sha1-m4sMxmPWaafY9vXQiToU00jzD78= 182 | 183 | "@protobufjs/base64@^1.1.2": 184 | version "1.1.2" 185 | resolved "https://registry.yarnpkg.com/@protobufjs/base64/-/base64-1.1.2.tgz#4c85730e59b9a1f1f349047dbf24296034bb2735" 186 | integrity sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg== 187 | 188 | "@protobufjs/codegen@^2.0.4": 189 | version "2.0.4" 190 | resolved "https://registry.yarnpkg.com/@protobufjs/codegen/-/codegen-2.0.4.tgz#7ef37f0d010fb028ad1ad59722e506d9262815cb" 191 | integrity sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg== 192 | 193 | "@protobufjs/eventemitter@^1.1.0": 194 | version "1.1.0" 195 | resolved "https://registry.yarnpkg.com/@protobufjs/eventemitter/-/eventemitter-1.1.0.tgz#355cbc98bafad5978f9ed095f397621f1d066b70" 196 | integrity sha1-NVy8mLr61ZePntCV85diHx0Ga3A= 197 | 198 | "@protobufjs/fetch@^1.1.0": 199 | version "1.1.0" 200 | resolved "https://registry.yarnpkg.com/@protobufjs/fetch/-/fetch-1.1.0.tgz#ba99fb598614af65700c1619ff06d454b0d84c45" 201 | integrity sha1-upn7WYYUr2VwDBYZ/wbUVLDYTEU= 202 | dependencies: 203 | "@protobufjs/aspromise" "^1.1.1" 204 | "@protobufjs/inquire" "^1.1.0" 205 | 206 | "@protobufjs/float@^1.0.2": 207 | version "1.0.2" 208 | resolved "https://registry.yarnpkg.com/@protobufjs/float/-/float-1.0.2.tgz#5e9e1abdcb73fc0a7cb8b291df78c8cbd97b87d1" 209 | integrity sha1-Xp4avctz/Ap8uLKR33jIy9l7h9E= 210 | 211 | "@protobufjs/inquire@^1.1.0": 212 | version "1.1.0" 213 | resolved "https://registry.yarnpkg.com/@protobufjs/inquire/-/inquire-1.1.0.tgz#ff200e3e7cf2429e2dcafc1140828e8cc638f089" 214 | integrity sha1-/yAOPnzyQp4tyvwRQIKOjMY48Ik= 215 | 216 | "@protobufjs/path@^1.1.2": 217 | version "1.1.2" 218 | resolved "https://registry.yarnpkg.com/@protobufjs/path/-/path-1.1.2.tgz#6cc2b20c5c9ad6ad0dccfd21ca7673d8d7fbf68d" 219 | integrity sha1-bMKyDFya1q0NzP0hynZz2Nf79o0= 220 | 221 | "@protobufjs/pool@^1.1.0": 222 | version "1.1.0" 223 | resolved "https://registry.yarnpkg.com/@protobufjs/pool/-/pool-1.1.0.tgz#09fd15f2d6d3abfa9b65bc366506d6ad7846ff54" 224 | integrity sha1-Cf0V8tbTq/qbZbw2ZQbWrXhG/1Q= 225 | 226 | "@protobufjs/utf8@^1.1.0": 227 | version "1.1.0" 228 | resolved "https://registry.yarnpkg.com/@protobufjs/utf8/-/utf8-1.1.0.tgz#a777360b5b39a1a2e5106f8e858f2fd2d060c570" 229 | integrity sha1-p3c2C1s5oaLlEG+OhY8v0tBgxXA= 230 | 231 | "@tootallnate/once@1": 232 | version "1.1.2" 233 | resolved "https://registry.yarnpkg.com/@tootallnate/once/-/once-1.1.2.tgz#ccb91445360179a04e7fe6aff78c00ffc1eeaf82" 234 | integrity sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw== 235 | 236 | "@types/body-parser@*": 237 | version "1.19.0" 238 | resolved "https://registry.yarnpkg.com/@types/body-parser/-/body-parser-1.19.0.tgz#0685b3c47eb3006ffed117cdd55164b61f80538f" 239 | integrity sha512-W98JrE0j2K78swW4ukqMleo8R7h/pFETjM2DQ90MF6XK2i4LO4W3gQ71Lt4w3bfm2EvVSyWHplECvB5sK22yFQ== 240 | dependencies: 241 | "@types/connect" "*" 242 | "@types/node" "*" 243 | 244 | "@types/chai@^4.2.18": 245 | version "4.2.18" 246 | resolved "https://registry.yarnpkg.com/@types/chai/-/chai-4.2.18.tgz#0c8e298dbff8205e2266606c1ea5fbdba29b46e4" 247 | integrity sha512-rS27+EkB/RE1Iz3u0XtVL5q36MGDWbgYe7zWiodyKNUnthxY0rukK5V36eiUCtCisB7NN8zKYH6DO2M37qxFEQ== 248 | 249 | "@types/connect@*": 250 | version "3.4.34" 251 | resolved "https://registry.yarnpkg.com/@types/connect/-/connect-3.4.34.tgz#170a40223a6d666006d93ca128af2beb1d9b1901" 252 | integrity sha512-ePPA/JuI+X0vb+gSWlPKOY0NdNAie/rPUqX2GUPpbZwiKTkSPhjXWuee47E4MtE54QVzGCQMQkAL6JhV2E1+cQ== 253 | dependencies: 254 | "@types/node" "*" 255 | 256 | "@types/express-jwt@0.0.42": 257 | version "0.0.42" 258 | resolved "https://registry.yarnpkg.com/@types/express-jwt/-/express-jwt-0.0.42.tgz#4f04e1fadf9d18725950dc041808a4a4adf7f5ae" 259 | integrity sha512-WszgUddvM1t5dPpJ3LhWNH8kfNN8GPIBrAGxgIYXVCEGx6Bx4A036aAuf/r5WH9DIEdlmp7gHOYvSM6U87B0ag== 260 | dependencies: 261 | "@types/express" "*" 262 | "@types/express-unless" "*" 263 | 264 | "@types/express-serve-static-core@^4.17.18": 265 | version "4.17.19" 266 | resolved "https://registry.yarnpkg.com/@types/express-serve-static-core/-/express-serve-static-core-4.17.19.tgz#00acfc1632e729acac4f1530e9e16f6dd1508a1d" 267 | integrity sha512-DJOSHzX7pCiSElWaGR8kCprwibCB/3yW6vcT8VG3P0SJjnv19gnWG/AZMfM60Xj/YJIp/YCaDHyvzsFVeniARA== 268 | dependencies: 269 | "@types/node" "*" 270 | "@types/qs" "*" 271 | "@types/range-parser" "*" 272 | 273 | "@types/express-unless@*": 274 | version "0.5.1" 275 | resolved "https://registry.yarnpkg.com/@types/express-unless/-/express-unless-0.5.1.tgz#4f440b905e42bbf53382b8207bc337dc5ff9fd1f" 276 | integrity sha512-5fuvg7C69lemNgl0+v+CUxDYWVPSfXHhJPst4yTLcqi4zKJpORCxnDrnnilk3k0DTq/WrAUdvXFs01+vUqUZHw== 277 | dependencies: 278 | "@types/express" "*" 279 | 280 | "@types/express@*": 281 | version "4.17.11" 282 | resolved "https://registry.yarnpkg.com/@types/express/-/express-4.17.11.tgz#debe3caa6f8e5fcda96b47bd54e2f40c4ee59545" 283 | integrity sha512-no+R6rW60JEc59977wIxreQVsIEOAYwgCqldrA/vkpCnbD7MqTefO97lmoBe4WE0F156bC4uLSP1XHDOySnChg== 284 | dependencies: 285 | "@types/body-parser" "*" 286 | "@types/express-serve-static-core" "^4.17.18" 287 | "@types/qs" "*" 288 | "@types/serve-static" "*" 289 | 290 | "@types/long@^4.0.0", "@types/long@^4.0.1": 291 | version "4.0.1" 292 | resolved "https://registry.yarnpkg.com/@types/long/-/long-4.0.1.tgz#459c65fa1867dafe6a8f322c4c51695663cc55e9" 293 | integrity sha512-5tXH6Bx/kNGd3MgffdmP4dy2Z+G4eaXw0SE81Tq3BNadtnMR5/ySMzX4SLEzHJzSmPNn4HIdpQsBvXMUykr58w== 294 | 295 | "@types/mime@^1": 296 | version "1.3.2" 297 | resolved "https://registry.yarnpkg.com/@types/mime/-/mime-1.3.2.tgz#93e25bf9ee75fe0fd80b594bc4feb0e862111b5a" 298 | integrity sha512-YATxVxgRqNH6nHEIsvg6k2Boc1JHI9ZbH5iWFFv/MTkchz3b1ieGDa5T0a9RznNdI0KhVbdbWSN+KWWrQZRxTw== 299 | 300 | "@types/mocha@^8.2.2": 301 | version "8.2.2" 302 | resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-8.2.2.tgz#91daa226eb8c2ff261e6a8cbf8c7304641e095e0" 303 | integrity sha512-Lwh0lzzqT5Pqh6z61P3c3P5nm6fzQK/MMHl9UKeneAeInVflBSz1O2EkX6gM6xfJd7FBXBY5purtLx7fUiZ7Hw== 304 | 305 | "@types/node@*", "@types/node@>=12.12.47": 306 | version "15.3.0" 307 | resolved "https://registry.yarnpkg.com/@types/node/-/node-15.3.0.tgz#d6fed7d6bc6854306da3dea1af9f874b00783e26" 308 | integrity sha512-8/bnjSZD86ZfpBsDlCIkNXIvm+h6wi9g7IqL+kmFkQ+Wvu3JrasgLElfiPgoo8V8vVfnEi0QVS12gbl94h9YsQ== 309 | 310 | "@types/node@^12.12.47": 311 | version "12.19.6" 312 | resolved "https://registry.yarnpkg.com/@types/node/-/node-12.19.6.tgz#fbf249fa46487dd8c7386d785231368b92a33a53" 313 | integrity sha512-U2VopDdmBoYBmtm8Rz340mvvSz34VgX/K9+XCuckvcLGMkt3rbMX8soqFOikIPlPBc5lmw8By9NUK7bEFSBFlQ== 314 | 315 | "@types/node@^13.7.0": 316 | version "13.13.32" 317 | resolved "https://registry.yarnpkg.com/@types/node/-/node-13.13.32.tgz#f0edd0fb57b3c9f6e64a0b3ddb1e0f729b6f71ce" 318 | integrity sha512-sPBvDnrwZE1uePhkCEyI/qQlgZM5kePPAhHIFDWNsOrWBFRBOk3LKJYmVCLeLZlL9Ub/FzMJb31OTWCg2F+06g== 319 | 320 | "@types/qs@*": 321 | version "6.9.6" 322 | resolved "https://registry.yarnpkg.com/@types/qs/-/qs-6.9.6.tgz#df9c3c8b31a247ec315e6996566be3171df4b3b1" 323 | integrity sha512-0/HnwIfW4ki2D8L8c9GVcG5I72s9jP5GSLVF0VIXDW00kmIpA6O33G7a8n59Tmh7Nz0WUC3rSb7PTY/sdW2JzA== 324 | 325 | "@types/range-parser@*": 326 | version "1.2.3" 327 | resolved "https://registry.yarnpkg.com/@types/range-parser/-/range-parser-1.2.3.tgz#7ee330ba7caafb98090bece86a5ee44115904c2c" 328 | integrity sha512-ewFXqrQHlFsgc09MK5jP5iR7vumV/BYayNC6PgJO2LPe8vrnNFyjQjSppfEngITi0qvfKtzFvgKymGheFM9UOA== 329 | 330 | "@types/serve-static@*": 331 | version "1.13.9" 332 | resolved "https://registry.yarnpkg.com/@types/serve-static/-/serve-static-1.13.9.tgz#aacf28a85a05ee29a11fb7c3ead935ac56f33e4e" 333 | integrity sha512-ZFqF6qa48XsPdjXV5Gsz0Zqmux2PerNd3a/ktL45mHpa19cuMi/cL8tcxdAx497yRh+QtYPuofjT9oWw9P7nkA== 334 | dependencies: 335 | "@types/mime" "^1" 336 | "@types/node" "*" 337 | 338 | "@ungap/promise-all-settled@1.1.2": 339 | version "1.1.2" 340 | resolved "https://registry.yarnpkg.com/@ungap/promise-all-settled/-/promise-all-settled-1.1.2.tgz#aa58042711d6e3275dd37dc597e5d31e8c290a44" 341 | integrity sha512-sL/cEvJWAnClXw0wHk85/2L0G6Sj8UB0Ctc1TEMbKSsmpRosqhwj9gWgFRZSrBr2f9tiXISwNhCPmlfqUqyb9Q== 342 | 343 | abort-controller@^3.0.0: 344 | version "3.0.0" 345 | resolved "https://registry.yarnpkg.com/abort-controller/-/abort-controller-3.0.0.tgz#eaf54d53b62bae4138e809ca225c8439a6efb392" 346 | integrity sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg== 347 | dependencies: 348 | event-target-shim "^5.0.0" 349 | 350 | agent-base@6: 351 | version "6.0.2" 352 | resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" 353 | integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ== 354 | dependencies: 355 | debug "4" 356 | 357 | ansi-colors@4.1.1: 358 | version "4.1.1" 359 | resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.1.tgz#cbb9ae256bf750af1eab344f229aa27fe94ba348" 360 | integrity sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA== 361 | 362 | ansi-regex@^3.0.0: 363 | version "3.0.0" 364 | resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-3.0.0.tgz#ed0317c322064f79466c02966bddb605ab37d998" 365 | integrity sha1-7QMXwyIGT3lGbAKWa922Bas32Zg= 366 | 367 | ansi-regex@^5.0.0: 368 | version "5.0.0" 369 | resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.0.tgz#388539f55179bf39339c81af30a654d69f87cb75" 370 | integrity sha512-bY6fj56OUQ0hU1KjFNDQuJFezqKdrAyFdIevADiqrWHwSlbmBNMHp5ak2f40Pm8JTFyM2mqxkG6ngkHO11f/lg== 371 | 372 | ansi-styles@^3.2.1: 373 | version "3.2.1" 374 | resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d" 375 | integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA== 376 | dependencies: 377 | color-convert "^1.9.0" 378 | 379 | ansi-styles@^4.0.0, ansi-styles@^4.1.0: 380 | version "4.3.0" 381 | resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" 382 | integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== 383 | dependencies: 384 | color-convert "^2.0.1" 385 | 386 | anymatch@~3.1.1: 387 | version "3.1.1" 388 | resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-3.1.1.tgz#c55ecf02185e2469259399310c173ce31233b142" 389 | integrity sha512-mM8522psRCqzV+6LhomX5wgp25YVibjh8Wj23I5RPkPppSVSjyKD2A2mBJmWGa+KN7f2D6LNh9jkBCeyLktzjg== 390 | dependencies: 391 | normalize-path "^3.0.0" 392 | picomatch "^2.0.4" 393 | 394 | arg@^4.1.0: 395 | version "4.1.3" 396 | resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089" 397 | integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA== 398 | 399 | argparse@^1.0.7: 400 | version "1.0.10" 401 | resolved "https://registry.yarnpkg.com/argparse/-/argparse-1.0.10.tgz#bcd6791ea5ae09725e17e5ad988134cd40b3d911" 402 | integrity sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg== 403 | dependencies: 404 | sprintf-js "~1.0.2" 405 | 406 | argparse@^2.0.1: 407 | version "2.0.1" 408 | resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" 409 | integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== 410 | 411 | arrify@^2.0.0, arrify@^2.0.1: 412 | version "2.0.1" 413 | resolved "https://registry.yarnpkg.com/arrify/-/arrify-2.0.1.tgz#c9655e9331e0abcd588d2a7cad7e9956f66701fa" 414 | integrity sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug== 415 | 416 | assertion-error@^1.1.0: 417 | version "1.1.0" 418 | resolved "https://registry.yarnpkg.com/assertion-error/-/assertion-error-1.1.0.tgz#e60b6b0e8f301bd97e5375215bda406c85118c0b" 419 | integrity sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw== 420 | 421 | balanced-match@^1.0.0: 422 | version "1.0.0" 423 | resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.0.tgz#89b4d199ab2bee49de164ea02b89ce462d71b767" 424 | integrity sha1-ibTRmasr7kneFk6gK4nORi1xt2c= 425 | 426 | base64-js@^1.3.0: 427 | version "1.5.1" 428 | resolved "https://registry.yarnpkg.com/base64-js/-/base64-js-1.5.1.tgz#1b1b440160a5bf7ad40b650f095963481903930a" 429 | integrity sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA== 430 | 431 | bignumber.js@^9.0.0: 432 | version "9.0.1" 433 | resolved "https://registry.yarnpkg.com/bignumber.js/-/bignumber.js-9.0.1.tgz#8d7ba124c882bfd8e43260c67475518d0689e4e5" 434 | integrity sha512-IdZR9mh6ahOBv/hYGiXyVuyCetmGJhtYkqLBpTStdhEGjegpPlUawydyaF3pbIOFynJTpllEs+NP+CS9jKFLjA== 435 | 436 | binary-extensions@^2.0.0: 437 | version "2.1.0" 438 | resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-2.1.0.tgz#30fa40c9e7fe07dbc895678cd287024dea241dd9" 439 | integrity sha512-1Yj8h9Q+QDF5FzhMs/c9+6UntbD5MkRfRwac8DoEm9ZfUBZ7tZ55YcGVAzEe4bXsdQHEk+s9S5wsOKVdZrw0tQ== 440 | 441 | brace-expansion@^1.1.7: 442 | version "1.1.11" 443 | resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" 444 | integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== 445 | dependencies: 446 | balanced-match "^1.0.0" 447 | concat-map "0.0.1" 448 | 449 | braces@~3.0.2: 450 | version "3.0.2" 451 | resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" 452 | integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== 453 | dependencies: 454 | fill-range "^7.0.1" 455 | 456 | browser-stdout@1.3.1: 457 | version "1.3.1" 458 | resolved "https://registry.yarnpkg.com/browser-stdout/-/browser-stdout-1.3.1.tgz#baa559ee14ced73452229bad7326467c61fabd60" 459 | integrity sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw== 460 | 461 | buffer-equal-constant-time@1.0.1: 462 | version "1.0.1" 463 | resolved "https://registry.yarnpkg.com/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz#f8e71132f7ffe6e01a5c9697a4c6f3e48d5cc819" 464 | integrity sha1-+OcRMvf/5uAaXJaXpMbz5I1cyBk= 465 | 466 | buffer-from@^1.0.0: 467 | version "1.1.1" 468 | resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.1.tgz#32713bc028f75c02fdb710d7c7bcec1f2c6070ef" 469 | integrity sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A== 470 | 471 | builtin-modules@^1.1.1: 472 | version "1.1.1" 473 | resolved "https://registry.yarnpkg.com/builtin-modules/-/builtin-modules-1.1.1.tgz#270f076c5a72c02f5b65a47df94c5fe3a278892f" 474 | integrity sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8= 475 | 476 | camelcase@^5.0.0: 477 | version "5.3.1" 478 | resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-5.3.1.tgz#e3c9b31569e106811df242f715725a1f4c494320" 479 | integrity sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg== 480 | 481 | camelcase@^6.0.0: 482 | version "6.2.0" 483 | resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-6.2.0.tgz#924af881c9d525ac9d87f40d964e5cea982a1809" 484 | integrity sha512-c7wVvbw3f37nuobQNtgsgG9POC9qMbNuMQmTCqZv23b6MIz0fcYpBiOlv9gEN/hdLdnZTDQhg6e9Dq5M1vKvfg== 485 | 486 | chai@^4.3.4: 487 | version "4.3.4" 488 | resolved "https://registry.yarnpkg.com/chai/-/chai-4.3.4.tgz#b55e655b31e1eac7099be4c08c21964fce2e6c49" 489 | integrity sha512-yS5H68VYOCtN1cjfwumDSuzn/9c+yza4f3reKXlE5rUg7SFcCEy90gJvydNgOYtblyf4Zi6jIWRnXOgErta0KA== 490 | dependencies: 491 | assertion-error "^1.1.0" 492 | check-error "^1.0.2" 493 | deep-eql "^3.0.1" 494 | get-func-name "^2.0.0" 495 | pathval "^1.1.1" 496 | type-detect "^4.0.5" 497 | 498 | chalk@^2.0.0, chalk@^2.3.0: 499 | version "2.4.2" 500 | resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424" 501 | integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== 502 | dependencies: 503 | ansi-styles "^3.2.1" 504 | escape-string-regexp "^1.0.5" 505 | supports-color "^5.3.0" 506 | 507 | chalk@^4.0.0: 508 | version "4.1.0" 509 | resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.0.tgz#4e14870a618d9e2edd97dd8345fd9d9dc315646a" 510 | integrity sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A== 511 | dependencies: 512 | ansi-styles "^4.1.0" 513 | supports-color "^7.1.0" 514 | 515 | check-error@^1.0.2: 516 | version "1.0.2" 517 | resolved "https://registry.yarnpkg.com/check-error/-/check-error-1.0.2.tgz#574d312edd88bb5dd8912e9286dd6c0aed4aac82" 518 | integrity sha1-V00xLt2Iu13YkS6Sht1sCu1KrII= 519 | 520 | chokidar@3.5.1: 521 | version "3.5.1" 522 | resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-3.5.1.tgz#ee9ce7bbebd2b79f49f304799d5468e31e14e68a" 523 | integrity sha512-9+s+Od+W0VJJzawDma/gvBNQqkTiqYTWLuZoyAsivsI4AaWTCzHG06/TMjsf1cYe9Cb97UCEhjz7HvnPk2p/tw== 524 | dependencies: 525 | anymatch "~3.1.1" 526 | braces "~3.0.2" 527 | glob-parent "~5.1.0" 528 | is-binary-path "~2.1.0" 529 | is-glob "~4.0.1" 530 | normalize-path "~3.0.0" 531 | readdirp "~3.5.0" 532 | optionalDependencies: 533 | fsevents "~2.3.1" 534 | 535 | cliui@^6.0.0: 536 | version "6.0.0" 537 | resolved "https://registry.yarnpkg.com/cliui/-/cliui-6.0.0.tgz#511d702c0c4e41ca156d7d0e96021f23e13225b1" 538 | integrity sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ== 539 | dependencies: 540 | string-width "^4.2.0" 541 | strip-ansi "^6.0.0" 542 | wrap-ansi "^6.2.0" 543 | 544 | cliui@^7.0.2: 545 | version "7.0.4" 546 | resolved "https://registry.yarnpkg.com/cliui/-/cliui-7.0.4.tgz#a0265ee655476fc807aea9df3df8df7783808b4f" 547 | integrity sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ== 548 | dependencies: 549 | string-width "^4.2.0" 550 | strip-ansi "^6.0.0" 551 | wrap-ansi "^7.0.0" 552 | 553 | color-convert@^1.9.0: 554 | version "1.9.3" 555 | resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8" 556 | integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg== 557 | dependencies: 558 | color-name "1.1.3" 559 | 560 | color-convert@^2.0.1: 561 | version "2.0.1" 562 | resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" 563 | integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== 564 | dependencies: 565 | color-name "~1.1.4" 566 | 567 | color-name@1.1.3: 568 | version "1.1.3" 569 | resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25" 570 | integrity sha1-p9BVi9icQveV3UIyj3QIMcpTvCU= 571 | 572 | color-name@~1.1.4: 573 | version "1.1.4" 574 | resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" 575 | integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== 576 | 577 | commander@^2.12.1: 578 | version "2.20.3" 579 | resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.3.tgz#fd485e84c03eb4881c20722ba48035e8531aeb33" 580 | integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== 581 | 582 | compressible@^2.0.12: 583 | version "2.0.18" 584 | resolved "https://registry.yarnpkg.com/compressible/-/compressible-2.0.18.tgz#af53cca6b070d4c3c0750fbd77286a6d7cc46fba" 585 | integrity sha512-AF3r7P5dWxL8MxyITRMlORQNaOA2IkAFaTr4k7BUumjPtRpGDTZpl0Pb1XCO6JeDCBdp126Cgs9sMxqSjgYyRg== 586 | dependencies: 587 | mime-db ">= 1.43.0 < 2" 588 | 589 | concat-map@0.0.1: 590 | version "0.0.1" 591 | resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" 592 | integrity sha1-2Klr13/Wjfd5OnMDajug1UBdR3s= 593 | 594 | configstore@^5.0.0: 595 | version "5.0.1" 596 | resolved "https://registry.yarnpkg.com/configstore/-/configstore-5.0.1.tgz#d365021b5df4b98cdd187d6a3b0e3f6a7cc5ed96" 597 | integrity sha512-aMKprgk5YhBNyH25hj8wGt2+D52Sw1DRRIzqBwLp2Ya9mFmY8KPvvtvmna8SxVR9JMZ4kzMD68N22vlaRpkeFA== 598 | dependencies: 599 | dot-prop "^5.2.0" 600 | graceful-fs "^4.1.2" 601 | make-dir "^3.0.0" 602 | unique-string "^2.0.0" 603 | write-file-atomic "^3.0.0" 604 | xdg-basedir "^4.0.0" 605 | 606 | create-require@^1.1.0: 607 | version "1.1.1" 608 | resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333" 609 | integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ== 610 | 611 | crypto-random-string@^2.0.0: 612 | version "2.0.0" 613 | resolved "https://registry.yarnpkg.com/crypto-random-string/-/crypto-random-string-2.0.0.tgz#ef2a7a966ec11083388369baa02ebead229b30d5" 614 | integrity sha512-v1plID3y9r/lPhviJ1wrXpLeyUIGAZ2SHNYTEapm7/8A9nLPoyvVp3RK/EPFqn5kEznyWgYZNsRtYYIWbuG8KA== 615 | 616 | date-and-time@^0.14.0: 617 | version "0.14.2" 618 | resolved "https://registry.yarnpkg.com/date-and-time/-/date-and-time-0.14.2.tgz#a4266c3dead460f6c231fe9674e585908dac354e" 619 | integrity sha512-EFTCh9zRSEpGPmJaexg7HTuzZHh6cnJj1ui7IGCFNXzd2QdpsNh05Db5TF3xzJm30YN+A8/6xHSuRcQqoc3kFA== 620 | 621 | debug@4, debug@4.3.1, debug@^4.1.0, debug@^4.1.1: 622 | version "4.3.1" 623 | resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.1.tgz#f0d229c505e0c6d8c49ac553d1b13dc183f6b2ee" 624 | integrity sha512-doEwdvm4PCeK4K3RQN2ZC2BYUBaxwLARCqZmMjtF8a51J2Rb0xpVloFRnCODwqjpwnAoao4pelN8l3RJdv3gRQ== 625 | dependencies: 626 | ms "2.1.2" 627 | 628 | decamelize@^1.2.0: 629 | version "1.2.0" 630 | resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-1.2.0.tgz#f6534d15148269b20352e7bee26f501f9a191290" 631 | integrity sha1-9lNNFRSCabIDUue+4m9QH5oZEpA= 632 | 633 | decamelize@^4.0.0: 634 | version "4.0.0" 635 | resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-4.0.0.tgz#aa472d7bf660eb15f3494efd531cab7f2a709837" 636 | integrity sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ== 637 | 638 | deep-eql@^3.0.1: 639 | version "3.0.1" 640 | resolved "https://registry.yarnpkg.com/deep-eql/-/deep-eql-3.0.1.tgz#dfc9404400ad1c8fe023e7da1df1c147c4b444df" 641 | integrity sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw== 642 | dependencies: 643 | type-detect "^4.0.0" 644 | 645 | dicer@^0.3.0: 646 | version "0.3.0" 647 | resolved "https://registry.yarnpkg.com/dicer/-/dicer-0.3.0.tgz#eacd98b3bfbf92e8ab5c2fdb71aaac44bb06b872" 648 | integrity sha512-MdceRRWqltEG2dZqO769g27N/3PXfcKl04VhYnBlo2YhH7zPi88VebsjTKclaOyiuMaGU72hTfw3VkUitGcVCA== 649 | dependencies: 650 | streamsearch "0.1.2" 651 | 652 | diff@5.0.0: 653 | version "5.0.0" 654 | resolved "https://registry.yarnpkg.com/diff/-/diff-5.0.0.tgz#7ed6ad76d859d030787ec35855f5b1daf31d852b" 655 | integrity sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w== 656 | 657 | diff@^4.0.1: 658 | version "4.0.2" 659 | resolved "https://registry.yarnpkg.com/diff/-/diff-4.0.2.tgz#60f3aecb89d5fae520c11aa19efc2bb982aade7d" 660 | integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A== 661 | 662 | dot-prop@^5.2.0: 663 | version "5.3.0" 664 | resolved "https://registry.yarnpkg.com/dot-prop/-/dot-prop-5.3.0.tgz#90ccce708cd9cd82cc4dc8c3ddd9abdd55b20e88" 665 | integrity sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q== 666 | dependencies: 667 | is-obj "^2.0.0" 668 | 669 | duplexify@^4.0.0, duplexify@^4.1.1: 670 | version "4.1.1" 671 | resolved "https://registry.yarnpkg.com/duplexify/-/duplexify-4.1.1.tgz#7027dc374f157b122a8ae08c2d3ea4d2d953aa61" 672 | integrity sha512-DY3xVEmVHTv1wSzKNbwoU6nVjzI369Y6sPoqfYr0/xlx3IdX2n94xIszTcjPO8W8ZIv0Wb0PXNcjuZyT4wiICA== 673 | dependencies: 674 | end-of-stream "^1.4.1" 675 | inherits "^2.0.3" 676 | readable-stream "^3.1.1" 677 | stream-shift "^1.0.0" 678 | 679 | ecdsa-sig-formatter@1.0.11, ecdsa-sig-formatter@^1.0.11: 680 | version "1.0.11" 681 | resolved "https://registry.yarnpkg.com/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz#ae0f0fa2d85045ef14a817daa3ce9acd0489e5bf" 682 | integrity sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ== 683 | dependencies: 684 | safe-buffer "^5.0.1" 685 | 686 | emoji-regex@^8.0.0: 687 | version "8.0.0" 688 | resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" 689 | integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== 690 | 691 | end-of-stream@^1.1.0, end-of-stream@^1.4.1: 692 | version "1.4.4" 693 | resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.4.tgz#5ae64a5f45057baf3626ec14da0ca5e4b2431eb0" 694 | integrity sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q== 695 | dependencies: 696 | once "^1.4.0" 697 | 698 | ent@^2.2.0: 699 | version "2.2.0" 700 | resolved "https://registry.yarnpkg.com/ent/-/ent-2.2.0.tgz#e964219325a21d05f44466a2f686ed6ce5f5dd1d" 701 | integrity sha1-6WQhkyWiHQX0RGai9obtbOX13R0= 702 | 703 | escalade@^3.1.1: 704 | version "3.1.1" 705 | resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" 706 | integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== 707 | 708 | escape-string-regexp@4.0.0: 709 | version "4.0.0" 710 | resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz#14ba83a5d373e3d311e5afca29cf5bfad965bf34" 711 | integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== 712 | 713 | escape-string-regexp@^1.0.5: 714 | version "1.0.5" 715 | resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" 716 | integrity sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ= 717 | 718 | esprima@^4.0.0: 719 | version "4.0.1" 720 | resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.1.tgz#13b04cdb3e6c5d19df91ab6987a8695619b0aa71" 721 | integrity sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A== 722 | 723 | event-target-shim@^5.0.0: 724 | version "5.0.1" 725 | resolved "https://registry.yarnpkg.com/event-target-shim/-/event-target-shim-5.0.1.tgz#5d4d3ebdf9583d63a5333ce2deb7480ab2b05789" 726 | integrity sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ== 727 | 728 | extend@^3.0.2: 729 | version "3.0.2" 730 | resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.2.tgz#f8b1136b4071fbd8eb140aff858b1019ec2915fa" 731 | integrity sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g== 732 | 733 | fast-deep-equal@^3.1.1: 734 | version "3.1.3" 735 | resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz#3a7d56b559d6cbc3eb512325244e619a65c6c525" 736 | integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== 737 | 738 | fast-text-encoding@^1.0.0: 739 | version "1.0.3" 740 | resolved "https://registry.yarnpkg.com/fast-text-encoding/-/fast-text-encoding-1.0.3.tgz#ec02ac8e01ab8a319af182dae2681213cfe9ce53" 741 | integrity sha512-dtm4QZH9nZtcDt8qJiOH9fcQd1NAgi+K1O2DbE6GG1PPCK/BWfOH3idCTRQ4ImXRUOyopDEgDEnVEE7Y/2Wrig== 742 | 743 | faye-websocket@0.11.3: 744 | version "0.11.3" 745 | resolved "https://registry.yarnpkg.com/faye-websocket/-/faye-websocket-0.11.3.tgz#5c0e9a8968e8912c286639fde977a8b209f2508e" 746 | integrity sha512-D2y4bovYpzziGgbHYtGCMjlJM36vAl/y+xUyn1C+FVx8szd1E+86KwVw6XvYSzOP8iMpm1X0I4xJD+QtUb36OA== 747 | dependencies: 748 | websocket-driver ">=0.5.1" 749 | 750 | fill-range@^7.0.1: 751 | version "7.0.1" 752 | resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" 753 | integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== 754 | dependencies: 755 | to-regex-range "^5.0.1" 756 | 757 | find-up@5.0.0: 758 | version "5.0.0" 759 | resolved "https://registry.yarnpkg.com/find-up/-/find-up-5.0.0.tgz#4c92819ecb7083561e4f4a240a86be5198f536fc" 760 | integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== 761 | dependencies: 762 | locate-path "^6.0.0" 763 | path-exists "^4.0.0" 764 | 765 | find-up@^4.1.0: 766 | version "4.1.0" 767 | resolved "https://registry.yarnpkg.com/find-up/-/find-up-4.1.0.tgz#97afe7d6cdc0bc5928584b7c8d7b16e8a9aa5d19" 768 | integrity sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw== 769 | dependencies: 770 | locate-path "^5.0.0" 771 | path-exists "^4.0.0" 772 | 773 | firebase-admin@^9.8.0: 774 | version "9.8.0" 775 | resolved "https://registry.yarnpkg.com/firebase-admin/-/firebase-admin-9.8.0.tgz#d54d1acdd2e1117e59b7d74cb467ef3d18f3aa7a" 776 | integrity sha512-v8B1qU8McZZT2hlLZ018TKz2FoKlfFkZq9mOIyzN7wJUOlAywqQX0JyqNpVGyPeU+B+77ojlvmkGTNXt2OFkgw== 777 | dependencies: 778 | "@firebase/database" "^0.10.0" 779 | "@firebase/database-types" "^0.7.2" 780 | "@types/node" ">=12.12.47" 781 | dicer "^0.3.0" 782 | jsonwebtoken "^8.5.1" 783 | jwks-rsa "^2.0.2" 784 | node-forge "^0.10.0" 785 | optionalDependencies: 786 | "@google-cloud/firestore" "^4.5.0" 787 | "@google-cloud/storage" "^5.3.0" 788 | 789 | firestore-export-import@^0.15.0: 790 | version "0.15.0" 791 | resolved "https://registry.yarnpkg.com/firestore-export-import/-/firestore-export-import-0.15.0.tgz#331e60f4c81d91f869a06aa98402513908447a36" 792 | integrity sha512-zUnbwNJ2YItLUZTJHIR7i5uRfoOGY5thaAwtYvhtDyL47meyQ7DWL1sm2/bIloZ09hS0AmSex0YxFrhsZeTKMQ== 793 | dependencies: 794 | firebase-admin "^9.8.0" 795 | 796 | flat@^5.0.2: 797 | version "5.0.2" 798 | resolved "https://registry.yarnpkg.com/flat/-/flat-5.0.2.tgz#8ca6fe332069ffa9d324c327198c598259ceb241" 799 | integrity sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ== 800 | 801 | fs.realpath@^1.0.0: 802 | version "1.0.0" 803 | resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" 804 | integrity sha1-FQStJSMVjKpA20onh8sBQRmU6k8= 805 | 806 | fsevents@~2.3.1: 807 | version "2.3.2" 808 | resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.2.tgz#8a526f78b8fdf4623b709e0b975c52c24c02fd1a" 809 | integrity sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA== 810 | 811 | function-bind@^1.1.1: 812 | version "1.1.1" 813 | resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.1.tgz#a56899d3ea3c9bab874bb9773b7c5ede92f4895d" 814 | integrity sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A== 815 | 816 | functional-red-black-tree@^1.0.1: 817 | version "1.0.1" 818 | resolved "https://registry.yarnpkg.com/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz#1b0ab3bd553b2a0d6399d29c0e3ea0b252078327" 819 | integrity sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc= 820 | 821 | gaxios@^3.0.0: 822 | version "3.2.0" 823 | resolved "https://registry.yarnpkg.com/gaxios/-/gaxios-3.2.0.tgz#11b6f0e8fb08d94a10d4d58b044ad3bec6dd486a" 824 | integrity sha512-+6WPeVzPvOshftpxJwRi2Ozez80tn/hdtOUag7+gajDHRJvAblKxTFSSMPtr2hmnLy7p0mvYz0rMXLBl8pSO7Q== 825 | dependencies: 826 | abort-controller "^3.0.0" 827 | extend "^3.0.2" 828 | https-proxy-agent "^5.0.0" 829 | is-stream "^2.0.0" 830 | node-fetch "^2.3.0" 831 | 832 | gaxios@^4.0.0: 833 | version "4.0.1" 834 | resolved "https://registry.yarnpkg.com/gaxios/-/gaxios-4.0.1.tgz#bc7b205a89d883452822cc75e138620c35e3291e" 835 | integrity sha512-jOin8xRZ/UytQeBpSXFqIzqU7Fi5TqgPNLlUsSB8kjJ76+FiGBfImF8KJu++c6J4jOldfJUtt0YmkRj2ZpSHTQ== 836 | dependencies: 837 | abort-controller "^3.0.0" 838 | extend "^3.0.2" 839 | https-proxy-agent "^5.0.0" 840 | is-stream "^2.0.0" 841 | node-fetch "^2.3.0" 842 | 843 | gcp-metadata@^4.2.0: 844 | version "4.2.1" 845 | resolved "https://registry.yarnpkg.com/gcp-metadata/-/gcp-metadata-4.2.1.tgz#31849fbcf9025ef34c2297c32a89a1e7e9f2cd62" 846 | integrity sha512-tSk+REe5iq/N+K+SK1XjZJUrFPuDqGZVzCy2vocIHIGmPlTGsa8owXMJwGkrXr73NO0AzhPW4MF2DEHz7P2AVw== 847 | dependencies: 848 | gaxios "^4.0.0" 849 | json-bigint "^1.0.0" 850 | 851 | gcs-resumable-upload@^3.1.0: 852 | version "3.1.1" 853 | resolved "https://registry.yarnpkg.com/gcs-resumable-upload/-/gcs-resumable-upload-3.1.1.tgz#67c766a0555d6a352f9651b7603337207167d0de" 854 | integrity sha512-RS1osvAicj9+MjCc6jAcVL1Pt3tg7NK2C2gXM5nqD1Gs0klF2kj5nnAFSBy97JrtslMIQzpb7iSuxaG8rFWd2A== 855 | dependencies: 856 | abort-controller "^3.0.0" 857 | configstore "^5.0.0" 858 | extend "^3.0.2" 859 | gaxios "^3.0.0" 860 | google-auth-library "^6.0.0" 861 | pumpify "^2.0.0" 862 | stream-events "^1.0.4" 863 | 864 | get-caller-file@^2.0.1, get-caller-file@^2.0.5: 865 | version "2.0.5" 866 | resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.5.tgz#4f94412a82db32f36e3b0b9741f8a97feb031f7e" 867 | integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== 868 | 869 | get-func-name@^2.0.0: 870 | version "2.0.0" 871 | resolved "https://registry.yarnpkg.com/get-func-name/-/get-func-name-2.0.0.tgz#ead774abee72e20409433a066366023dd6887a41" 872 | integrity sha1-6td0q+5y4gQJQzoGY2YCPdaIekE= 873 | 874 | get-stream@^6.0.0: 875 | version "6.0.0" 876 | resolved "https://registry.yarnpkg.com/get-stream/-/get-stream-6.0.0.tgz#3e0012cb6827319da2706e601a1583e8629a6718" 877 | integrity sha512-A1B3Bh1UmL0bidM/YX2NsCOTnGJePL9rO/M+Mw3m9f2gUpfokS0hi5Eah0WSUEWZdZhIZtMjkIYS7mDfOqNHbg== 878 | 879 | glob-parent@~5.1.0: 880 | version "5.1.1" 881 | resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.1.tgz#b6c1ef417c4e5663ea498f1c45afac6916bbc229" 882 | integrity sha512-FnI+VGOpnlGHWZxthPGR+QhR78fuiK0sNLkHQv+bL9fQi57lNNdquIbna/WrfROrolq8GK5Ek6BiMwqL/voRYQ== 883 | dependencies: 884 | is-glob "^4.0.1" 885 | 886 | glob@7.1.6, glob@^7.1.1: 887 | version "7.1.6" 888 | resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.6.tgz#141f33b81a7c2492e125594307480c46679278a6" 889 | integrity sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA== 890 | dependencies: 891 | fs.realpath "^1.0.0" 892 | inflight "^1.0.4" 893 | inherits "2" 894 | minimatch "^3.0.4" 895 | once "^1.3.0" 896 | path-is-absolute "^1.0.0" 897 | 898 | google-auth-library@^6.0.0, google-auth-library@^6.1.1, google-auth-library@^6.1.3: 899 | version "6.1.3" 900 | resolved "https://registry.yarnpkg.com/google-auth-library/-/google-auth-library-6.1.3.tgz#39d868140b70d0c4b32c6f6d8f4ccc1400d84dca" 901 | integrity sha512-m9mwvY3GWbr7ZYEbl61isWmk+fvTmOt0YNUfPOUY2VH8K5pZlAIWJjxEi0PqR3OjMretyiQLI6GURMrPSwHQ2g== 902 | dependencies: 903 | arrify "^2.0.0" 904 | base64-js "^1.3.0" 905 | ecdsa-sig-formatter "^1.0.11" 906 | fast-text-encoding "^1.0.0" 907 | gaxios "^4.0.0" 908 | gcp-metadata "^4.2.0" 909 | gtoken "^5.0.4" 910 | jws "^4.0.0" 911 | lru-cache "^6.0.0" 912 | 913 | google-gax@^2.9.2: 914 | version "2.9.2" 915 | resolved "https://registry.yarnpkg.com/google-gax/-/google-gax-2.9.2.tgz#780b2c0fc031c864007e1e198a9b90c7e946cca0" 916 | integrity sha512-Pve4osEzNKpBZqFXMfGKBbKCtgnHpUe5IQMh5Ou+Xtg8nLcba94L3gF0xgM5phMdGRRqJn0SMjcuEVmOYu7EBg== 917 | dependencies: 918 | "@grpc/grpc-js" "~1.1.1" 919 | "@grpc/proto-loader" "^0.5.1" 920 | "@types/long" "^4.0.0" 921 | abort-controller "^3.0.0" 922 | duplexify "^4.0.0" 923 | google-auth-library "^6.1.3" 924 | is-stream-ended "^0.1.4" 925 | node-fetch "^2.6.1" 926 | protobufjs "^6.9.0" 927 | retry-request "^4.0.0" 928 | 929 | google-p12-pem@^3.0.3: 930 | version "3.0.3" 931 | resolved "https://registry.yarnpkg.com/google-p12-pem/-/google-p12-pem-3.0.3.tgz#673ac3a75d3903a87f05878f3c75e06fc151669e" 932 | integrity sha512-wS0ek4ZtFx/ACKYF3JhyGe5kzH7pgiQ7J5otlumqR9psmWMYc+U9cErKlCYVYHoUaidXHdZ2xbo34kB+S+24hA== 933 | dependencies: 934 | node-forge "^0.10.0" 935 | 936 | graceful-fs@^4.1.2: 937 | version "4.2.4" 938 | resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.4.tgz#2256bde14d3632958c465ebc96dc467ca07a29fb" 939 | integrity sha512-WjKPNJF79dtJAVniUlGGWHYGz2jWxT6VhN/4m1NdkbZ2nOsEF+cI1Edgql5zCRhs/VsQYRvrXctxktVXZUkixw== 940 | 941 | growl@1.10.5: 942 | version "1.10.5" 943 | resolved "https://registry.yarnpkg.com/growl/-/growl-1.10.5.tgz#f2735dc2283674fa67478b10181059355c369e5e" 944 | integrity sha512-qBr4OuELkhPenW6goKVXiv47US3clb3/IbuWF9KNKEijAy9oeHxU9IgzjvJhHkUzhaj7rOUD7+YGWqUjLp5oSA== 945 | 946 | gtoken@^5.0.4: 947 | version "5.1.0" 948 | resolved "https://registry.yarnpkg.com/gtoken/-/gtoken-5.1.0.tgz#4ba8d2fc9a8459098f76e7e8fd7beaa39fda9fe4" 949 | integrity sha512-4d8N6Lk8TEAHl9vVoRVMh9BNOKWVgl2DdNtr3428O75r3QFrF/a5MMu851VmK0AA8+iSvbwRv69k5XnMLURGhg== 950 | dependencies: 951 | gaxios "^4.0.0" 952 | google-p12-pem "^3.0.3" 953 | jws "^4.0.0" 954 | mime "^2.2.0" 955 | 956 | has-flag@^3.0.0: 957 | version "3.0.0" 958 | resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" 959 | integrity sha1-tdRU3CGZriJWmfNGfloH87lVuv0= 960 | 961 | has-flag@^4.0.0: 962 | version "4.0.0" 963 | resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" 964 | integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== 965 | 966 | has@^1.0.3: 967 | version "1.0.3" 968 | resolved "https://registry.yarnpkg.com/has/-/has-1.0.3.tgz#722d7cbfc1f6aa8241f16dd814e011e1f41e8796" 969 | integrity sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw== 970 | dependencies: 971 | function-bind "^1.1.1" 972 | 973 | hash-stream-validation@^0.2.2: 974 | version "0.2.4" 975 | resolved "https://registry.yarnpkg.com/hash-stream-validation/-/hash-stream-validation-0.2.4.tgz#ee68b41bf822f7f44db1142ec28ba9ee7ccb7512" 976 | integrity sha512-Gjzu0Xn7IagXVkSu9cSFuK1fqzwtLwFhNhVL8IFJijRNMgUttFbBSIAzKuSIrsFMO1+g1RlsoN49zPIbwPDMGQ== 977 | 978 | he@1.2.0: 979 | version "1.2.0" 980 | resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f" 981 | integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw== 982 | 983 | http-parser-js@>=0.5.1: 984 | version "0.5.2" 985 | resolved "https://registry.yarnpkg.com/http-parser-js/-/http-parser-js-0.5.2.tgz#da2e31d237b393aae72ace43882dd7e270a8ff77" 986 | integrity sha512-opCO9ASqg5Wy2FNo7A0sxy71yGbbkJJXLdgMK04Tcypw9jr2MgWbyubb0+WdmDmGnFflO7fRbqbaihh/ENDlRQ== 987 | 988 | http-proxy-agent@^4.0.0: 989 | version "4.0.1" 990 | resolved "https://registry.yarnpkg.com/http-proxy-agent/-/http-proxy-agent-4.0.1.tgz#8a8c8ef7f5932ccf953c296ca8291b95aa74aa3a" 991 | integrity sha512-k0zdNgqWTGA6aeIRVpvfVob4fL52dTfaehylg0Y4UvSySvOq/Y+BOyPrgpUrA7HylqvU8vIZGsRuXmspskV0Tg== 992 | dependencies: 993 | "@tootallnate/once" "1" 994 | agent-base "6" 995 | debug "4" 996 | 997 | https-proxy-agent@^5.0.0: 998 | version "5.0.0" 999 | resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.0.tgz#e2a90542abb68a762e0a0850f6c9edadfd8506b2" 1000 | integrity sha512-EkYm5BcKUGiduxzSt3Eppko+PiNWNEpa4ySk9vTC6wDsQJW9rHSa+UhGNJoRYp7bz6Ht1eaRIa6QaJqO5rCFbA== 1001 | dependencies: 1002 | agent-base "6" 1003 | debug "4" 1004 | 1005 | imurmurhash@^0.1.4: 1006 | version "0.1.4" 1007 | resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea" 1008 | integrity sha1-khi5srkoojixPcT7a21XbyMUU+o= 1009 | 1010 | inflight@^1.0.4: 1011 | version "1.0.6" 1012 | resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" 1013 | integrity sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk= 1014 | dependencies: 1015 | once "^1.3.0" 1016 | wrappy "1" 1017 | 1018 | inherits@2, inherits@^2.0.3: 1019 | version "2.0.4" 1020 | resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" 1021 | integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== 1022 | 1023 | is-binary-path@~2.1.0: 1024 | version "2.1.0" 1025 | resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09" 1026 | integrity sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw== 1027 | dependencies: 1028 | binary-extensions "^2.0.0" 1029 | 1030 | is-core-module@^2.1.0: 1031 | version "2.1.0" 1032 | resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.1.0.tgz#a4cc031d9b1aca63eecbd18a650e13cb4eeab946" 1033 | integrity sha512-YcV7BgVMRFRua2FqQzKtTDMz8iCuLEyGKjr70q8Zm1yy2qKcurbFEd79PAdHV77oL3NrAaOVQIbMmiHQCHB7ZA== 1034 | dependencies: 1035 | has "^1.0.3" 1036 | 1037 | is-extglob@^2.1.1: 1038 | version "2.1.1" 1039 | resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" 1040 | integrity sha1-qIwCU1eR8C7TfHahueqXc8gz+MI= 1041 | 1042 | is-fullwidth-code-point@^2.0.0: 1043 | version "2.0.0" 1044 | resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz#a3b30a5c4f199183167aaab93beefae3ddfb654f" 1045 | integrity sha1-o7MKXE8ZkYMWeqq5O+764937ZU8= 1046 | 1047 | is-fullwidth-code-point@^3.0.0: 1048 | version "3.0.0" 1049 | resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" 1050 | integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== 1051 | 1052 | is-glob@^4.0.1, is-glob@~4.0.1: 1053 | version "4.0.1" 1054 | resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.1.tgz#7567dbe9f2f5e2467bc77ab83c4a29482407a5dc" 1055 | integrity sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg== 1056 | dependencies: 1057 | is-extglob "^2.1.1" 1058 | 1059 | is-number@^7.0.0: 1060 | version "7.0.0" 1061 | resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" 1062 | integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== 1063 | 1064 | is-obj@^2.0.0: 1065 | version "2.0.0" 1066 | resolved "https://registry.yarnpkg.com/is-obj/-/is-obj-2.0.0.tgz#473fb05d973705e3fd9620545018ca8e22ef4982" 1067 | integrity sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w== 1068 | 1069 | is-plain-obj@^2.1.0: 1070 | version "2.1.0" 1071 | resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-2.1.0.tgz#45e42e37fccf1f40da8e5f76ee21515840c09287" 1072 | integrity sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA== 1073 | 1074 | is-stream-ended@^0.1.4: 1075 | version "0.1.4" 1076 | resolved "https://registry.yarnpkg.com/is-stream-ended/-/is-stream-ended-0.1.4.tgz#f50224e95e06bce0e356d440a4827cd35b267eda" 1077 | integrity sha512-xj0XPvmr7bQFTvirqnFr50o0hQIh6ZItDqloxt5aJrR4NQsYeSsyFQERYGCAzfindAcnKjINnwEEgLx4IqVzQw== 1078 | 1079 | is-stream@^2.0.0: 1080 | version "2.0.0" 1081 | resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-2.0.0.tgz#bde9c32680d6fae04129d6ac9d921ce7815f78e3" 1082 | integrity sha512-XCoy+WlUr7d1+Z8GgSuXmpuUFC9fOhRXglJMx+dwLKTkL44Cjd4W1Z5P+BQZpr+cR93aGP4S/s7Ftw6Nd/kiEw== 1083 | 1084 | is-typedarray@^1.0.0: 1085 | version "1.0.0" 1086 | resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a" 1087 | integrity sha1-5HnICFjfDBsR3dppQPlgEfzaSpo= 1088 | 1089 | isexe@^2.0.0: 1090 | version "2.0.0" 1091 | resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10" 1092 | integrity sha1-6PvzdNxVb/iUehDcsFctYz8s+hA= 1093 | 1094 | jose@^2.0.5: 1095 | version "2.0.5" 1096 | resolved "https://registry.yarnpkg.com/jose/-/jose-2.0.5.tgz#29746a18d9fff7dcf9d5d2a6f62cb0c7cd27abd3" 1097 | integrity sha512-BAiDNeDKTMgk4tvD0BbxJ8xHEHBZgpeRZ1zGPPsitSyMgjoMWiLGYAE7H7NpP5h0lPppQajQs871E8NHUrzVPA== 1098 | dependencies: 1099 | "@panva/asn1.js" "^1.0.0" 1100 | 1101 | js-tokens@^4.0.0: 1102 | version "4.0.0" 1103 | resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499" 1104 | integrity sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ== 1105 | 1106 | js-yaml@4.0.0: 1107 | version "4.0.0" 1108 | resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-4.0.0.tgz#f426bc0ff4b4051926cd588c71113183409a121f" 1109 | integrity sha512-pqon0s+4ScYUvX30wxQi3PogGFAlUyH0awepWvwkj4jD4v+ova3RiYw8bmA6x2rDrEaj8i/oWKoRxpVNW+Re8Q== 1110 | dependencies: 1111 | argparse "^2.0.1" 1112 | 1113 | js-yaml@^3.13.1: 1114 | version "3.14.0" 1115 | resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.14.0.tgz#a7a34170f26a21bb162424d8adacb4113a69e482" 1116 | integrity sha512-/4IbIeHcD9VMHFqDR/gQ7EdZdLimOvW2DdcxFjdyyZ9NsbS+ccrXqVWDtab/lRl5AlUqmpBx8EhPaWR+OtY17A== 1117 | dependencies: 1118 | argparse "^1.0.7" 1119 | esprima "^4.0.0" 1120 | 1121 | jsmin@^1.0.1: 1122 | version "1.0.1" 1123 | resolved "https://registry.yarnpkg.com/jsmin/-/jsmin-1.0.1.tgz#e7bd0dcd6496c3bf4863235bf461a3d98aa3b98c" 1124 | integrity sha1-570NzWSWw79IYyNb9GGj2YqjuYw= 1125 | 1126 | json-bigint@^1.0.0: 1127 | version "1.0.0" 1128 | resolved "https://registry.yarnpkg.com/json-bigint/-/json-bigint-1.0.0.tgz#ae547823ac0cad8398667f8cd9ef4730f5b01ff1" 1129 | integrity sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ== 1130 | dependencies: 1131 | bignumber.js "^9.0.0" 1132 | 1133 | jsonwebtoken@^8.5.1: 1134 | version "8.5.1" 1135 | resolved "https://registry.yarnpkg.com/jsonwebtoken/-/jsonwebtoken-8.5.1.tgz#00e71e0b8df54c2121a1f26137df2280673bcc0d" 1136 | integrity sha512-XjwVfRS6jTMsqYs0EsuJ4LGxXV14zQybNd4L2r0UvbVnSF9Af8x7p5MzbJ90Ioz/9TI41/hTCvznF/loiSzn8w== 1137 | dependencies: 1138 | jws "^3.2.2" 1139 | lodash.includes "^4.3.0" 1140 | lodash.isboolean "^3.0.3" 1141 | lodash.isinteger "^4.0.4" 1142 | lodash.isnumber "^3.0.3" 1143 | lodash.isplainobject "^4.0.6" 1144 | lodash.isstring "^4.0.1" 1145 | lodash.once "^4.0.0" 1146 | ms "^2.1.1" 1147 | semver "^5.6.0" 1148 | 1149 | jwa@^1.4.1: 1150 | version "1.4.1" 1151 | resolved "https://registry.yarnpkg.com/jwa/-/jwa-1.4.1.tgz#743c32985cb9e98655530d53641b66c8645b039a" 1152 | integrity sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA== 1153 | dependencies: 1154 | buffer-equal-constant-time "1.0.1" 1155 | ecdsa-sig-formatter "1.0.11" 1156 | safe-buffer "^5.0.1" 1157 | 1158 | jwa@^2.0.0: 1159 | version "2.0.0" 1160 | resolved "https://registry.yarnpkg.com/jwa/-/jwa-2.0.0.tgz#a7e9c3f29dae94027ebcaf49975c9345593410fc" 1161 | integrity sha512-jrZ2Qx916EA+fq9cEAeCROWPTfCwi1IVHqT2tapuqLEVVDKFDENFw1oL+MwrTvH6msKxsd1YTDVw6uKEcsrLEA== 1162 | dependencies: 1163 | buffer-equal-constant-time "1.0.1" 1164 | ecdsa-sig-formatter "1.0.11" 1165 | safe-buffer "^5.0.1" 1166 | 1167 | jwks-rsa@^2.0.2: 1168 | version "2.0.3" 1169 | resolved "https://registry.yarnpkg.com/jwks-rsa/-/jwks-rsa-2.0.3.tgz#4059f25e27f1d9cb5681dd12a98e46f8aa39fcbd" 1170 | integrity sha512-/rkjXRWAp0cS00tunsHResw68P5iTQru8+jHufLNv3JHc4nObFEndfEUSuPugh09N+V9XYxKUqi7QrkmCHSSSg== 1171 | dependencies: 1172 | "@types/express-jwt" "0.0.42" 1173 | debug "^4.1.0" 1174 | jose "^2.0.5" 1175 | limiter "^1.1.5" 1176 | lru-memoizer "^2.1.2" 1177 | 1178 | jws@^3.2.2: 1179 | version "3.2.2" 1180 | resolved "https://registry.yarnpkg.com/jws/-/jws-3.2.2.tgz#001099f3639468c9414000e99995fa52fb478304" 1181 | integrity sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA== 1182 | dependencies: 1183 | jwa "^1.4.1" 1184 | safe-buffer "^5.0.1" 1185 | 1186 | jws@^4.0.0: 1187 | version "4.0.0" 1188 | resolved "https://registry.yarnpkg.com/jws/-/jws-4.0.0.tgz#2d4e8cf6a318ffaa12615e9dec7e86e6c97310f4" 1189 | integrity sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg== 1190 | dependencies: 1191 | jwa "^2.0.0" 1192 | safe-buffer "^5.0.1" 1193 | 1194 | limiter@^1.1.5: 1195 | version "1.1.5" 1196 | resolved "https://registry.yarnpkg.com/limiter/-/limiter-1.1.5.tgz#8f92a25b3b16c6131293a0cc834b4a838a2aa7c2" 1197 | integrity sha512-FWWMIEOxz3GwUI4Ts/IvgVy6LPvoMPgjMdQ185nN6psJyBJ4yOpzqm695/h5umdLJg2vW3GR5iG11MAkR2AzJA== 1198 | 1199 | locate-path@^5.0.0: 1200 | version "5.0.0" 1201 | resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-5.0.0.tgz#1afba396afd676a6d42504d0a67a3a7eb9f62aa0" 1202 | integrity sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g== 1203 | dependencies: 1204 | p-locate "^4.1.0" 1205 | 1206 | locate-path@^6.0.0: 1207 | version "6.0.0" 1208 | resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-6.0.0.tgz#55321eb309febbc59c4801d931a72452a681d286" 1209 | integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== 1210 | dependencies: 1211 | p-locate "^5.0.0" 1212 | 1213 | lodash.camelcase@^4.3.0: 1214 | version "4.3.0" 1215 | resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6" 1216 | integrity sha1-soqmKIorn8ZRA1x3EfZathkDMaY= 1217 | 1218 | lodash.clonedeep@^4.5.0: 1219 | version "4.5.0" 1220 | resolved "https://registry.yarnpkg.com/lodash.clonedeep/-/lodash.clonedeep-4.5.0.tgz#e23f3f9c4f8fbdde872529c1071857a086e5ccef" 1221 | integrity sha1-4j8/nE+Pvd6HJSnBBxhXoIblzO8= 1222 | 1223 | lodash.includes@^4.3.0: 1224 | version "4.3.0" 1225 | resolved "https://registry.yarnpkg.com/lodash.includes/-/lodash.includes-4.3.0.tgz#60bb98a87cb923c68ca1e51325483314849f553f" 1226 | integrity sha1-YLuYqHy5I8aMoeUTJUgzFISfVT8= 1227 | 1228 | lodash.isboolean@^3.0.3: 1229 | version "3.0.3" 1230 | resolved "https://registry.yarnpkg.com/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz#6c2e171db2a257cd96802fd43b01b20d5f5870f6" 1231 | integrity sha1-bC4XHbKiV82WgC/UOwGyDV9YcPY= 1232 | 1233 | lodash.isinteger@^4.0.4: 1234 | version "4.0.4" 1235 | resolved "https://registry.yarnpkg.com/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz#619c0af3d03f8b04c31f5882840b77b11cd68343" 1236 | integrity sha1-YZwK89A/iwTDH1iChAt3sRzWg0M= 1237 | 1238 | lodash.isnumber@^3.0.3: 1239 | version "3.0.3" 1240 | resolved "https://registry.yarnpkg.com/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz#3ce76810c5928d03352301ac287317f11c0b1ffc" 1241 | integrity sha1-POdoEMWSjQM1IwGsKHMX8RwLH/w= 1242 | 1243 | lodash.isplainobject@^4.0.6: 1244 | version "4.0.6" 1245 | resolved "https://registry.yarnpkg.com/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz#7c526a52d89b45c45cc690b88163be0497f550cb" 1246 | integrity sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs= 1247 | 1248 | lodash.isstring@^4.0.1: 1249 | version "4.0.1" 1250 | resolved "https://registry.yarnpkg.com/lodash.isstring/-/lodash.isstring-4.0.1.tgz#d527dfb5456eca7cc9bb95d5daeaf88ba54a5451" 1251 | integrity sha1-1SfftUVuynzJu5XV2ur4i6VKVFE= 1252 | 1253 | lodash.once@^4.0.0: 1254 | version "4.1.1" 1255 | resolved "https://registry.yarnpkg.com/lodash.once/-/lodash.once-4.1.1.tgz#0dd3971213c7c56df880977d504c88fb471a97ac" 1256 | integrity sha1-DdOXEhPHxW34gJd9UEyI+0cal6w= 1257 | 1258 | log-symbols@4.0.0: 1259 | version "4.0.0" 1260 | resolved "https://registry.yarnpkg.com/log-symbols/-/log-symbols-4.0.0.tgz#69b3cc46d20f448eccdb75ea1fa733d9e821c920" 1261 | integrity sha512-FN8JBzLx6CzeMrB0tg6pqlGU1wCrXW+ZXGH481kfsBqer0hToTIiHdjH4Mq8xJUbvATujKCvaREGWpGUionraA== 1262 | dependencies: 1263 | chalk "^4.0.0" 1264 | 1265 | long@^4.0.0: 1266 | version "4.0.0" 1267 | resolved "https://registry.yarnpkg.com/long/-/long-4.0.0.tgz#9a7b71cfb7d361a194ea555241c92f7468d5bf28" 1268 | integrity sha512-XsP+KhQif4bjX1kbuSiySJFNAehNxgLb6hPRGJ9QsUr8ajHkuXGdrHmFUTUUXhDwVX2R5bY4JNZEwbUiMhV+MA== 1269 | 1270 | lru-cache@^6.0.0: 1271 | version "6.0.0" 1272 | resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" 1273 | integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== 1274 | dependencies: 1275 | yallist "^4.0.0" 1276 | 1277 | lru-cache@~4.0.0: 1278 | version "4.0.2" 1279 | resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-4.0.2.tgz#1d17679c069cda5d040991a09dbc2c0db377e55e" 1280 | integrity sha1-HRdnnAac2l0ECZGgnbwsDbN35V4= 1281 | dependencies: 1282 | pseudomap "^1.0.1" 1283 | yallist "^2.0.0" 1284 | 1285 | lru-memoizer@^2.1.2: 1286 | version "2.1.4" 1287 | resolved "https://registry.yarnpkg.com/lru-memoizer/-/lru-memoizer-2.1.4.tgz#b864d92b557f00b1eeb322156a0409cb06dafac6" 1288 | integrity sha512-IXAq50s4qwrOBrXJklY+KhgZF+5y98PDaNo0gi/v2KQBFLyWr+JyFvijZXkGKjQj/h9c0OwoE+JZbwUXce76hQ== 1289 | dependencies: 1290 | lodash.clonedeep "^4.5.0" 1291 | lru-cache "~4.0.0" 1292 | 1293 | make-dir@^3.0.0: 1294 | version "3.1.0" 1295 | resolved "https://registry.yarnpkg.com/make-dir/-/make-dir-3.1.0.tgz#415e967046b3a7f1d185277d84aa58203726a13f" 1296 | integrity sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw== 1297 | dependencies: 1298 | semver "^6.0.0" 1299 | 1300 | make-error@^1.1.1: 1301 | version "1.3.6" 1302 | resolved "https://registry.yarnpkg.com/make-error/-/make-error-1.3.6.tgz#2eb2e37ea9b67c4891f684a1394799af484cf7a2" 1303 | integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw== 1304 | 1305 | mime-db@1.44.0: 1306 | version "1.44.0" 1307 | resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.44.0.tgz#fa11c5eb0aca1334b4233cb4d52f10c5a6272f92" 1308 | integrity sha512-/NOTfLrsPBVeH7YtFPgsVWveuL+4SjjYxaQ1xtM1KMFj7HdxlBlxeyNLzhyJVx7r4rZGJAZ/6lkKCitSc/Nmpg== 1309 | 1310 | "mime-db@>= 1.43.0 < 2": 1311 | version "1.45.0" 1312 | resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.45.0.tgz#cceeda21ccd7c3a745eba2decd55d4b73e7879ea" 1313 | integrity sha512-CkqLUxUk15hofLoLyljJSrukZi8mAtgd+yE5uO4tqRZsdsAJKv0O+rFMhVDRJgozy+yG6md5KwuXhD4ocIoP+w== 1314 | 1315 | mime-types@^2.0.8: 1316 | version "2.1.27" 1317 | resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.27.tgz#47949f98e279ea53119f5722e0f34e529bec009f" 1318 | integrity sha512-JIhqnCasI9yD+SsmkquHBxTSEuZdQX5BuQnS2Vc7puQQQ+8yiP5AY5uWhpdv4YL4VM5c6iliiYWPgJ/nJQLp7w== 1319 | dependencies: 1320 | mime-db "1.44.0" 1321 | 1322 | mime@^2.2.0: 1323 | version "2.4.6" 1324 | resolved "https://registry.yarnpkg.com/mime/-/mime-2.4.6.tgz#e5b407c90db442f2beb5b162373d07b69affa4d1" 1325 | integrity sha512-RZKhC3EmpBchfTGBVb8fb+RL2cWyw/32lshnsETttkBAyAUXSGHxbEJWWRXc751DrIxG1q04b8QwMbAwkRPpUA== 1326 | 1327 | mimic-fn@^2.1.0: 1328 | version "2.1.0" 1329 | resolved "https://registry.yarnpkg.com/mimic-fn/-/mimic-fn-2.1.0.tgz#7ed2c2ccccaf84d3ffcb7a69b57711fc2083401b" 1330 | integrity sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg== 1331 | 1332 | minimatch@3.0.4, minimatch@^3.0.4: 1333 | version "3.0.4" 1334 | resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083" 1335 | integrity sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA== 1336 | dependencies: 1337 | brace-expansion "^1.1.7" 1338 | 1339 | minimist@^1.2.5: 1340 | version "1.2.5" 1341 | resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.5.tgz#67d66014b66a6a8aaa0c083c5fd58df4e4e97602" 1342 | integrity sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw== 1343 | 1344 | mkdirp@^0.5.3: 1345 | version "0.5.5" 1346 | resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.5.tgz#d91cefd62d1436ca0f41620e251288d420099def" 1347 | integrity sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ== 1348 | dependencies: 1349 | minimist "^1.2.5" 1350 | 1351 | mocha@^8.4.0: 1352 | version "8.4.0" 1353 | resolved "https://registry.yarnpkg.com/mocha/-/mocha-8.4.0.tgz#677be88bf15980a3cae03a73e10a0fc3997f0cff" 1354 | integrity sha512-hJaO0mwDXmZS4ghXsvPVriOhsxQ7ofcpQdm8dE+jISUOKopitvnXFQmpRR7jd2K6VBG6E26gU3IAbXXGIbu4sQ== 1355 | dependencies: 1356 | "@ungap/promise-all-settled" "1.1.2" 1357 | ansi-colors "4.1.1" 1358 | browser-stdout "1.3.1" 1359 | chokidar "3.5.1" 1360 | debug "4.3.1" 1361 | diff "5.0.0" 1362 | escape-string-regexp "4.0.0" 1363 | find-up "5.0.0" 1364 | glob "7.1.6" 1365 | growl "1.10.5" 1366 | he "1.2.0" 1367 | js-yaml "4.0.0" 1368 | log-symbols "4.0.0" 1369 | minimatch "3.0.4" 1370 | ms "2.1.3" 1371 | nanoid "3.1.20" 1372 | serialize-javascript "5.0.1" 1373 | strip-json-comments "3.1.1" 1374 | supports-color "8.1.1" 1375 | which "2.0.2" 1376 | wide-align "1.1.3" 1377 | workerpool "6.1.0" 1378 | yargs "16.2.0" 1379 | yargs-parser "20.2.4" 1380 | yargs-unparser "2.0.0" 1381 | 1382 | ms@2.1.2, ms@^2.1.1: 1383 | version "2.1.2" 1384 | resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009" 1385 | integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== 1386 | 1387 | ms@2.1.3: 1388 | version "2.1.3" 1389 | resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2" 1390 | integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA== 1391 | 1392 | nanoid@3.1.20: 1393 | version "3.1.20" 1394 | resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.1.20.tgz#badc263c6b1dcf14b71efaa85f6ab4c1d6cfc788" 1395 | integrity sha512-a1cQNyczgKbLX9jwbS/+d7W8fX/RfgYR7lVWwWOGIPNgK2m0MWvrGF6/m4kk6U3QcFMnZf3RIhL0v2Jgh/0Uxw== 1396 | 1397 | node-fetch@^2.3.0, node-fetch@^2.6.1: 1398 | version "2.6.1" 1399 | resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.1.tgz#045bd323631f76ed2e2b55573394416b639a0052" 1400 | integrity sha512-V4aYg89jEoVRxRb2fJdAg8FHvI7cEyYdVAh94HH0UIK8oJxUfkjlDQN9RbMx+bEjP7+ggMiFRprSti032Oipxw== 1401 | 1402 | node-forge@^0.10.0: 1403 | version "0.10.0" 1404 | resolved "https://registry.yarnpkg.com/node-forge/-/node-forge-0.10.0.tgz#32dea2afb3e9926f02ee5ce8794902691a676bf3" 1405 | integrity sha512-PPmu8eEeG9saEUvI97fm4OYxXVB6bFvyNTyiUOBichBpFG8A1Ljw3bY62+5oOjDEMHRnd0Y7HQ+x7uzxOzC6JA== 1406 | 1407 | normalize-path@^3.0.0, normalize-path@~3.0.0: 1408 | version "3.0.0" 1409 | resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-3.0.0.tgz#0dcd69ff23a1c9b11fd0978316644a0388216a65" 1410 | integrity sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA== 1411 | 1412 | once@^1.3.0, once@^1.3.1, once@^1.4.0: 1413 | version "1.4.0" 1414 | resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" 1415 | integrity sha1-WDsap3WWHUsROsF9nFC6753Xa9E= 1416 | dependencies: 1417 | wrappy "1" 1418 | 1419 | onetime@^5.1.0: 1420 | version "5.1.2" 1421 | resolved "https://registry.yarnpkg.com/onetime/-/onetime-5.1.2.tgz#d0e96ebb56b07476df1dd9c4806e5237985ca45e" 1422 | integrity sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg== 1423 | dependencies: 1424 | mimic-fn "^2.1.0" 1425 | 1426 | p-limit@^2.2.0: 1427 | version "2.3.0" 1428 | resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-2.3.0.tgz#3dd33c647a214fdfffd835933eb086da0dc21db1" 1429 | integrity sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w== 1430 | dependencies: 1431 | p-try "^2.0.0" 1432 | 1433 | p-limit@^3.0.1, p-limit@^3.0.2: 1434 | version "3.0.2" 1435 | resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.0.2.tgz#1664e010af3cadc681baafd3e2a437be7b0fb5fe" 1436 | integrity sha512-iwqZSOoWIW+Ew4kAGUlN16J4M7OB3ysMLSZtnhmqx7njIHFPlxWBX8xo3lVTyFVq6mI/lL9qt2IsN1sHwaxJkg== 1437 | dependencies: 1438 | p-try "^2.0.0" 1439 | 1440 | p-locate@^4.1.0: 1441 | version "4.1.0" 1442 | resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-4.1.0.tgz#a3428bb7088b3a60292f66919278b7c297ad4f07" 1443 | integrity sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A== 1444 | dependencies: 1445 | p-limit "^2.2.0" 1446 | 1447 | p-locate@^5.0.0: 1448 | version "5.0.0" 1449 | resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-5.0.0.tgz#83c8315c6785005e3bd021839411c9e110e6d834" 1450 | integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== 1451 | dependencies: 1452 | p-limit "^3.0.2" 1453 | 1454 | p-try@^2.0.0: 1455 | version "2.2.0" 1456 | resolved "https://registry.yarnpkg.com/p-try/-/p-try-2.2.0.tgz#cb2868540e313d61de58fafbe35ce9004d5540e6" 1457 | integrity sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ== 1458 | 1459 | path-exists@^4.0.0: 1460 | version "4.0.0" 1461 | resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-4.0.0.tgz#513bdbe2d3b95d7762e8c1137efa195c6c61b5b3" 1462 | integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== 1463 | 1464 | path-is-absolute@^1.0.0: 1465 | version "1.0.1" 1466 | resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" 1467 | integrity sha1-F0uSaHNVNP+8es5r9TpanhtcX18= 1468 | 1469 | path-parse@^1.0.6: 1470 | version "1.0.6" 1471 | resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.6.tgz#d62dbb5679405d72c4737ec58600e9ddcf06d24c" 1472 | integrity sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw== 1473 | 1474 | pathval@^1.1.1: 1475 | version "1.1.1" 1476 | resolved "https://registry.yarnpkg.com/pathval/-/pathval-1.1.1.tgz#8534e77a77ce7ac5a2512ea21e0fdb8fcf6c3d8d" 1477 | integrity sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ== 1478 | 1479 | picomatch@^2.0.4, picomatch@^2.2.1: 1480 | version "2.2.2" 1481 | resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.2.2.tgz#21f333e9b6b8eaff02468f5146ea406d345f4dad" 1482 | integrity sha512-q0M/9eZHzmr0AulXyPwNfZjtwZ/RBZlbN3K3CErVrk50T2ASYI7Bye0EvekFY3IP1Nt2DHu0re+V2ZHIpMkuWg== 1483 | 1484 | protobufjs@^6.8.6, protobufjs@^6.9.0: 1485 | version "6.10.2" 1486 | resolved "https://registry.yarnpkg.com/protobufjs/-/protobufjs-6.10.2.tgz#b9cb6bd8ec8f87514592ba3fdfd28e93f33a469b" 1487 | integrity sha512-27yj+04uF6ya9l+qfpH187aqEzfCF4+Uit0I9ZBQVqK09hk/SQzKa2MUqUpXaVa7LOFRg1TSSr3lVxGOk6c0SQ== 1488 | dependencies: 1489 | "@protobufjs/aspromise" "^1.1.2" 1490 | "@protobufjs/base64" "^1.1.2" 1491 | "@protobufjs/codegen" "^2.0.4" 1492 | "@protobufjs/eventemitter" "^1.1.0" 1493 | "@protobufjs/fetch" "^1.1.0" 1494 | "@protobufjs/float" "^1.0.2" 1495 | "@protobufjs/inquire" "^1.1.0" 1496 | "@protobufjs/path" "^1.1.2" 1497 | "@protobufjs/pool" "^1.1.0" 1498 | "@protobufjs/utf8" "^1.1.0" 1499 | "@types/long" "^4.0.1" 1500 | "@types/node" "^13.7.0" 1501 | long "^4.0.0" 1502 | 1503 | pseudomap@^1.0.1: 1504 | version "1.0.2" 1505 | resolved "https://registry.yarnpkg.com/pseudomap/-/pseudomap-1.0.2.tgz#f052a28da70e618917ef0a8ac34c1ae5a68286b3" 1506 | integrity sha1-8FKijacOYYkX7wqKw0wa5aaChrM= 1507 | 1508 | pump@^3.0.0: 1509 | version "3.0.0" 1510 | resolved "https://registry.yarnpkg.com/pump/-/pump-3.0.0.tgz#b4a2116815bde2f4e1ea602354e8c75565107a64" 1511 | integrity sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww== 1512 | dependencies: 1513 | end-of-stream "^1.1.0" 1514 | once "^1.3.1" 1515 | 1516 | pumpify@^2.0.0: 1517 | version "2.0.1" 1518 | resolved "https://registry.yarnpkg.com/pumpify/-/pumpify-2.0.1.tgz#abfc7b5a621307c728b551decbbefb51f0e4aa1e" 1519 | integrity sha512-m7KOje7jZxrmutanlkS1daj1dS6z6BgslzOXmcSEpIlCxM3VJH7lG5QLeck/6hgF6F4crFf01UtQmNsJfweTAw== 1520 | dependencies: 1521 | duplexify "^4.1.1" 1522 | inherits "^2.0.3" 1523 | pump "^3.0.0" 1524 | 1525 | randombytes@^2.1.0: 1526 | version "2.1.0" 1527 | resolved "https://registry.yarnpkg.com/randombytes/-/randombytes-2.1.0.tgz#df6f84372f0270dc65cdf6291349ab7a473d4f2a" 1528 | integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ== 1529 | dependencies: 1530 | safe-buffer "^5.1.0" 1531 | 1532 | readable-stream@^3.1.1: 1533 | version "3.6.0" 1534 | resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-3.6.0.tgz#337bbda3adc0706bd3e024426a286d4b4b2c9198" 1535 | integrity sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA== 1536 | dependencies: 1537 | inherits "^2.0.3" 1538 | string_decoder "^1.1.1" 1539 | util-deprecate "^1.0.1" 1540 | 1541 | readdirp@~3.5.0: 1542 | version "3.5.0" 1543 | resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-3.5.0.tgz#9ba74c019b15d365278d2e91bb8c48d7b4d42c9e" 1544 | integrity sha512-cMhu7c/8rdhkHXWsY+osBhfSy0JikwpHK/5+imo+LpeasTF8ouErHrlYkwT0++njiyuDvc7OFY5T3ukvZ8qmFQ== 1545 | dependencies: 1546 | picomatch "^2.2.1" 1547 | 1548 | require-directory@^2.1.1: 1549 | version "2.1.1" 1550 | resolved "https://registry.yarnpkg.com/require-directory/-/require-directory-2.1.1.tgz#8c64ad5fd30dab1c976e2344ffe7f792a6a6df42" 1551 | integrity sha1-jGStX9MNqxyXbiNE/+f3kqam30I= 1552 | 1553 | require-main-filename@^2.0.0: 1554 | version "2.0.0" 1555 | resolved "https://registry.yarnpkg.com/require-main-filename/-/require-main-filename-2.0.0.tgz#d0b329ecc7cc0f61649f62215be69af54aa8989b" 1556 | integrity sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg== 1557 | 1558 | resolve@^1.3.2: 1559 | version "1.19.0" 1560 | resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.19.0.tgz#1af5bf630409734a067cae29318aac7fa29a267c" 1561 | integrity sha512-rArEXAgsBG4UgRGcynxWIWKFvh/XZCcS8UJdHhwy91zwAvCZIbcs+vAbflgBnNjYMs/i/i+/Ux6IZhML1yPvxg== 1562 | dependencies: 1563 | is-core-module "^2.1.0" 1564 | path-parse "^1.0.6" 1565 | 1566 | retry-request@^4.0.0, retry-request@^4.1.1: 1567 | version "4.1.3" 1568 | resolved "https://registry.yarnpkg.com/retry-request/-/retry-request-4.1.3.tgz#d5f74daf261372cff58d08b0a1979b4d7cab0fde" 1569 | integrity sha512-QnRZUpuPNgX0+D1xVxul6DbJ9slvo4Rm6iV/dn63e048MvGbUZiKySVt6Tenp04JqmchxjiLltGerOJys7kJYQ== 1570 | dependencies: 1571 | debug "^4.1.1" 1572 | 1573 | safe-buffer@>=5.1.0, safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@~5.2.0: 1574 | version "5.2.1" 1575 | resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" 1576 | integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== 1577 | 1578 | semver@^5.3.0, semver@^5.6.0: 1579 | version "5.7.1" 1580 | resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.1.tgz#a954f931aeba508d307bbf069eff0c01c96116f7" 1581 | integrity sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ== 1582 | 1583 | semver@^6.0.0, semver@^6.2.0: 1584 | version "6.3.0" 1585 | resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.0.tgz#ee0a64c8af5e8ceea67687b133761e1becbd1d3d" 1586 | integrity sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw== 1587 | 1588 | serialize-javascript@5.0.1: 1589 | version "5.0.1" 1590 | resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-5.0.1.tgz#7886ec848049a462467a97d3d918ebb2aaf934f4" 1591 | integrity sha512-SaaNal9imEO737H2c05Og0/8LUXG7EnsZyMa8MzkmuHoELfT6txuj0cMqRj6zfPKnmQ1yasR4PCJc8x+M4JSPA== 1592 | dependencies: 1593 | randombytes "^2.1.0" 1594 | 1595 | set-blocking@^2.0.0: 1596 | version "2.0.0" 1597 | resolved "https://registry.yarnpkg.com/set-blocking/-/set-blocking-2.0.0.tgz#045f9782d011ae9a6803ddd382b24392b3d890f7" 1598 | integrity sha1-BF+XgtARrppoA93TgrJDkrPYkPc= 1599 | 1600 | signal-exit@^3.0.2: 1601 | version "3.0.3" 1602 | resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.3.tgz#a1410c2edd8f077b08b4e253c8eacfcaf057461c" 1603 | integrity sha512-VUJ49FC8U1OxwZLxIbTTrDvLnf/6TDgxZcK8wxR8zs13xpx7xbG60ndBlhNrFi2EMuFRoeDoJO7wthSLq42EjA== 1604 | 1605 | snakeize@^0.1.0: 1606 | version "0.1.0" 1607 | resolved "https://registry.yarnpkg.com/snakeize/-/snakeize-0.1.0.tgz#10c088d8b58eb076b3229bb5a04e232ce126422d" 1608 | integrity sha1-EMCI2LWOsHazIpu1oE4jLOEmQi0= 1609 | 1610 | source-map-support@^0.5.17: 1611 | version "0.5.19" 1612 | resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.19.tgz#a98b62f86dcaf4f67399648c085291ab9e8fed61" 1613 | integrity sha512-Wonm7zOCIJzBGQdB+thsPar0kYuCIzYvxZwlBa87yi/Mdjv7Tip2cyVbLj5o0cFPN4EVkuTwb3GDDyUx2DGnGw== 1614 | dependencies: 1615 | buffer-from "^1.0.0" 1616 | source-map "^0.6.0" 1617 | 1618 | source-map@^0.6.0: 1619 | version "0.6.1" 1620 | resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" 1621 | integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== 1622 | 1623 | sprintf-js@~1.0.2: 1624 | version "1.0.3" 1625 | resolved "https://registry.yarnpkg.com/sprintf-js/-/sprintf-js-1.0.3.tgz#04e6926f662895354f3dd015203633b857297e2c" 1626 | integrity sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw= 1627 | 1628 | stream-events@^1.0.1, stream-events@^1.0.4, stream-events@^1.0.5: 1629 | version "1.0.5" 1630 | resolved "https://registry.yarnpkg.com/stream-events/-/stream-events-1.0.5.tgz#bbc898ec4df33a4902d892333d47da9bf1c406d5" 1631 | integrity sha512-E1GUzBSgvct8Jsb3v2X15pjzN1tYebtbLaMg+eBOUOAxgbLoSbT2NS91ckc5lJD1KfLjId+jXJRgo0qnV5Nerg== 1632 | dependencies: 1633 | stubs "^3.0.0" 1634 | 1635 | stream-shift@^1.0.0: 1636 | version "1.0.1" 1637 | resolved "https://registry.yarnpkg.com/stream-shift/-/stream-shift-1.0.1.tgz#d7088281559ab2778424279b0877da3c392d5a3d" 1638 | integrity sha512-AiisoFqQ0vbGcZgQPY1cdP2I76glaVA/RauYR4G4thNFgkTqr90yXTo4LYX60Jl+sIlPNHHdGSwo01AvbKUSVQ== 1639 | 1640 | streamsearch@0.1.2: 1641 | version "0.1.2" 1642 | resolved "https://registry.yarnpkg.com/streamsearch/-/streamsearch-0.1.2.tgz#808b9d0e56fc273d809ba57338e929919a1a9f1a" 1643 | integrity sha1-gIudDlb8Jz2Am6VzOOkpkZoanxo= 1644 | 1645 | "string-width@^1.0.2 || 2": 1646 | version "2.1.1" 1647 | resolved "https://registry.yarnpkg.com/string-width/-/string-width-2.1.1.tgz#ab93f27a8dc13d28cac815c462143a6d9012ae9e" 1648 | integrity sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw== 1649 | dependencies: 1650 | is-fullwidth-code-point "^2.0.0" 1651 | strip-ansi "^4.0.0" 1652 | 1653 | string-width@^4.1.0, string-width@^4.2.0: 1654 | version "4.2.0" 1655 | resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.0.tgz#952182c46cc7b2c313d1596e623992bd163b72b5" 1656 | integrity sha512-zUz5JD+tgqtuDjMhwIg5uFVV3dtqZ9yQJlZVfq4I01/K5Paj5UHj7VyrQOJvzawSVlKpObApbfD0Ed6yJc+1eg== 1657 | dependencies: 1658 | emoji-regex "^8.0.0" 1659 | is-fullwidth-code-point "^3.0.0" 1660 | strip-ansi "^6.0.0" 1661 | 1662 | string_decoder@^1.1.1: 1663 | version "1.3.0" 1664 | resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e" 1665 | integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== 1666 | dependencies: 1667 | safe-buffer "~5.2.0" 1668 | 1669 | strip-ansi@^4.0.0: 1670 | version "4.0.0" 1671 | resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-4.0.0.tgz#a8479022eb1ac368a871389b635262c505ee368f" 1672 | integrity sha1-qEeQIusaw2iocTibY1JixQXuNo8= 1673 | dependencies: 1674 | ansi-regex "^3.0.0" 1675 | 1676 | strip-ansi@^6.0.0: 1677 | version "6.0.0" 1678 | resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.0.tgz#0b1571dd7669ccd4f3e06e14ef1eed26225ae532" 1679 | integrity sha512-AuvKTrTfQNYNIctbR1K/YGTR1756GycPsg7b9bdV9Duqur4gv6aKqHXah67Z8ImS7WEz5QVcOtlfW2rZEugt6w== 1680 | dependencies: 1681 | ansi-regex "^5.0.0" 1682 | 1683 | strip-json-comments@3.1.1: 1684 | version "3.1.1" 1685 | resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" 1686 | integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== 1687 | 1688 | stubs@^3.0.0: 1689 | version "3.0.0" 1690 | resolved "https://registry.yarnpkg.com/stubs/-/stubs-3.0.0.tgz#e8d2ba1fa9c90570303c030b6900f7d5f89abe5b" 1691 | integrity sha1-6NK6H6nJBXAwPAMLaQD31fiavls= 1692 | 1693 | supports-color@8.1.1: 1694 | version "8.1.1" 1695 | resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-8.1.1.tgz#cd6fc17e28500cff56c1b86c0a7fd4a54a73005c" 1696 | integrity sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q== 1697 | dependencies: 1698 | has-flag "^4.0.0" 1699 | 1700 | supports-color@^5.3.0: 1701 | version "5.5.0" 1702 | resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" 1703 | integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== 1704 | dependencies: 1705 | has-flag "^3.0.0" 1706 | 1707 | supports-color@^7.1.0: 1708 | version "7.2.0" 1709 | resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.2.0.tgz#1b7dcdcb32b8138801b3e478ba6a51caa89648da" 1710 | integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== 1711 | dependencies: 1712 | has-flag "^4.0.0" 1713 | 1714 | teeny-request@^7.0.0: 1715 | version "7.0.1" 1716 | resolved "https://registry.yarnpkg.com/teeny-request/-/teeny-request-7.0.1.tgz#bdd41fdffea5f8fbc0d29392cb47bec4f66b2b4c" 1717 | integrity sha512-sasJmQ37klOlplL4Ia/786M5YlOcoLGQyq2TE4WHSRupbAuDaQW0PfVxV4MtdBtRJ4ngzS+1qim8zP6Zp35qCw== 1718 | dependencies: 1719 | http-proxy-agent "^4.0.0" 1720 | https-proxy-agent "^5.0.0" 1721 | node-fetch "^2.6.1" 1722 | stream-events "^1.0.5" 1723 | uuid "^8.0.0" 1724 | 1725 | to-regex-range@^5.0.1: 1726 | version "5.0.1" 1727 | resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" 1728 | integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== 1729 | dependencies: 1730 | is-number "^7.0.0" 1731 | 1732 | ts-node@^9.1.1: 1733 | version "9.1.1" 1734 | resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-9.1.1.tgz#51a9a450a3e959401bda5f004a72d54b936d376d" 1735 | integrity sha512-hPlt7ZACERQGf03M253ytLY3dHbGNGrAq9qIHWUY9XHYl1z7wYngSr3OQ5xmui8o2AaxsONxIzjafLUiWBo1Fg== 1736 | dependencies: 1737 | arg "^4.1.0" 1738 | create-require "^1.1.0" 1739 | diff "^4.0.1" 1740 | make-error "^1.1.1" 1741 | source-map-support "^0.5.17" 1742 | yn "3.1.1" 1743 | 1744 | tslib@^1.13.0, tslib@^1.8.1: 1745 | version "1.14.1" 1746 | resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.14.1.tgz#cf2d38bdc34a134bcaf1091c41f6619e2f672d00" 1747 | integrity sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg== 1748 | 1749 | tslib@^2.1.0: 1750 | version "2.2.0" 1751 | resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.2.0.tgz#fb2c475977e35e241311ede2693cee1ec6698f5c" 1752 | integrity sha512-gS9GVHRU+RGn5KQM2rllAlR3dU6m7AcpJKdtH8gFvQiC4Otgk98XnmMU+nZenHt/+VhnBPWwgrJsyrdcw6i23w== 1753 | 1754 | tslint@^6.1.3: 1755 | version "6.1.3" 1756 | resolved "https://registry.yarnpkg.com/tslint/-/tslint-6.1.3.tgz#5c23b2eccc32487d5523bd3a470e9aa31789d904" 1757 | integrity sha512-IbR4nkT96EQOvKE2PW/djGz8iGNeJ4rF2mBfiYaR/nvUWYKJhLwimoJKgjIFEIDibBtOevj7BqCRL4oHeWWUCg== 1758 | dependencies: 1759 | "@babel/code-frame" "^7.0.0" 1760 | builtin-modules "^1.1.1" 1761 | chalk "^2.3.0" 1762 | commander "^2.12.1" 1763 | diff "^4.0.1" 1764 | glob "^7.1.1" 1765 | js-yaml "^3.13.1" 1766 | minimatch "^3.0.4" 1767 | mkdirp "^0.5.3" 1768 | resolve "^1.3.2" 1769 | semver "^5.3.0" 1770 | tslib "^1.13.0" 1771 | tsutils "^2.29.0" 1772 | 1773 | tsutils@^2.29.0: 1774 | version "2.29.0" 1775 | resolved "https://registry.yarnpkg.com/tsutils/-/tsutils-2.29.0.tgz#32b488501467acbedd4b85498673a0812aca0b99" 1776 | integrity sha512-g5JVHCIJwzfISaXpXE1qvNalca5Jwob6FjI4AoPlqMusJ6ftFE7IkkFoMhVLRgK+4Kx3gkzb8UZK5t5yTTvEmA== 1777 | dependencies: 1778 | tslib "^1.8.1" 1779 | 1780 | type-detect@^4.0.0, type-detect@^4.0.5: 1781 | version "4.0.8" 1782 | resolved "https://registry.yarnpkg.com/type-detect/-/type-detect-4.0.8.tgz#7646fb5f18871cfbb7749e69bd39a6388eb7450c" 1783 | integrity sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g== 1784 | 1785 | typedarray-to-buffer@^3.1.5: 1786 | version "3.1.5" 1787 | resolved "https://registry.yarnpkg.com/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz#a97ee7a9ff42691b9f783ff1bc5112fe3fca9080" 1788 | integrity sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q== 1789 | dependencies: 1790 | is-typedarray "^1.0.0" 1791 | 1792 | typescript@^4.2.4: 1793 | version "4.2.4" 1794 | resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.2.4.tgz#8610b59747de028fda898a8aef0e103f156d0961" 1795 | integrity sha512-V+evlYHZnQkaz8TRBuxTA92yZBPotr5H+WhQ7bD3hZUndx5tGOa1fuCgeSjxAzM1RiN5IzvadIXTVefuuwZCRg== 1796 | 1797 | unique-string@^2.0.0: 1798 | version "2.0.0" 1799 | resolved "https://registry.yarnpkg.com/unique-string/-/unique-string-2.0.0.tgz#39c6451f81afb2749de2b233e3f7c5e8843bd89d" 1800 | integrity sha512-uNaeirEPvpZWSgzwsPGtU2zVSTrn/8L5q/IexZmH0eH6SA73CmAA5U4GwORTxQAZs95TAXLNqeLoPPNO5gZfWg== 1801 | dependencies: 1802 | crypto-random-string "^2.0.0" 1803 | 1804 | util-deprecate@^1.0.1: 1805 | version "1.0.2" 1806 | resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" 1807 | integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8= 1808 | 1809 | uuid@^8.0.0: 1810 | version "8.3.1" 1811 | resolved "https://registry.yarnpkg.com/uuid/-/uuid-8.3.1.tgz#2ba2e6ca000da60fce5a196954ab241131e05a31" 1812 | integrity sha512-FOmRr+FmWEIG8uhZv6C2bTgEVXsHk08kE7mPlrBbEe+c3r9pjceVPgupIfNIhc4yx55H69OXANrUaSuu9eInKg== 1813 | 1814 | websocket-driver@>=0.5.1: 1815 | version "0.7.4" 1816 | resolved "https://registry.yarnpkg.com/websocket-driver/-/websocket-driver-0.7.4.tgz#89ad5295bbf64b480abcba31e4953aca706f5760" 1817 | integrity sha512-b17KeDIQVjvb0ssuSDF2cYXSg2iztliJ4B9WdsuB6J952qCPKmnVq4DyW5motImXHDC1cBT/1UezrJVsKw5zjg== 1818 | dependencies: 1819 | http-parser-js ">=0.5.1" 1820 | safe-buffer ">=5.1.0" 1821 | websocket-extensions ">=0.1.1" 1822 | 1823 | websocket-extensions@>=0.1.1: 1824 | version "0.1.4" 1825 | resolved "https://registry.yarnpkg.com/websocket-extensions/-/websocket-extensions-0.1.4.tgz#7f8473bc839dfd87608adb95d7eb075211578a42" 1826 | integrity sha512-OqedPIGOfsDlo31UNwYbCFMSaO9m9G/0faIHj5/dZFDMFqPTcx6UwqyOy3COEaEOg/9VsGIpdqn62W5KhoKSpg== 1827 | 1828 | which-module@^2.0.0: 1829 | version "2.0.0" 1830 | resolved "https://registry.yarnpkg.com/which-module/-/which-module-2.0.0.tgz#d9ef07dce77b9902b8a3a8fa4b31c3e3f7e6e87a" 1831 | integrity sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho= 1832 | 1833 | which@2.0.2: 1834 | version "2.0.2" 1835 | resolved "https://registry.yarnpkg.com/which/-/which-2.0.2.tgz#7c6a8dd0a636a0327e10b59c9286eee93f3f51b1" 1836 | integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA== 1837 | dependencies: 1838 | isexe "^2.0.0" 1839 | 1840 | wide-align@1.1.3: 1841 | version "1.1.3" 1842 | resolved "https://registry.yarnpkg.com/wide-align/-/wide-align-1.1.3.tgz#ae074e6bdc0c14a431e804e624549c633b000457" 1843 | integrity sha512-QGkOQc8XL6Bt5PwnsExKBPuMKBxnGxWWW3fU55Xt4feHozMUhdUMaBCk290qpm/wG5u/RSKzwdAC4i51YigihA== 1844 | dependencies: 1845 | string-width "^1.0.2 || 2" 1846 | 1847 | workerpool@6.1.0: 1848 | version "6.1.0" 1849 | resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-6.1.0.tgz#a8e038b4c94569596852de7a8ea4228eefdeb37b" 1850 | integrity sha512-toV7q9rWNYha963Pl/qyeZ6wG+3nnsyvolaNUS8+R5Wtw6qJPTxIlOP1ZSvcGhEJw+l3HMMmtiNo9Gl61G4GVg== 1851 | 1852 | wrap-ansi@^6.2.0: 1853 | version "6.2.0" 1854 | resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-6.2.0.tgz#e9393ba07102e6c91a3b221478f0257cd2856e53" 1855 | integrity sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA== 1856 | dependencies: 1857 | ansi-styles "^4.0.0" 1858 | string-width "^4.1.0" 1859 | strip-ansi "^6.0.0" 1860 | 1861 | wrap-ansi@^7.0.0: 1862 | version "7.0.0" 1863 | resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43" 1864 | integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q== 1865 | dependencies: 1866 | ansi-styles "^4.0.0" 1867 | string-width "^4.1.0" 1868 | strip-ansi "^6.0.0" 1869 | 1870 | wrappy@1: 1871 | version "1.0.2" 1872 | resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" 1873 | integrity sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8= 1874 | 1875 | write-file-atomic@^3.0.0: 1876 | version "3.0.3" 1877 | resolved "https://registry.yarnpkg.com/write-file-atomic/-/write-file-atomic-3.0.3.tgz#56bd5c5a5c70481cd19c571bd39ab965a5de56e8" 1878 | integrity sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q== 1879 | dependencies: 1880 | imurmurhash "^0.1.4" 1881 | is-typedarray "^1.0.0" 1882 | signal-exit "^3.0.2" 1883 | typedarray-to-buffer "^3.1.5" 1884 | 1885 | xdg-basedir@^4.0.0: 1886 | version "4.0.0" 1887 | resolved "https://registry.yarnpkg.com/xdg-basedir/-/xdg-basedir-4.0.0.tgz#4bc8d9984403696225ef83a1573cbbcb4e79db13" 1888 | integrity sha512-PSNhEJDejZYV7h50BohL09Er9VaIefr2LMAf3OEmpCkjOi34eYyQYAXUTjEQtZJTKcF0E2UKTh+osDLsgNim9Q== 1889 | 1890 | y18n@^4.0.0: 1891 | version "4.0.0" 1892 | resolved "https://registry.yarnpkg.com/y18n/-/y18n-4.0.0.tgz#95ef94f85ecc81d007c264e190a120f0a3c8566b" 1893 | integrity sha512-r9S/ZyXu/Xu9q1tYlpsLIsa3EeLXXk0VwlxqTcFRfg9EhMW+17kbt9G0NrgCmhGb5vT2hyhJZLfDGx+7+5Uj/w== 1894 | 1895 | y18n@^5.0.5: 1896 | version "5.0.5" 1897 | resolved "https://registry.yarnpkg.com/y18n/-/y18n-5.0.5.tgz#8769ec08d03b1ea2df2500acef561743bbb9ab18" 1898 | integrity sha512-hsRUr4FFrvhhRH12wOdfs38Gy7k2FFzB9qgN9v3aLykRq0dRcdcpz5C9FxdS2NuhOrI/628b/KSTJ3rwHysYSg== 1899 | 1900 | yallist@^2.0.0: 1901 | version "2.1.2" 1902 | resolved "https://registry.yarnpkg.com/yallist/-/yallist-2.1.2.tgz#1c11f9218f076089a47dd512f93c6699a6a81d52" 1903 | integrity sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI= 1904 | 1905 | yallist@^4.0.0: 1906 | version "4.0.0" 1907 | resolved "https://registry.yarnpkg.com/yallist/-/yallist-4.0.0.tgz#9bb92790d9c0effec63be73519e11a35019a3a72" 1908 | integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== 1909 | 1910 | yargs-parser@20.2.4: 1911 | version "20.2.4" 1912 | resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.4.tgz#b42890f14566796f85ae8e3a25290d205f154a54" 1913 | integrity sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA== 1914 | 1915 | yargs-parser@^18.1.2: 1916 | version "18.1.3" 1917 | resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-18.1.3.tgz#be68c4975c6b2abf469236b0c870362fab09a7b0" 1918 | integrity sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ== 1919 | dependencies: 1920 | camelcase "^5.0.0" 1921 | decamelize "^1.2.0" 1922 | 1923 | yargs-parser@^20.2.2: 1924 | version "20.2.7" 1925 | resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.7.tgz#61df85c113edfb5a7a4e36eb8aa60ef423cbc90a" 1926 | integrity sha512-FiNkvbeHzB/syOjIUxFDCnhSfzAL8R5vs40MgLFBorXACCOAEaWu0gRZl14vG8MR9AOJIZbmkjhusqBYZ3HTHw== 1927 | 1928 | yargs-unparser@2.0.0: 1929 | version "2.0.0" 1930 | resolved "https://registry.yarnpkg.com/yargs-unparser/-/yargs-unparser-2.0.0.tgz#f131f9226911ae5d9ad38c432fe809366c2325eb" 1931 | integrity sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA== 1932 | dependencies: 1933 | camelcase "^6.0.0" 1934 | decamelize "^4.0.0" 1935 | flat "^5.0.2" 1936 | is-plain-obj "^2.1.0" 1937 | 1938 | yargs@16.2.0: 1939 | version "16.2.0" 1940 | resolved "https://registry.yarnpkg.com/yargs/-/yargs-16.2.0.tgz#1c82bf0f6b6a66eafce7ef30e376f49a12477f66" 1941 | integrity sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw== 1942 | dependencies: 1943 | cliui "^7.0.2" 1944 | escalade "^3.1.1" 1945 | get-caller-file "^2.0.5" 1946 | require-directory "^2.1.1" 1947 | string-width "^4.2.0" 1948 | y18n "^5.0.5" 1949 | yargs-parser "^20.2.2" 1950 | 1951 | yargs@^15.3.1: 1952 | version "15.4.1" 1953 | resolved "https://registry.yarnpkg.com/yargs/-/yargs-15.4.1.tgz#0d87a16de01aee9d8bec2bfbf74f67851730f4f8" 1954 | integrity sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A== 1955 | dependencies: 1956 | cliui "^6.0.0" 1957 | decamelize "^1.2.0" 1958 | find-up "^4.1.0" 1959 | get-caller-file "^2.0.1" 1960 | require-directory "^2.1.1" 1961 | require-main-filename "^2.0.0" 1962 | set-blocking "^2.0.0" 1963 | string-width "^4.2.0" 1964 | which-module "^2.0.0" 1965 | y18n "^4.0.0" 1966 | yargs-parser "^18.1.2" 1967 | 1968 | yn@3.1.1: 1969 | version "3.1.1" 1970 | resolved "https://registry.yarnpkg.com/yn/-/yn-3.1.1.tgz#1e87401a09d767c1d5eab26a6e4c185182d2eb50" 1971 | integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q== 1972 | --------------------------------------------------------------------------------