├── .eslintrc.cjs ├── .gitignore ├── README.md ├── _gitignore ├── index.html ├── package-lock.json ├── package.json ├── public └── vite.svg ├── src ├── App.css ├── App.tsx ├── Counter.tsx ├── assets │ └── react.svg ├── database │ ├── SqliteDatabase.ts │ ├── context.tsx │ ├── parseTableNames.ts │ ├── schema.ts │ └── upsertRecordSql.ts ├── index.css ├── main.tsx ├── useThreadMessages.ts └── vite-env.d.ts ├── tsconfig.json ├── tsconfig.node.json ├── vite.config.ts └── yarn.lock /.eslintrc.cjs: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | root: true, 3 | env: { browser: true, es2020: true }, 4 | extends: [ 5 | 'eslint:recommended', 6 | 'plugin:@typescript-eslint/recommended', 7 | 'plugin:react-hooks/recommended', 8 | ], 9 | ignorePatterns: ['dist', '.eslintrc.cjs'], 10 | parser: '@typescript-eslint/parser', 11 | plugins: ['react-refresh'], 12 | rules: { 13 | 'react-refresh/only-export-components': [ 14 | 'warn', 15 | { allowConstantExport: true }, 16 | ], 17 | }, 18 | } 19 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Observable SQLite 2 | 3 | ### [See demo](https://stackblitz.com/~/github.com/jorroll/observable-sqlite) 4 | 5 | This repo is a minimal example of how to subscribe to SQL queries in a SQLite database. This example uses typescript and the official WASM distribution of SQLite. 6 | 7 | The basic strategy is that we provide a thin wrapper around SQLite for performing queries. This wrapper primarily does three things. 8 | 1. It provides a method to update records in the SQLite database. All updates to the database should go through this method. 9 | 2. When a record is updated, we emit a table change event that subscribers can listen to to know when a table has been updated. 10 | 3. We provide a subscribeToQuery or observeQuery method that we can use to view updates to a specific query. This method accepts a query string, then it parses it and notes what tables are touched by the query, then we subscribe to updates to those tables. Whenever a table touched by the query is changed, we re-run the query. While this method of observing queries isn't the most efficient (the query might rerender even if it's results haven't changed), most applications will probably be pleasantly surprised that it's more than good enough for their use case. SQLite can be very fast. 11 | - To parse the SQL queries, we're using the very helpful [pgsql-ast-parser](https://github.com/oguimbal/pgsql-ast-parser) library. While this library was designed for Postgres, it works well for our usecase here since postgres and SQLite have a lot of query syntax overlap. 12 | 13 | To learn more, [open this repo in Stackblitz](https://stackblitz.com/~/github.com/jorroll/observable-sqlite) and check out `./src/database/SqliteDatabase.ts`. The `liveQuery` method shows how you might subscribe to a query without using [RxJS](https://rxjs.dev/) and the `observeQuery` method shows the same thing except using [RxJS](https://rxjs.dev/). 14 | 15 | If you open up the stackblitz example, note that clicking the `increment` button in the demo is using SQlite reactivity to update. -------------------------------------------------------------------------------- /_gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Vite + React + TS 8 | 9 | 10 |
11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vite-react-typescript-starter", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "scripts": { 7 | "dev": "vite", 8 | "build": "tsc && vite build", 9 | "lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0", 10 | "preview": "vite preview" 11 | }, 12 | "dependencies": { 13 | "@sqlite.org/sqlite-wasm": "^3.43.2-build1", 14 | "observable-hooks": "^4.2.3", 15 | "pgsql-ast-parser": "^11.1.0", 16 | "react": "^18.2.0", 17 | "react-dom": "^18.2.0", 18 | "rxjs": "^7.8.1", 19 | "sql-template-tag": "^5.1.0" 20 | }, 21 | "devDependencies": { 22 | "@types/react": "^18.2.28", 23 | "@types/react-dom": "^18.2.13", 24 | "@typescript-eslint/eslint-plugin": "^6.7.5", 25 | "@typescript-eslint/parser": "^6.7.5", 26 | "@vitejs/plugin-react": "^4.1.0", 27 | "eslint": "^8.51.0", 28 | "eslint-plugin-react-hooks": "^4.6.0", 29 | "eslint-plugin-react-refresh": "^0.4.3", 30 | "typescript": "^5.2.2", 31 | "vite": "^5.0.0-beta.7" 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /public/vite.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /src/App.css: -------------------------------------------------------------------------------- 1 | #root { 2 | max-width: 1280px; 3 | margin: 0 auto; 4 | padding: 2rem; 5 | text-align: center; 6 | } 7 | 8 | .logo { 9 | height: 6em; 10 | padding: 1.5em; 11 | will-change: filter; 12 | transition: filter 300ms; 13 | } 14 | .logo:hover { 15 | filter: drop-shadow(0 0 2em #646cffaa); 16 | } 17 | .logo.react:hover { 18 | filter: drop-shadow(0 0 2em #61dafbaa); 19 | } 20 | 21 | @keyframes logo-spin { 22 | from { 23 | transform: rotate(0deg); 24 | } 25 | to { 26 | transform: rotate(360deg); 27 | } 28 | } 29 | 30 | @media (prefers-reduced-motion: no-preference) { 31 | a:nth-of-type(2) .logo { 32 | animation: logo-spin infinite 20s linear; 33 | } 34 | } 35 | 36 | .card { 37 | padding: 2em; 38 | } 39 | 40 | .read-the-docs { 41 | color: #888; 42 | } 43 | -------------------------------------------------------------------------------- /src/App.tsx: -------------------------------------------------------------------------------- 1 | import reactLogo from './assets/react.svg'; 2 | import viteLogo from '/vite.svg'; 3 | import './App.css'; 4 | import { ProvideDatabaseContext } from './database/context'; 5 | import { Counter } from './Counter'; 6 | import { Suspense } from 'react'; 7 | 8 | function App() { 9 | return ( 10 | 11 |
12 | 13 | Vite logo 14 | 15 | 16 | React logo 17 | 18 |
19 | 20 |

ObserveSQLite

21 | 22 | 23 |
24 | ); 25 | } 26 | 27 | export default App; 28 | -------------------------------------------------------------------------------- /src/Counter.tsx: -------------------------------------------------------------------------------- 1 | import { ComponentType, useCallback } from 'react'; 2 | import sql from 'sql-template-tag'; 3 | import { useDatabaseContext } from './database/context'; 4 | import { SQLiteClient } from './database/SqliteDatabase'; 5 | import { useObservable, useObservableState } from 'observable-hooks'; 6 | import { of, switchMap } from 'rxjs'; 7 | import { CounterRecord } from './database/schema'; 8 | 9 | export const Counter: ComponentType<{}> = () => { 10 | const counterId = '1'; 11 | const counter = useCounter(counterId); 12 | const increment = useIncrement(); 13 | 14 | if (counter === 'loading') return 'loading'; 15 | 16 | return ( 17 |
18 |

The current count is: {counter?.value ?? 0}

19 | 22 |
23 | ); 24 | }; 25 | 26 | function useCounter(counterId: string | null | undefined) { 27 | const db = useDatabaseContext(); 28 | 29 | const query = useObservable( 30 | (inputs$) => { 31 | return inputs$.pipe( 32 | switchMap(([counterId, db]) => 33 | counterId ? db.observeRecord('counter', counterId) : of(null) 34 | ) 35 | ); 36 | }, 37 | [counterId, db] 38 | ); 39 | 40 | const record = useObservableState(query, 'loading'); 41 | 42 | return record; 43 | } 44 | 45 | function useIncrement() { 46 | const db = useDatabaseContext(); 47 | 48 | return useCallback( 49 | async (counterId: string) => { 50 | const count = await getCounter(db, counterId); 51 | 52 | await db.writeRecordMap({ 53 | counter: { 54 | [counterId]: { 55 | id: counterId, 56 | value: count.value + 1, 57 | }, 58 | }, 59 | }); 60 | }, 61 | [db] 62 | ); 63 | } 64 | 65 | async function getCounter(db: SQLiteClient, counterId: string) { 66 | const query = sql` 67 | SELECT * FROM counter WHERE counter.id = ${counterId} 68 | `; 69 | 70 | const { resultRows } = await db.exec({ 71 | sql: query.sql, 72 | bind: query.values, 73 | }); 74 | 75 | return ( 76 | resultRows[0] || { id: counterId, value: 0 } // Lets return this default value if the record doesn'talready exist 77 | ); 78 | } 79 | -------------------------------------------------------------------------------- /src/assets/react.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /src/database/SqliteDatabase.ts: -------------------------------------------------------------------------------- 1 | import sqlite3InitModule, { Database, SqlValue } from '@sqlite.org/sqlite-wasm'; 2 | import { hasIntersection, parseTestTableNames } from './parseTableNames'; 3 | import { Observable, from, share, switchMap, throttle } from 'rxjs'; 4 | import { RecordMap, RecordTable, schema } from './schema'; 5 | import { upsertRecordSql } from './upsertRecordSql'; 6 | 7 | const modulePromise = sqlite3InitModule({ 8 | print: console.log, 9 | printErr: console.error, 10 | }); 11 | 12 | export class SQLiteClient { 13 | static async init() { 14 | const sqlite3 = await modulePromise; 15 | const db = new sqlite3.oo1.DB(':memory:'); 16 | db.exec({ sql: schema }); 17 | return new SQLiteClient(db); 18 | } 19 | 20 | private changeSubscriptions = new Set<(change: DatabaseChange) => void>(); 21 | 22 | private constructor(private db: Database) {} 23 | 24 | async exec( 25 | args: SQLiteClientExecProps 26 | ): Promise<{ resultRows: T[] }> { 27 | // Worth noting that this is actually a synchronous operation since we're 28 | // using the synchronous build of sqlite. But we don't want to commit to 29 | // using the sync build so we wrap this method in a promise. 30 | const res = this.db.exec({ 31 | sql: args.sql, 32 | bind: args.bind, 33 | returnValue: 'resultRows', 34 | rowMode: 'object', 35 | }); 36 | 37 | return { 38 | resultRows: res as T[], 39 | }; 40 | } 41 | 42 | /** 43 | * @returns an object with runQuery and subscribe methods. 44 | * - runQuery will run an async query returning the specified record or null. 45 | * - subscribe recieves an onChange callback that will be called whenever the 46 | * runQuery result changes in the database. It returns an unsubscribe function. 47 | * Use runQuery inside the onChange callback to get the current query results. 48 | */ 49 | liveRecord(table: RecordTable, id: string) { 50 | const runQuery = async () => { 51 | const { resultRows } = await this.exec({ 52 | sql: `SELECT * FROM ${table} WHERE ${table}.id = $1 LIMIT 1`, 53 | bind: { $1: id }, 54 | }); 55 | 56 | return resultRows[0] || null; 57 | }; 58 | 59 | return { 60 | runQuery, 61 | subscribe: (onChange: () => void) => 62 | this.subscribeToRowChanges(({ changes }) => { 63 | if (!(table in changes) || !(id in changes[table])) return; 64 | onChange(); 65 | }), 66 | }; 67 | } 68 | 69 | /** 70 | * Same as liveRecord except returns an Observable for the query. 71 | * The observable version has backpressure support which the liveRecord 72 | * version doesn't have out of the box (you'd need to build it on 73 | * top of the liveRecord version). 74 | */ 75 | observeRecord(table: RecordTable, id: string) { 76 | const runQuery = async () => { 77 | const { resultRows } = await this.exec({ 78 | sql: `SELECT * FROM ${table} WHERE ${table}.id = $1 LIMIT 1`, 79 | bind: { $1: id }, 80 | }); 81 | 82 | return resultRows[0] || null; 83 | }; 84 | 85 | const subscribeToQuery = (onChange: () => void) => 86 | this.subscribeToRowChanges(({ changes }) => { 87 | if (!(table in changes) || !(id in changes[table])) return; 88 | onChange(); 89 | }); 90 | 91 | return observable({ 92 | runQuery, 93 | subscribeToQuery, 94 | }); 95 | } 96 | 97 | /** 98 | * @returns an object with runQuery and subscribe methods. 99 | * - runQuery will run an async query returning the current query results. 100 | * - subscribe recieves an onChange callback that will be called whenever the 101 | * runQuery result may have changed in the database. `onChange` will likely 102 | * be called more times than necessary. It returns an unsubscribe 103 | * function. Use runQuery inside the onChange callback to get the current 104 | * query results. 105 | */ 106 | liveQuery(statement: { sql: string; values: any[] }) { 107 | const affectedTableNames = parseTestTableNames(statement.sql); 108 | 109 | if (affectedTableNames.length === 0) { 110 | throw new Error('Could not calculate selected table names'); 111 | } 112 | 113 | const runQuery = () => 114 | this.exec({ sql: statement.sql, bind: statement.values }); 115 | 116 | return { 117 | runQuery, 118 | subscribe: (onChange: () => void) => 119 | this.subscribeToRowChanges(({ tableNames }) => { 120 | if (!hasIntersection(affectedTableNames, tableNames)) return; 121 | onChange(); 122 | }), 123 | }; 124 | } 125 | 126 | /** 127 | * Same as liveQuery except returns an Observable for the query. 128 | * The observable version has backpressure support which the liveQuery 129 | * version doesn't have out of the box (you'd need to build it on 130 | * top of the liveQuery version). 131 | */ 132 | observeQuery(statement: { sql: string; values: any[] }) { 133 | const affectedTableNames = parseTestTableNames(statement.sql); 134 | 135 | if (affectedTableNames.length === 0) { 136 | throw new Error('Could not calculate selected table names'); 137 | } 138 | 139 | const runQuery = () => 140 | this.exec({ sql: statement.sql, bind: statement.values }); 141 | 142 | const subscribeToQuery = (onChange: () => void) => 143 | this.subscribeToRowChanges(({ tableNames }) => { 144 | if (!hasIntersection(affectedTableNames, tableNames)) return; 145 | onChange(); 146 | }); 147 | 148 | return observable({ 149 | runQuery, 150 | subscribeToQuery, 151 | }); 152 | } 153 | 154 | async writeRecordMap(recordMap: RecordMap) { 155 | this.db.transaction((db) => { 156 | for (const [table, rows] of Object.entries(recordMap)) { 157 | for (const row of Object.values(rows)) { 158 | const query = upsertRecordSql(table as RecordTable, row); 159 | 160 | db.exec({ 161 | sql: query.sql, 162 | bind: query.values as any[], 163 | returnValue: 'resultRows', 164 | rowMode: 'object', 165 | }); 166 | } 167 | } 168 | }); 169 | 170 | this.emitTableChanges({ 171 | tableNames: Object.keys(recordMap), 172 | changes: recordMap, 173 | }); 174 | } 175 | 176 | subscribeToRowChanges(callback: (change: DatabaseChange) => void) { 177 | this.changeSubscriptions.add(callback); 178 | 179 | return () => { 180 | this.changeSubscriptions.delete(callback); 181 | }; 182 | } 183 | 184 | private emitTableChanges(change: DatabaseChange) { 185 | console.log('Database changes:', change); 186 | 187 | for (const callback of this.changeSubscriptions) { 188 | callback(change); 189 | } 190 | } 191 | } 192 | 193 | function observable(args: { 194 | runQuery: () => Promise; 195 | subscribeToQuery: (onChanges: () => void) => () => void; 196 | }) { 197 | const { runQuery, subscribeToQuery } = args; 198 | 199 | let query: Promise; 200 | 201 | return new Observable((subscriber) => { 202 | const unsubscribe = subscribeToQuery(async () => subscriber.next(null)); 203 | subscriber.next(null); 204 | 205 | return () => { 206 | unsubscribe(); 207 | }; 208 | }).pipe( 209 | // If the Observable's `subscribeToQuery` onChanges callback fired, and 210 | // then the observable ran the query again in switchMap (below), if the 211 | // `subscribeToQuery#onChanges` callback fired again before `runQuery` 212 | // had finished processing then the result of the previous run would 213 | // be discarded and the query execution would restart. Potentially, 214 | // this cycle could happen repeatedly causing this observable to never 215 | // re-emit. Or, more practically, it could just delay emission of the 216 | // the query. We throttle the onChanges emissions to ensure that we 217 | // a query being processed currently has a chance to complete. By 218 | // using `trailing` true, we ensure that we also always get the 219 | // latest values. 220 | throttle( 221 | () => { 222 | // This works because we have `leading: true` so emitted values 223 | // first pass through `throttle` (triggering switchMap) before 224 | // this factory function is called (confirmed expirimentally). 225 | return from(query); 226 | }, 227 | { 228 | leading: true, 229 | trailing: true, 230 | } 231 | ), 232 | switchMap(() => { 233 | query = runQuery(); 234 | return query; 235 | }), 236 | share({ resetOnRefCountZero: true }) 237 | ); 238 | } 239 | 240 | interface DatabaseChange { 241 | tableNames: string[]; 242 | changes: RecordMap; 243 | } 244 | 245 | type SQLiteClientExecProps = { 246 | sql: string; 247 | /** 248 | * Binds one or more values to its bindable parameters. It accepts 1 or 2 arguments: 249 | * 250 | * If passed a single argument, it must be either an array, an object, or a value of 251 | * a bindable type (see below). Its bind index is assumed to be 1. 252 | * 253 | * If passed 2 arguments, the first one is the 1-based bind index or bindable 254 | * parameter name and the second one must be a value of a bindable type. 255 | * 256 | * Bindable value types: 257 | * - null is bound as NULL. 258 | * - undefined as a standalone value is a no-op: passing undefined as a value to this 259 | * function will not actually bind anything and this function will skip confirmation 260 | * that binding is even legal. (Those semantics simplify certain client-side uses.) 261 | * Conversely, a value of undefined as an array or object property when binding an 262 | * array/object (see below) is treated the same as null. 263 | * - Numbers are bound as either doubles or integers: doubles if they are larger than 264 | * 32 bits, else double or int32, depending on whether they have a fractional part. 265 | * Booleans are bound as integer 0 or 1. It is not expected the distinction of 266 | * binding doubles which have no fractional parts as integers is significant for the 267 | * majority of clients due to sqlite3's data typing model. If BigInt support is 268 | * enabled then this routine will bind BigInt values as 64-bit integers if they'll 269 | * fit in 64 bits. If that support is disabled, it will store the BigInt as an int32 270 | * or a double if it can do so without loss of precision. In either case, if a BigInt 271 | * is too BigInt then it will throw. 272 | * - Strings are bound as strings (use bindAsBlob() to force blob binding). 273 | * - Uint8Array, Int8Array, and ArrayBuffer instances are bound as blobs. 274 | * 275 | * If passed an array, each element of the array is bound at the parameter index equal 276 | * to the array index plus 1 (because arrays are 0-based but binding is 1-based). 277 | * 278 | * If passed an object, each object key is treated as a bindable parameter name. The 279 | * object keys must match any bindable parameter names, including any $, @, or : prefix. 280 | * Because $ is a legal identifier chararacter in JavaScript, that is the suggested 281 | * prefix for bindable parameters: stmt.bind({$a: 1, $b: 2}). 282 | * 283 | * It returns this object on success and throws on error. Errors include: 284 | * - Any bind index is out of range, a named bind parameter does not match, or this 285 | * statement has no bindable parameters. 286 | * - Any value to bind is of an unsupported type. 287 | * - Passed no arguments or more than two. 288 | * - The statement has been finalized. 289 | */ 290 | bind?: any[] | { [key: string]: any }; 291 | /** 292 | * One of 293 | * - 'array' (the default) causes the results of stmt.get([]) to be passed to the 294 | * callback and/or appended to resultRows. 295 | * - 'object' causes the results of stmt.get(Object.create(null)) to be passed to the 296 | * callback and/or appended to resultRows. Achtung: an SQL result may have multiple 297 | * columns with identical names. In that case, the right-most column will be the one 298 | * set in this object! 299 | */ 300 | // rowMode?: 'object' | 'array'; 301 | }; 302 | -------------------------------------------------------------------------------- /src/database/context.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | createContext, 3 | useContext, 4 | PropsWithChildren, 5 | useState, 6 | useEffect, 7 | FunctionComponent, 8 | } from 'react'; 9 | import { SQLiteClient } from './SqliteDatabase'; 10 | 11 | const DatabaseContext = createContext(null); 12 | 13 | export const ProvideDatabaseContext: FunctionComponent> = 14 | (props) => { 15 | const [context, setContext] = useState(null); 16 | 17 | useEffect(() => { 18 | SQLiteClient.init().then(setContext); 19 | }, []); 20 | 21 | if (!context) return null; 22 | 23 | return ( 24 | 25 | {props.children} 26 | 27 | ); 28 | }; 29 | 30 | export function useDatabaseContext() { 31 | const context = useContext(DatabaseContext); 32 | 33 | if (!context) { 34 | throw new Error('DatabaseContext not provided'); 35 | } 36 | 37 | return context as SQLiteClient; 38 | } 39 | -------------------------------------------------------------------------------- /src/database/parseTableNames.ts: -------------------------------------------------------------------------------- 1 | import { astVisitor, parse } from 'pgsql-ast-parser'; 2 | 3 | export function parseTestTableNames(sqlQuery: string): string[] { 4 | const statements = parse(sqlQuery); 5 | 6 | if (statements.length !== 1) { 7 | throw new Error(`Must receive exactly one SQL statement`); 8 | } 9 | 10 | const statement = statements[0]!; 11 | 12 | const tables = new Set(); 13 | 14 | const visitor = astVisitor(() => ({ 15 | tableRef: (t) => tables.add(t.name), 16 | })); 17 | 18 | visitor.statement(statement); 19 | 20 | return Array.from(tables); 21 | } 22 | 23 | export function hasIntersection( 24 | first: A[], 25 | second: B[], 26 | isEqual: (a: A, b: B) => boolean = Object.is 27 | ): boolean { 28 | const tLen = first.length; 29 | const cLen = second.length; 30 | 31 | for (let i = 0; i < tLen; ++i) { 32 | const tablename = first[i]; 33 | 34 | for (let j = 0; j < cLen; ++j) { 35 | const candidate = second[j]; 36 | 37 | if (isEqual(tablename, candidate)) { 38 | return true; 39 | } 40 | } 41 | } 42 | 43 | return false; 44 | } 45 | -------------------------------------------------------------------------------- /src/database/schema.ts: -------------------------------------------------------------------------------- 1 | export const schema = ` 2 | CREATE TABLE counter ( 3 | id TEXT PRIMARY KEY, 4 | value INTEGER NOT NULL DEFAULT 0 5 | ); 6 | 7 | CREATE TABLE thread ( 8 | id TEXT PRIMARY KEY, 9 | subject TEXT NOT NULL 10 | ); 11 | 12 | CREATE TABLE message ( 13 | id TEXT PRIMARY KEY, 14 | thread_id TEXT NOT NULL, 15 | content TEXT NOT NULL 16 | ); 17 | `; 18 | 19 | export type TableToRecord = { 20 | counter: CounterRecord; 21 | thread: ThreadRecord; 22 | thread_message: ThreadMessageRecord; 23 | message: MessageRecord; 24 | }; 25 | 26 | export type CounterRecord = { 27 | id: string; 28 | value: number; 29 | }; 30 | 31 | export type ThreadRecord = { 32 | id: string; 33 | subject: string; 34 | }; 35 | 36 | export type ThreadMessageRecord = { 37 | id: string; 38 | thread_id: string; 39 | message_id: string; 40 | }; 41 | 42 | export type MessageRecord = { 43 | id: string; 44 | content: string; 45 | }; 46 | 47 | export type RecordTable = keyof TableToRecord; 48 | export type RecordValue = TableToRecord[T]; 49 | 50 | export type RecordMap = { 51 | [Table in RecordTable]: { 52 | [recordId: string]: RecordValue; 53 | }; 54 | }; 55 | -------------------------------------------------------------------------------- /src/database/upsertRecordSql.ts: -------------------------------------------------------------------------------- 1 | import sql, { Sql } from "sql-template-tag"; 2 | import { RecordTable, RecordValue, TableToRecord } from "./schema"; 3 | 4 | export function upsertRecordSql(table: T, record: RecordValue) { 5 | return upsertRecordMap[table](record); 6 | } 7 | 8 | const upsertRecordMap = { 9 | counter: (record) => sql` 10 | INSERT INTO counter ( 11 | id, 12 | value 13 | ) 14 | VALUES ( 15 | ${record.id}, 16 | ${record.value} 17 | ) 18 | ON CONFLICT(id) 19 | DO UPDATE SET 20 | value = ${record.value}; 21 | ` 22 | } satisfies { 23 | [K in RecordTable]: (record: TableToRecord[K]) => Sql 24 | } -------------------------------------------------------------------------------- /src/index.css: -------------------------------------------------------------------------------- 1 | :root { 2 | font-family: Inter, system-ui, Avenir, Helvetica, Arial, sans-serif; 3 | line-height: 1.5; 4 | font-weight: 400; 5 | 6 | color-scheme: light dark; 7 | color: rgba(255, 255, 255, 0.87); 8 | background-color: #242424; 9 | 10 | font-synthesis: none; 11 | text-rendering: optimizeLegibility; 12 | -webkit-font-smoothing: antialiased; 13 | -moz-osx-font-smoothing: grayscale; 14 | } 15 | 16 | a { 17 | font-weight: 500; 18 | color: #646cff; 19 | text-decoration: inherit; 20 | } 21 | a:hover { 22 | color: #535bf2; 23 | } 24 | 25 | body { 26 | margin: 0; 27 | display: flex; 28 | place-items: center; 29 | min-width: 320px; 30 | min-height: 100vh; 31 | } 32 | 33 | h1 { 34 | font-size: 3.2em; 35 | line-height: 1.1; 36 | } 37 | 38 | button { 39 | border-radius: 8px; 40 | border: 1px solid transparent; 41 | padding: 0.6em 1.2em; 42 | font-size: 1em; 43 | font-weight: 500; 44 | font-family: inherit; 45 | background-color: #1a1a1a; 46 | cursor: pointer; 47 | transition: border-color 0.25s; 48 | } 49 | button:hover { 50 | border-color: #646cff; 51 | } 52 | button:focus, 53 | button:focus-visible { 54 | outline: 4px auto -webkit-focus-ring-color; 55 | } 56 | 57 | @media (prefers-color-scheme: light) { 58 | :root { 59 | color: #213547; 60 | background-color: #ffffff; 61 | } 62 | a:hover { 63 | color: #747bff; 64 | } 65 | button { 66 | background-color: #f9f9f9; 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /src/main.tsx: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import ReactDOM from 'react-dom/client' 3 | import App from './App.tsx' 4 | import './index.css' 5 | 6 | ReactDOM.createRoot(document.getElementById('root')!).render( 7 | 8 | 9 | , 10 | ) 11 | -------------------------------------------------------------------------------- /src/useThreadMessages.ts: -------------------------------------------------------------------------------- 1 | import sql from 'sql-template-tag'; 2 | import { useDatabaseContext } from './database/context'; 3 | import { SQLiteClient } from './database/SqliteDatabase'; 4 | import { useObservable, useObservableState } from 'observable-hooks'; 5 | import { of, switchMap } from 'rxjs'; 6 | import { MessageRecord } from './database/schema'; 7 | 8 | export function useThreadMessages(threadId: string | null | undefined) { 9 | const db = useDatabaseContext(); 10 | 11 | const query = useObservable( 12 | (inputs$) => { 13 | return inputs$.pipe( 14 | switchMap(([threadId, db]) => 15 | threadId 16 | ? db.observeQuery(getSqlForThreadMessages(threadId)) 17 | : of(null) 18 | ) 19 | ); 20 | }, 21 | [threadId, db] 22 | ); 23 | 24 | const record = useObservableState(query, 'loading'); 25 | 26 | return record; 27 | } 28 | 29 | export async function getThreadMessages(db: SQLiteClient, threadId: string) { 30 | const query = getSqlForThreadMessages(threadId); 31 | 32 | const { resultRows } = await db.exec({ 33 | sql: query.sql, 34 | bind: query.values, 35 | }); 36 | 37 | return resultRows; 38 | } 39 | 40 | // What if we had a server we were fetching these records from and then 41 | // loading them into the client. When should this query update? 42 | // 43 | // 1. It should update if any of the records returned from this query 44 | // are updated. 45 | // 2. It should update if any records are added or removed from the 46 | // `message` table IF those records have `thread_id = ${threadId}` 47 | // 48 | // We can handle #1 easily enough. Simply create a globally unique key for 49 | // the record and request updates about it from the server. E.g. 50 | // `${table}:${recordId}`. The server can easily figure out when to send 51 | // updates if a record with that ID and table is updated. 52 | // 53 | // What about #2? Here we can also pass a key to the server asking it 54 | // for specific updates. In this case we can use 55 | // `message:thread_id:${threadId}` for the key. The server knows 56 | // that if any `message` record with a `message.thread_id === ${threadId}` 57 | // is updated, then we send an update message down to the client containing 58 | // a globally unique identifier (e.g `${table}:${recordId}`) for that 59 | // record. The client then just fetches that record and our SQLite 60 | // observability automatically kicks in and rerenders any queries. 61 | const getSqlForThreadMessages = (threadId: string) => sql` 62 | SELECT 63 | * 64 | FROM 65 | message 66 | WHERE 67 | message.thread_id = ${threadId}; 68 | `; 69 | 70 | // But what about more complex queries? In this case the client 71 | // might need to subscribe to multiple keys associated with the query. 72 | // For example, below is a contrived query that involves two joins. 73 | // This query it attempting to fetch the labels which are associated 74 | // with the threads in a specific channel. It's a many to many to many 75 | // join. 76 | // 77 | // This query will update when 78 | // 1. Any of the returned labels update or 79 | // 2. A channel_thread is added/removed with `channel_thread.channel_id === ${channelId}` 80 | // 3. A thread_label is added/removed with 81 | // `thread_id === ${...uhh...how do we do this?}` 82 | const getSqlForLabelsAssocWithThreadsInChannel = (channelId: string) => sql` 83 | SELECT 84 | label.* 85 | FROM 86 | channel_thread 87 | JOIN 88 | thread_label ON thread_label.thread_id = channel_thread.thread_id 89 | JOIN 90 | label ON label.id = thread_label.label_id 91 | WHERE 92 | channel_thread.channel_id = ${channelId} 93 | `; 94 | 95 | // In this case, we can't use the same technique as before on this query. 96 | // So we have two choices. 97 | 98 | // 1. We can create a custom subscription key and send that to the client saying 99 | // I'd like updates to the getSqlForLabelsAssocWithThreadsInChannel query with 100 | // channelId === "1" (or whatever) please. Then the server needs to figure out 101 | // when that query has been updated and send updates to the client. This 102 | // sounds difficult... 103 | // 104 | // 2. The better choice is to harness the power of observables and perform some 105 | // simpler client side joins which we can easily track. 106 | // 107 | // Lets see what that looks like! 108 | // 109 | // Lets try breaking up the above query into two queries. 110 | // 111 | // This thread is updated when 112 | // 1. A returned channel_thread is updated 113 | // 2. A channel_thread with `channel_id === ${channelId}` is added or removed. 114 | const getSqlForChannelThreads = (channelId: string) => sql` 115 | SELECT 116 | * 117 | FROM 118 | channel_thread 119 | WHERE 120 | channel_thread.channel_id = ${channelId} 121 | `; 122 | 123 | // And this one is updated when 124 | // 1. A returned label is updated 125 | // 2. A thread_label with `thread_id === ${threadId}` is 126 | // added/removed 127 | const getSqlForLabelsInThread = (threadId: string) => sql` 128 | SELECT 129 | label.* 130 | FROM 131 | thread_label 132 | JOIN 133 | label ON label.id = thread_label.label_id 134 | WHERE 135 | thread_label.thread_id = ${threadId} 136 | `; 137 | 138 | // We can combine these queries with a client-side join using our live 139 | // query results and [rxjs](https://rxjs.dev). Here's we're subscribing to 140 | // our channel threads query, then using the results to subscribe to a bunch 141 | // of labels for thread queries. Then we deduplicate the results. 142 | // 143 | // This does increase the total amount of time it takes us to resolve this query, 144 | // but if your queries are each resolving in milliseconds this should often be 145 | // acceptable. 146 | function observeLabelsAssocWithThreadsInChannel( 147 | db: SQLiteClient, 148 | channelId: string 149 | ): Observable { 150 | return db.observeQuery(getSqlForChannelThreads(channelId)).pipe( 151 | switchMap((threadLabels) => { 152 | if (threadLabels.length === 0) return of([]); 153 | 154 | return combineLatest( 155 | threadLabels.map((thread_id) => 156 | db.observeQuery(getSqlForLabelsInThread(thread_id)) 157 | ) 158 | ); 159 | }), 160 | map((results) => uniqBy(results.flat(), 'id')) 161 | ); 162 | } 163 | -------------------------------------------------------------------------------- /src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ES2020", 4 | "useDefineForClassFields": true, 5 | "lib": ["ES2020", "DOM", "DOM.Iterable"], 6 | "module": "ESNext", 7 | "skipLibCheck": true, 8 | 9 | /* Bundler mode */ 10 | "moduleResolution": "bundler", 11 | "allowImportingTsExtensions": true, 12 | "resolveJsonModule": true, 13 | "isolatedModules": true, 14 | "noEmit": true, 15 | "jsx": "react-jsx", 16 | 17 | /* Linting */ 18 | "strict": true, 19 | "noUnusedLocals": true, 20 | "noUnusedParameters": true, 21 | "noFallthroughCasesInSwitch": true 22 | }, 23 | "include": ["src"], 24 | "references": [{ "path": "./tsconfig.node.json" }] 25 | } 26 | -------------------------------------------------------------------------------- /tsconfig.node.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "composite": true, 4 | "skipLibCheck": true, 5 | "module": "ESNext", 6 | "moduleResolution": "bundler", 7 | "allowSyntheticDefaultImports": true 8 | }, 9 | "include": ["vite.config.ts"] 10 | } 11 | -------------------------------------------------------------------------------- /vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vite'; 2 | import react from '@vitejs/plugin-react'; 3 | 4 | // https://vitejs.dev/config/ 5 | export default defineConfig({ 6 | plugins: [react()], 7 | optimizeDeps: { 8 | exclude: ['@sqlite.org/sqlite-wasm'], 9 | }, 10 | }); 11 | -------------------------------------------------------------------------------- /yarn.lock: -------------------------------------------------------------------------------- 1 | # THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. 2 | # yarn lockfile v1 3 | 4 | 5 | "@aashutoshrathi/word-wrap@^1.2.3": 6 | version "1.2.6" 7 | resolved "https://registry.yarnpkg.com/@aashutoshrathi/word-wrap/-/word-wrap-1.2.6.tgz#bd9154aec9983f77b3a034ecaa015c2e4201f6cf" 8 | integrity sha512-1Yjs2SvM8TflER/OD3cOjhWWOZb58A2t7wpE2S9XfBYTiIl+XFhQG2bjy4Pu1I+EAlCNUzRDYDdFwFYUKvXcIA== 9 | 10 | "@ampproject/remapping@^2.2.0": 11 | version "2.2.1" 12 | resolved "https://registry.yarnpkg.com/@ampproject/remapping/-/remapping-2.2.1.tgz#99e8e11851128b8702cd57c33684f1d0f260b630" 13 | integrity sha512-lFMjJTrFL3j7L9yBxwYfCq2k6qqwHyzuUl/XBnif78PWTJYyL/dfowQHWE3sp6U6ZzqWiiIZnpTMO96zhkjwtg== 14 | dependencies: 15 | "@jridgewell/gen-mapping" "^0.3.0" 16 | "@jridgewell/trace-mapping" "^0.3.9" 17 | 18 | "@babel/code-frame@^7.22.13": 19 | version "7.22.13" 20 | resolved "https://registry.yarnpkg.com/@babel/code-frame/-/code-frame-7.22.13.tgz#e3c1c099402598483b7a8c46a721d1038803755e" 21 | integrity sha512-XktuhWlJ5g+3TJXc5upd9Ks1HutSArik6jf2eAjYFyIOf4ej3RN+184cZbzDvbPnuTJIUhPKKJE3cIsYTiAT3w== 22 | dependencies: 23 | "@babel/highlight" "^7.22.13" 24 | chalk "^2.4.2" 25 | 26 | "@babel/compat-data@^7.22.9": 27 | version "7.23.2" 28 | resolved "https://registry.yarnpkg.com/@babel/compat-data/-/compat-data-7.23.2.tgz#6a12ced93455827037bfb5ed8492820d60fc32cc" 29 | integrity sha512-0S9TQMmDHlqAZ2ITT95irXKfxN9bncq8ZCoJhun3nHL/lLUxd2NKBJYoNGWH7S0hz6fRQwWlAWn/ILM0C70KZQ== 30 | 31 | "@babel/core@^7.22.20": 32 | version "7.23.2" 33 | resolved "https://registry.yarnpkg.com/@babel/core/-/core-7.23.2.tgz#ed10df0d580fff67c5f3ee70fd22e2e4c90a9f94" 34 | integrity sha512-n7s51eWdaWZ3vGT2tD4T7J6eJs3QoBXydv7vkUM06Bf1cbVD2Kc2UrkzhiQwobfV7NwOnQXYL7UBJ5VPU+RGoQ== 35 | dependencies: 36 | "@ampproject/remapping" "^2.2.0" 37 | "@babel/code-frame" "^7.22.13" 38 | "@babel/generator" "^7.23.0" 39 | "@babel/helper-compilation-targets" "^7.22.15" 40 | "@babel/helper-module-transforms" "^7.23.0" 41 | "@babel/helpers" "^7.23.2" 42 | "@babel/parser" "^7.23.0" 43 | "@babel/template" "^7.22.15" 44 | "@babel/traverse" "^7.23.2" 45 | "@babel/types" "^7.23.0" 46 | convert-source-map "^2.0.0" 47 | debug "^4.1.0" 48 | gensync "^1.0.0-beta.2" 49 | json5 "^2.2.3" 50 | semver "^6.3.1" 51 | 52 | "@babel/generator@^7.23.0": 53 | version "7.23.0" 54 | resolved "https://registry.yarnpkg.com/@babel/generator/-/generator-7.23.0.tgz#df5c386e2218be505b34837acbcb874d7a983420" 55 | integrity sha512-lN85QRR+5IbYrMWM6Y4pE/noaQtg4pNiqeNGX60eqOfo6gtEj6uw/JagelB8vVztSd7R6M5n1+PQkDbHbBRU4g== 56 | dependencies: 57 | "@babel/types" "^7.23.0" 58 | "@jridgewell/gen-mapping" "^0.3.2" 59 | "@jridgewell/trace-mapping" "^0.3.17" 60 | jsesc "^2.5.1" 61 | 62 | "@babel/helper-compilation-targets@^7.22.15": 63 | version "7.22.15" 64 | resolved "https://registry.yarnpkg.com/@babel/helper-compilation-targets/-/helper-compilation-targets-7.22.15.tgz#0698fc44551a26cf29f18d4662d5bf545a6cfc52" 65 | integrity sha512-y6EEzULok0Qvz8yyLkCvVX+02ic+By2UdOhylwUOvOn9dvYc9mKICJuuU1n1XBI02YWsNsnrY1kc6DVbjcXbtw== 66 | dependencies: 67 | "@babel/compat-data" "^7.22.9" 68 | "@babel/helper-validator-option" "^7.22.15" 69 | browserslist "^4.21.9" 70 | lru-cache "^5.1.1" 71 | semver "^6.3.1" 72 | 73 | "@babel/helper-environment-visitor@^7.22.20": 74 | version "7.22.20" 75 | resolved "https://registry.yarnpkg.com/@babel/helper-environment-visitor/-/helper-environment-visitor-7.22.20.tgz#96159db61d34a29dba454c959f5ae4a649ba9167" 76 | integrity sha512-zfedSIzFhat/gFhWfHtgWvlec0nqB9YEIVrpuwjruLlXfUSnA8cJB0miHKwqDnQ7d32aKo2xt88/xZptwxbfhA== 77 | 78 | "@babel/helper-function-name@^7.23.0": 79 | version "7.23.0" 80 | resolved "https://registry.yarnpkg.com/@babel/helper-function-name/-/helper-function-name-7.23.0.tgz#1f9a3cdbd5b2698a670c30d2735f9af95ed52759" 81 | integrity sha512-OErEqsrxjZTJciZ4Oo+eoZqeW9UIiOcuYKRJA4ZAgV9myA+pOXhhmpfNCKjEH/auVfEYVFJ6y1Tc4r0eIApqiw== 82 | dependencies: 83 | "@babel/template" "^7.22.15" 84 | "@babel/types" "^7.23.0" 85 | 86 | "@babel/helper-hoist-variables@^7.22.5": 87 | version "7.22.5" 88 | resolved "https://registry.yarnpkg.com/@babel/helper-hoist-variables/-/helper-hoist-variables-7.22.5.tgz#c01a007dac05c085914e8fb652b339db50d823bb" 89 | integrity sha512-wGjk9QZVzvknA6yKIUURb8zY3grXCcOZt+/7Wcy8O2uctxhplmUPkOdlgoNhmdVee2c92JXbf1xpMtVNbfoxRw== 90 | dependencies: 91 | "@babel/types" "^7.22.5" 92 | 93 | "@babel/helper-module-imports@^7.22.15": 94 | version "7.22.15" 95 | resolved "https://registry.yarnpkg.com/@babel/helper-module-imports/-/helper-module-imports-7.22.15.tgz#16146307acdc40cc00c3b2c647713076464bdbf0" 96 | integrity sha512-0pYVBnDKZO2fnSPCrgM/6WMc7eS20Fbok+0r88fp+YtWVLZrp4CkafFGIp+W0VKw4a22sgebPT99y+FDNMdP4w== 97 | dependencies: 98 | "@babel/types" "^7.22.15" 99 | 100 | "@babel/helper-module-transforms@^7.23.0": 101 | version "7.23.0" 102 | resolved "https://registry.yarnpkg.com/@babel/helper-module-transforms/-/helper-module-transforms-7.23.0.tgz#3ec246457f6c842c0aee62a01f60739906f7047e" 103 | integrity sha512-WhDWw1tdrlT0gMgUJSlX0IQvoO1eN279zrAUbVB+KpV2c3Tylz8+GnKOLllCS6Z/iZQEyVYxhZVUdPTqs2YYPw== 104 | dependencies: 105 | "@babel/helper-environment-visitor" "^7.22.20" 106 | "@babel/helper-module-imports" "^7.22.15" 107 | "@babel/helper-simple-access" "^7.22.5" 108 | "@babel/helper-split-export-declaration" "^7.22.6" 109 | "@babel/helper-validator-identifier" "^7.22.20" 110 | 111 | "@babel/helper-plugin-utils@^7.22.5": 112 | version "7.22.5" 113 | resolved "https://registry.yarnpkg.com/@babel/helper-plugin-utils/-/helper-plugin-utils-7.22.5.tgz#dd7ee3735e8a313b9f7b05a773d892e88e6d7295" 114 | integrity sha512-uLls06UVKgFG9QD4OeFYLEGteMIAa5kpTPcFL28yuCIIzsf6ZyKZMllKVOCZFhiZ5ptnwX4mtKdWCBE/uT4amg== 115 | 116 | "@babel/helper-simple-access@^7.22.5": 117 | version "7.22.5" 118 | resolved "https://registry.yarnpkg.com/@babel/helper-simple-access/-/helper-simple-access-7.22.5.tgz#4938357dc7d782b80ed6dbb03a0fba3d22b1d5de" 119 | integrity sha512-n0H99E/K+Bika3++WNL17POvo4rKWZ7lZEp1Q+fStVbUi8nxPQEBOlTmCOxW/0JsS56SKKQ+ojAe2pHKJHN35w== 120 | dependencies: 121 | "@babel/types" "^7.22.5" 122 | 123 | "@babel/helper-split-export-declaration@^7.22.6": 124 | version "7.22.6" 125 | resolved "https://registry.yarnpkg.com/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.22.6.tgz#322c61b7310c0997fe4c323955667f18fcefb91c" 126 | integrity sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g== 127 | dependencies: 128 | "@babel/types" "^7.22.5" 129 | 130 | "@babel/helper-string-parser@^7.22.5": 131 | version "7.22.5" 132 | resolved "https://registry.yarnpkg.com/@babel/helper-string-parser/-/helper-string-parser-7.22.5.tgz#533f36457a25814cf1df6488523ad547d784a99f" 133 | integrity sha512-mM4COjgZox8U+JcXQwPijIZLElkgEpO5rsERVDJTc2qfCDfERyob6k5WegS14SX18IIjv+XD+GrqNumY5JRCDw== 134 | 135 | "@babel/helper-validator-identifier@^7.22.20": 136 | version "7.22.20" 137 | resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.22.20.tgz#c4ae002c61d2879e724581d96665583dbc1dc0e0" 138 | integrity sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A== 139 | 140 | "@babel/helper-validator-option@^7.22.15": 141 | version "7.22.15" 142 | resolved "https://registry.yarnpkg.com/@babel/helper-validator-option/-/helper-validator-option-7.22.15.tgz#694c30dfa1d09a6534cdfcafbe56789d36aba040" 143 | integrity sha512-bMn7RmyFjY/mdECUbgn9eoSY4vqvacUnS9i9vGAGttgFWesO6B4CYWA7XlpbWgBt71iv/hfbPlynohStqnu5hA== 144 | 145 | "@babel/helpers@^7.23.2": 146 | version "7.23.2" 147 | resolved "https://registry.yarnpkg.com/@babel/helpers/-/helpers-7.23.2.tgz#2832549a6e37d484286e15ba36a5330483cac767" 148 | integrity sha512-lzchcp8SjTSVe/fPmLwtWVBFC7+Tbn8LGHDVfDp9JGxpAY5opSaEFgt8UQvrnECWOTdji2mOWMz1rOhkHscmGQ== 149 | dependencies: 150 | "@babel/template" "^7.22.15" 151 | "@babel/traverse" "^7.23.2" 152 | "@babel/types" "^7.23.0" 153 | 154 | "@babel/highlight@^7.22.13": 155 | version "7.22.20" 156 | resolved "https://registry.yarnpkg.com/@babel/highlight/-/highlight-7.22.20.tgz#4ca92b71d80554b01427815e06f2df965b9c1f54" 157 | integrity sha512-dkdMCN3py0+ksCgYmGG8jKeGA/8Tk+gJwSYYlFGxG5lmhfKNoAy004YpLxpS1W2J8m/EK2Ew+yOs9pVRwO89mg== 158 | dependencies: 159 | "@babel/helper-validator-identifier" "^7.22.20" 160 | chalk "^2.4.2" 161 | js-tokens "^4.0.0" 162 | 163 | "@babel/parser@^7.1.0", "@babel/parser@^7.20.7", "@babel/parser@^7.22.15", "@babel/parser@^7.23.0": 164 | version "7.23.0" 165 | resolved "https://registry.yarnpkg.com/@babel/parser/-/parser-7.23.0.tgz#da950e622420bf96ca0d0f2909cdddac3acd8719" 166 | integrity sha512-vvPKKdMemU85V9WE/l5wZEmImpCtLqbnTvqDS2U1fJ96KrxoW7KrXhNsNCblQlg8Ck4b85yxdTyelsMUgFUXiw== 167 | 168 | "@babel/plugin-transform-react-jsx-self@^7.22.5": 169 | version "7.22.5" 170 | resolved "https://registry.yarnpkg.com/@babel/plugin-transform-react-jsx-self/-/plugin-transform-react-jsx-self-7.22.5.tgz#ca2fdc11bc20d4d46de01137318b13d04e481d8e" 171 | integrity sha512-nTh2ogNUtxbiSbxaT4Ds6aXnXEipHweN9YRgOX/oNXdf0cCrGn/+2LozFa3lnPV5D90MkjhgckCPBrsoSc1a7g== 172 | dependencies: 173 | "@babel/helper-plugin-utils" "^7.22.5" 174 | 175 | "@babel/plugin-transform-react-jsx-source@^7.22.5": 176 | version "7.22.5" 177 | resolved "https://registry.yarnpkg.com/@babel/plugin-transform-react-jsx-source/-/plugin-transform-react-jsx-source-7.22.5.tgz#49af1615bfdf6ed9d3e9e43e425e0b2b65d15b6c" 178 | integrity sha512-yIiRO6yobeEIaI0RTbIr8iAK9FcBHLtZq0S89ZPjDLQXBA4xvghaKqI0etp/tF3htTM0sazJKKLz9oEiGRtu7w== 179 | dependencies: 180 | "@babel/helper-plugin-utils" "^7.22.5" 181 | 182 | "@babel/template@^7.22.15": 183 | version "7.22.15" 184 | resolved "https://registry.yarnpkg.com/@babel/template/-/template-7.22.15.tgz#09576efc3830f0430f4548ef971dde1350ef2f38" 185 | integrity sha512-QPErUVm4uyJa60rkI73qneDacvdvzxshT3kksGqlGWYdOTIUOwJ7RDUL8sGqslY1uXWSL6xMFKEXDS3ox2uF0w== 186 | dependencies: 187 | "@babel/code-frame" "^7.22.13" 188 | "@babel/parser" "^7.22.15" 189 | "@babel/types" "^7.22.15" 190 | 191 | "@babel/traverse@^7.23.2": 192 | version "7.23.2" 193 | resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.23.2.tgz#329c7a06735e144a506bdb2cad0268b7f46f4ad8" 194 | integrity sha512-azpe59SQ48qG6nu2CzcMLbxUudtN+dOM9kDbUqGq3HXUJRlo7i8fvPoxQUzYgLZ4cMVmuZgm8vvBpNeRhd6XSw== 195 | dependencies: 196 | "@babel/code-frame" "^7.22.13" 197 | "@babel/generator" "^7.23.0" 198 | "@babel/helper-environment-visitor" "^7.22.20" 199 | "@babel/helper-function-name" "^7.23.0" 200 | "@babel/helper-hoist-variables" "^7.22.5" 201 | "@babel/helper-split-export-declaration" "^7.22.6" 202 | "@babel/parser" "^7.23.0" 203 | "@babel/types" "^7.23.0" 204 | debug "^4.1.0" 205 | globals "^11.1.0" 206 | 207 | "@babel/types@^7.0.0", "@babel/types@^7.20.7", "@babel/types@^7.22.15", "@babel/types@^7.22.5", "@babel/types@^7.23.0": 208 | version "7.23.0" 209 | resolved "https://registry.yarnpkg.com/@babel/types/-/types-7.23.0.tgz#8c1f020c9df0e737e4e247c0619f58c68458aaeb" 210 | integrity sha512-0oIyUfKoI3mSqMvsxBdclDwxXKXAUA8v/apZbc+iSyARYou1o8ZGDxbUYyLFoW2arqS2jDGqJuZvv1d/io1axg== 211 | dependencies: 212 | "@babel/helper-string-parser" "^7.22.5" 213 | "@babel/helper-validator-identifier" "^7.22.20" 214 | to-fast-properties "^2.0.0" 215 | 216 | "@eslint-community/eslint-utils@^4.2.0", "@eslint-community/eslint-utils@^4.4.0": 217 | version "4.4.0" 218 | resolved "https://registry.yarnpkg.com/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz#a23514e8fb9af1269d5f7788aa556798d61c6b59" 219 | integrity sha512-1/sA4dwrzBAyeUoQ6oxahHKmrZvsnLCg4RfxW3ZFGGmQkSNQPFNLV9CUEFQP1x9EYXHTo5p6xdhZM1Ne9p/AfA== 220 | dependencies: 221 | eslint-visitor-keys "^3.3.0" 222 | 223 | "@eslint-community/regexpp@^4.5.1", "@eslint-community/regexpp@^4.6.1": 224 | version "4.9.1" 225 | resolved "https://registry.yarnpkg.com/@eslint-community/regexpp/-/regexpp-4.9.1.tgz#449dfa81a57a1d755b09aa58d826c1262e4283b4" 226 | integrity sha512-Y27x+MBLjXa+0JWDhykM3+JE+il3kHKAEqabfEWq3SDhZjLYb6/BHL/JKFnH3fe207JaXkyDo685Oc2Glt6ifA== 227 | 228 | "@eslint/eslintrc@^2.1.2": 229 | version "2.1.2" 230 | resolved "https://registry.yarnpkg.com/@eslint/eslintrc/-/eslintrc-2.1.2.tgz#c6936b4b328c64496692f76944e755738be62396" 231 | integrity sha512-+wvgpDsrB1YqAMdEUCcnTlpfVBH7Vqn6A/NT3D8WVXFIaKMlErPIZT3oCIAVCOtarRpMtelZLqJeU3t7WY6X6g== 232 | dependencies: 233 | ajv "^6.12.4" 234 | debug "^4.3.2" 235 | espree "^9.6.0" 236 | globals "^13.19.0" 237 | ignore "^5.2.0" 238 | import-fresh "^3.2.1" 239 | js-yaml "^4.1.0" 240 | minimatch "^3.1.2" 241 | strip-json-comments "^3.1.1" 242 | 243 | "@eslint/js@8.51.0": 244 | version "8.51.0" 245 | resolved "https://registry.yarnpkg.com/@eslint/js/-/js-8.51.0.tgz#6d419c240cfb2b66da37df230f7e7eef801c32fa" 246 | integrity sha512-HxjQ8Qn+4SI3/AFv6sOrDB+g6PpUTDwSJiQqOrnneEk8L71161srI9gjzzZvYVbzHiVg/BvcH95+cK/zfIt4pg== 247 | 248 | "@humanwhocodes/config-array@^0.11.11": 249 | version "0.11.11" 250 | resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.11.tgz#88a04c570dbbc7dd943e4712429c3df09bc32844" 251 | integrity sha512-N2brEuAadi0CcdeMXUkhbZB84eskAc8MEX1By6qEchoVywSgXPIjou4rYsl0V3Hj0ZnuGycGCjdNgockbzeWNA== 252 | dependencies: 253 | "@humanwhocodes/object-schema" "^1.2.1" 254 | debug "^4.1.1" 255 | minimatch "^3.0.5" 256 | 257 | "@humanwhocodes/module-importer@^1.0.1": 258 | version "1.0.1" 259 | resolved "https://registry.yarnpkg.com/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz#af5b2691a22b44be847b0ca81641c5fb6ad0172c" 260 | integrity sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA== 261 | 262 | "@humanwhocodes/object-schema@^1.2.1": 263 | version "1.2.1" 264 | resolved "https://registry.yarnpkg.com/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz#b520529ec21d8e5945a1851dfd1c32e94e39ff45" 265 | integrity sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA== 266 | 267 | "@jridgewell/gen-mapping@^0.3.0", "@jridgewell/gen-mapping@^0.3.2": 268 | version "0.3.3" 269 | resolved "https://registry.yarnpkg.com/@jridgewell/gen-mapping/-/gen-mapping-0.3.3.tgz#7e02e6eb5df901aaedb08514203b096614024098" 270 | integrity sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ== 271 | dependencies: 272 | "@jridgewell/set-array" "^1.0.1" 273 | "@jridgewell/sourcemap-codec" "^1.4.10" 274 | "@jridgewell/trace-mapping" "^0.3.9" 275 | 276 | "@jridgewell/resolve-uri@^3.1.0": 277 | version "3.1.1" 278 | resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.1.1.tgz#c08679063f279615a3326583ba3a90d1d82cc721" 279 | integrity sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA== 280 | 281 | "@jridgewell/set-array@^1.0.1": 282 | version "1.1.2" 283 | resolved "https://registry.yarnpkg.com/@jridgewell/set-array/-/set-array-1.1.2.tgz#7c6cf998d6d20b914c0a55a91ae928ff25965e72" 284 | integrity sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw== 285 | 286 | "@jridgewell/sourcemap-codec@^1.4.10", "@jridgewell/sourcemap-codec@^1.4.14": 287 | version "1.4.15" 288 | resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz#d7c6e6755c78567a951e04ab52ef0fd26de59f32" 289 | integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== 290 | 291 | "@jridgewell/trace-mapping@^0.3.17", "@jridgewell/trace-mapping@^0.3.9": 292 | version "0.3.20" 293 | resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.20.tgz#72e45707cf240fa6b081d0366f8265b0cd10197f" 294 | integrity sha512-R8LcPeWZol2zR8mmH3JeKQ6QRCFb7XgUhV9ZlGhHLGyg4wpPiPZNQOOWhFZhxKw8u//yTbNGI42Bx/3paXEQ+Q== 295 | dependencies: 296 | "@jridgewell/resolve-uri" "^3.1.0" 297 | "@jridgewell/sourcemap-codec" "^1.4.14" 298 | 299 | "@nodelib/fs.scandir@2.1.5": 300 | version "2.1.5" 301 | resolved "https://registry.yarnpkg.com/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz#7619c2eb21b25483f6d167548b4cfd5a7488c3d5" 302 | integrity sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g== 303 | dependencies: 304 | "@nodelib/fs.stat" "2.0.5" 305 | run-parallel "^1.1.9" 306 | 307 | "@nodelib/fs.stat@2.0.5", "@nodelib/fs.stat@^2.0.2": 308 | version "2.0.5" 309 | resolved "https://registry.yarnpkg.com/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz#5bd262af94e9d25bd1e71b05deed44876a222e8b" 310 | integrity sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A== 311 | 312 | "@nodelib/fs.walk@^1.2.3", "@nodelib/fs.walk@^1.2.8": 313 | version "1.2.8" 314 | resolved "https://registry.yarnpkg.com/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz#e95737e8bb6746ddedf69c556953494f196fe69a" 315 | integrity sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg== 316 | dependencies: 317 | "@nodelib/fs.scandir" "2.1.5" 318 | fastq "^1.6.0" 319 | 320 | "@sqlite.org/sqlite-wasm@^3.43.2-build1": 321 | version "3.43.2-build1" 322 | resolved "https://registry.yarnpkg.com/@sqlite.org/sqlite-wasm/-/sqlite-wasm-3.43.2-build1.tgz#5f1768e2df7328bdd9a5b9ec7c94eaa0bd36705a" 323 | integrity sha512-f0qln3z0RFWV5WTwsidFRJ0e8dCeilGB4kKVUTA0IHVPIIAW75AWZKfPcI5kHiC+VIYhlT8lM3k+9MNeAcv9uA== 324 | 325 | "@types/babel__core@^7.20.2": 326 | version "7.20.3" 327 | resolved "https://registry.yarnpkg.com/@types/babel__core/-/babel__core-7.20.3.tgz#d5625a50b6f18244425a1359a858c73d70340778" 328 | integrity sha512-54fjTSeSHwfan8AyHWrKbfBWiEUrNTZsUwPTDSNaaP1QDQIZbeNUg3a59E9D+375MzUw/x1vx2/0F5LBz+AeYA== 329 | dependencies: 330 | "@babel/parser" "^7.20.7" 331 | "@babel/types" "^7.20.7" 332 | "@types/babel__generator" "*" 333 | "@types/babel__template" "*" 334 | "@types/babel__traverse" "*" 335 | 336 | "@types/babel__generator@*": 337 | version "7.6.6" 338 | resolved "https://registry.yarnpkg.com/@types/babel__generator/-/babel__generator-7.6.6.tgz#676f89f67dc8ddaae923f70ebc5f1fa800c031a8" 339 | integrity sha512-66BXMKb/sUWbMdBNdMvajU7i/44RkrA3z/Yt1c7R5xejt8qh84iU54yUWCtm0QwGJlDcf/gg4zd/x4mpLAlb/w== 340 | dependencies: 341 | "@babel/types" "^7.0.0" 342 | 343 | "@types/babel__template@*": 344 | version "7.4.3" 345 | resolved "https://registry.yarnpkg.com/@types/babel__template/-/babel__template-7.4.3.tgz#db9ac539a2fe05cfe9e168b24f360701bde41f5f" 346 | integrity sha512-ciwyCLeuRfxboZ4isgdNZi/tkt06m8Tw6uGbBSBgWrnnZGNXiEyM27xc/PjXGQLqlZ6ylbgHMnm7ccF9tCkOeQ== 347 | dependencies: 348 | "@babel/parser" "^7.1.0" 349 | "@babel/types" "^7.0.0" 350 | 351 | "@types/babel__traverse@*": 352 | version "7.20.3" 353 | resolved "https://registry.yarnpkg.com/@types/babel__traverse/-/babel__traverse-7.20.3.tgz#a971aa47441b28ef17884ff945d0551265a2d058" 354 | integrity sha512-Lsh766rGEFbaxMIDH7Qa+Yha8cMVI3qAK6CHt3OR0YfxOIn5Z54iHiyDRycHrBqeIiqGa20Kpsv1cavfBKkRSw== 355 | dependencies: 356 | "@babel/types" "^7.20.7" 357 | 358 | "@types/json-schema@^7.0.12": 359 | version "7.0.14" 360 | resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.14.tgz#74a97a5573980802f32c8e47b663530ab3b6b7d1" 361 | integrity sha512-U3PUjAudAdJBeC2pgN8uTIKgxrb4nlDF3SF0++EldXQvQBGkpFZMSnwQiIoDU77tv45VgNkl/L4ouD+rEomujw== 362 | 363 | "@types/prop-types@*": 364 | version "15.7.8" 365 | resolved "https://registry.yarnpkg.com/@types/prop-types/-/prop-types-15.7.8.tgz#805eae6e8f41bd19e88917d2ea200dc992f405d3" 366 | integrity sha512-kMpQpfZKSCBqltAJwskgePRaYRFukDkm1oItcAbC3gNELR20XIBcN9VRgg4+m8DKsTfkWeA4m4Imp4DDuWy7FQ== 367 | 368 | "@types/react-dom@^18.2.13": 369 | version "18.2.13" 370 | resolved "https://registry.yarnpkg.com/@types/react-dom/-/react-dom-18.2.13.tgz#89cd7f9ec8b28c8b6f0392b9591671fb4a9e96b7" 371 | integrity sha512-eJIUv7rPP+EC45uNYp/ThhSpE16k22VJUknt5OLoH9tbXoi8bMhwLf5xRuWMywamNbWzhrSmU7IBJfPup1+3fw== 372 | dependencies: 373 | "@types/react" "*" 374 | 375 | "@types/react@*", "@types/react@^18.2.28": 376 | version "18.2.28" 377 | resolved "https://registry.yarnpkg.com/@types/react/-/react-18.2.28.tgz#86877465c0fcf751659a36c769ecedfcfacee332" 378 | integrity sha512-ad4aa/RaaJS3hyGz0BGegdnSRXQBkd1CCYDCdNjBPg90UUpLgo+WlJqb9fMYUxtehmzF3PJaTWqRZjko6BRzBg== 379 | dependencies: 380 | "@types/prop-types" "*" 381 | "@types/scheduler" "*" 382 | csstype "^3.0.2" 383 | 384 | "@types/scheduler@*": 385 | version "0.16.4" 386 | resolved "https://registry.yarnpkg.com/@types/scheduler/-/scheduler-0.16.4.tgz#fedc3e5b15c26dc18faae96bf1317487cb3658cf" 387 | integrity sha512-2L9ifAGl7wmXwP4v3pN4p2FLhD0O1qsJpvKmNin5VA8+UvNVb447UDaAEV6UdrkA+m/Xs58U1RFps44x6TFsVQ== 388 | 389 | "@types/semver@^7.5.0": 390 | version "7.5.3" 391 | resolved "https://registry.yarnpkg.com/@types/semver/-/semver-7.5.3.tgz#9a726e116beb26c24f1ccd6850201e1246122e04" 392 | integrity sha512-OxepLK9EuNEIPxWNME+C6WwbRAOOI2o2BaQEGzz5Lu2e4Z5eDnEo+/aVEDMIXywoJitJ7xWd641wrGLZdtwRyw== 393 | 394 | "@typescript-eslint/eslint-plugin@^6.7.5": 395 | version "6.8.0" 396 | resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-6.8.0.tgz#06abe4265e7c82f20ade2dcc0e3403c32d4f148b" 397 | integrity sha512-GosF4238Tkes2SHPQ1i8f6rMtG6zlKwMEB0abqSJ3Npvos+doIlc/ATG+vX1G9coDF3Ex78zM3heXHLyWEwLUw== 398 | dependencies: 399 | "@eslint-community/regexpp" "^4.5.1" 400 | "@typescript-eslint/scope-manager" "6.8.0" 401 | "@typescript-eslint/type-utils" "6.8.0" 402 | "@typescript-eslint/utils" "6.8.0" 403 | "@typescript-eslint/visitor-keys" "6.8.0" 404 | debug "^4.3.4" 405 | graphemer "^1.4.0" 406 | ignore "^5.2.4" 407 | natural-compare "^1.4.0" 408 | semver "^7.5.4" 409 | ts-api-utils "^1.0.1" 410 | 411 | "@typescript-eslint/parser@^6.7.5": 412 | version "6.8.0" 413 | resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-6.8.0.tgz#bb2a969d583db242f1ee64467542f8b05c2e28cb" 414 | integrity sha512-5tNs6Bw0j6BdWuP8Fx+VH4G9fEPDxnVI7yH1IAPkQH5RUtvKwRoqdecAPdQXv4rSOADAaz1LFBZvZG7VbXivSg== 415 | dependencies: 416 | "@typescript-eslint/scope-manager" "6.8.0" 417 | "@typescript-eslint/types" "6.8.0" 418 | "@typescript-eslint/typescript-estree" "6.8.0" 419 | "@typescript-eslint/visitor-keys" "6.8.0" 420 | debug "^4.3.4" 421 | 422 | "@typescript-eslint/scope-manager@6.8.0": 423 | version "6.8.0" 424 | resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-6.8.0.tgz#5cac7977385cde068ab30686889dd59879811efd" 425 | integrity sha512-xe0HNBVwCph7rak+ZHcFD6A+q50SMsFwcmfdjs9Kz4qDh5hWhaPhFjRs/SODEhroBI5Ruyvyz9LfwUJ624O40g== 426 | dependencies: 427 | "@typescript-eslint/types" "6.8.0" 428 | "@typescript-eslint/visitor-keys" "6.8.0" 429 | 430 | "@typescript-eslint/type-utils@6.8.0": 431 | version "6.8.0" 432 | resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-6.8.0.tgz#50365e44918ca0fd159844b5d6ea96789731e11f" 433 | integrity sha512-RYOJdlkTJIXW7GSldUIHqc/Hkto8E+fZN96dMIFhuTJcQwdRoGN2rEWA8U6oXbLo0qufH7NPElUb+MceHtz54g== 434 | dependencies: 435 | "@typescript-eslint/typescript-estree" "6.8.0" 436 | "@typescript-eslint/utils" "6.8.0" 437 | debug "^4.3.4" 438 | ts-api-utils "^1.0.1" 439 | 440 | "@typescript-eslint/types@6.8.0": 441 | version "6.8.0" 442 | resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-6.8.0.tgz#1ab5d4fe1d613e3f65f6684026ade6b94f7e3ded" 443 | integrity sha512-p5qOxSum7W3k+llc7owEStXlGmSl8FcGvhYt8Vjy7FqEnmkCVlM3P57XQEGj58oqaBWDQXbJDZxwUWMS/EAPNQ== 444 | 445 | "@typescript-eslint/typescript-estree@6.8.0": 446 | version "6.8.0" 447 | resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-6.8.0.tgz#9565f15e0cd12f55cf5aa0dfb130a6cb0d436ba1" 448 | integrity sha512-ISgV0lQ8XgW+mvv5My/+iTUdRmGspducmQcDw5JxznasXNnZn3SKNrTRuMsEXv+V/O+Lw9AGcQCfVaOPCAk/Zg== 449 | dependencies: 450 | "@typescript-eslint/types" "6.8.0" 451 | "@typescript-eslint/visitor-keys" "6.8.0" 452 | debug "^4.3.4" 453 | globby "^11.1.0" 454 | is-glob "^4.0.3" 455 | semver "^7.5.4" 456 | ts-api-utils "^1.0.1" 457 | 458 | "@typescript-eslint/utils@6.8.0": 459 | version "6.8.0" 460 | resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-6.8.0.tgz#d42939c2074c6b59844d0982ce26a51d136c4029" 461 | integrity sha512-dKs1itdE2qFG4jr0dlYLQVppqTE+Itt7GmIf/vX6CSvsW+3ov8PbWauVKyyfNngokhIO9sKZeRGCUo1+N7U98Q== 462 | dependencies: 463 | "@eslint-community/eslint-utils" "^4.4.0" 464 | "@types/json-schema" "^7.0.12" 465 | "@types/semver" "^7.5.0" 466 | "@typescript-eslint/scope-manager" "6.8.0" 467 | "@typescript-eslint/types" "6.8.0" 468 | "@typescript-eslint/typescript-estree" "6.8.0" 469 | semver "^7.5.4" 470 | 471 | "@typescript-eslint/visitor-keys@6.8.0": 472 | version "6.8.0" 473 | resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-6.8.0.tgz#cffebed56ae99c45eba901c378a6447b06be58b8" 474 | integrity sha512-oqAnbA7c+pgOhW2OhGvxm0t1BULX5peQI/rLsNDpGM78EebV3C9IGbX5HNZabuZ6UQrYveCLjKo8Iy/lLlBkkg== 475 | dependencies: 476 | "@typescript-eslint/types" "6.8.0" 477 | eslint-visitor-keys "^3.4.1" 478 | 479 | "@vitejs/plugin-react@^4.1.0": 480 | version "4.1.0" 481 | resolved "https://registry.yarnpkg.com/@vitejs/plugin-react/-/plugin-react-4.1.0.tgz#e4f56f46fd737c5d386bb1f1ade86ba275fe09bd" 482 | integrity sha512-rM0SqazU9iqPUraQ2JlIvReeaxOoRj6n+PzB1C0cBzIbd8qP336nC39/R9yPi3wVcah7E7j/kdU1uCUqMEU4OQ== 483 | dependencies: 484 | "@babel/core" "^7.22.20" 485 | "@babel/plugin-transform-react-jsx-self" "^7.22.5" 486 | "@babel/plugin-transform-react-jsx-source" "^7.22.5" 487 | "@types/babel__core" "^7.20.2" 488 | react-refresh "^0.14.0" 489 | 490 | acorn-jsx@^5.3.2: 491 | version "5.3.2" 492 | resolved "https://registry.yarnpkg.com/acorn-jsx/-/acorn-jsx-5.3.2.tgz#7ed5bb55908b3b2f1bc55c6af1653bada7f07937" 493 | integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ== 494 | 495 | acorn@^8.9.0: 496 | version "8.10.0" 497 | resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.10.0.tgz#8be5b3907a67221a81ab23c7889c4c5526b62ec5" 498 | integrity sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw== 499 | 500 | ajv@^6.12.4: 501 | version "6.12.6" 502 | resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.6.tgz#baf5a62e802b07d977034586f8c3baf5adf26df4" 503 | integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== 504 | dependencies: 505 | fast-deep-equal "^3.1.1" 506 | fast-json-stable-stringify "^2.0.0" 507 | json-schema-traverse "^0.4.1" 508 | uri-js "^4.2.2" 509 | 510 | ansi-regex@^5.0.1: 511 | version "5.0.1" 512 | resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304" 513 | integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== 514 | 515 | ansi-styles@^3.2.1: 516 | version "3.2.1" 517 | resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d" 518 | integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA== 519 | dependencies: 520 | color-convert "^1.9.0" 521 | 522 | ansi-styles@^4.1.0: 523 | version "4.3.0" 524 | resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" 525 | integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== 526 | dependencies: 527 | color-convert "^2.0.1" 528 | 529 | argparse@^2.0.1: 530 | version "2.0.1" 531 | resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" 532 | integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== 533 | 534 | array-union@^2.1.0: 535 | version "2.1.0" 536 | resolved "https://registry.yarnpkg.com/array-union/-/array-union-2.1.0.tgz#b798420adbeb1de828d84acd8a2e23d3efe85e8d" 537 | integrity sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw== 538 | 539 | balanced-match@^1.0.0: 540 | version "1.0.2" 541 | resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee" 542 | integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== 543 | 544 | brace-expansion@^1.1.7: 545 | version "1.1.11" 546 | resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" 547 | integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== 548 | dependencies: 549 | balanced-match "^1.0.0" 550 | concat-map "0.0.1" 551 | 552 | braces@^3.0.2: 553 | version "3.0.2" 554 | resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" 555 | integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== 556 | dependencies: 557 | fill-range "^7.0.1" 558 | 559 | browserslist@^4.21.9: 560 | version "4.22.1" 561 | resolved "https://registry.yarnpkg.com/browserslist/-/browserslist-4.22.1.tgz#ba91958d1a59b87dab6fed8dfbcb3da5e2e9c619" 562 | integrity sha512-FEVc202+2iuClEhZhrWy6ZiAcRLvNMyYcxZ8raemul1DYVOVdFsbqckWLdsixQZCpJlwe77Z3UTalE7jsjnKfQ== 563 | dependencies: 564 | caniuse-lite "^1.0.30001541" 565 | electron-to-chromium "^1.4.535" 566 | node-releases "^2.0.13" 567 | update-browserslist-db "^1.0.13" 568 | 569 | callsites@^3.0.0: 570 | version "3.1.0" 571 | resolved "https://registry.yarnpkg.com/callsites/-/callsites-3.1.0.tgz#b3630abd8943432f54b3f0519238e33cd7df2f73" 572 | integrity sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ== 573 | 574 | caniuse-lite@^1.0.30001541: 575 | version "1.0.30001550" 576 | resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001550.tgz#6ec6a2239eb2a8123cc26cfe0571db5c79eb8669" 577 | integrity sha512-p82WjBYIypO0ukTsd/FG3Xxs+4tFeaY9pfT4amQL8KWtYH7H9nYwReGAbMTJ0hsmRO8IfDtsS6p3ZWj8+1c2RQ== 578 | 579 | chalk@^2.4.2: 580 | version "2.4.2" 581 | resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424" 582 | integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== 583 | dependencies: 584 | ansi-styles "^3.2.1" 585 | escape-string-regexp "^1.0.5" 586 | supports-color "^5.3.0" 587 | 588 | chalk@^4.0.0: 589 | version "4.1.2" 590 | resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.2.tgz#aac4e2b7734a740867aeb16bf02aad556a1e7a01" 591 | integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA== 592 | dependencies: 593 | ansi-styles "^4.1.0" 594 | supports-color "^7.1.0" 595 | 596 | color-convert@^1.9.0: 597 | version "1.9.3" 598 | resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8" 599 | integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg== 600 | dependencies: 601 | color-name "1.1.3" 602 | 603 | color-convert@^2.0.1: 604 | version "2.0.1" 605 | resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" 606 | integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== 607 | dependencies: 608 | color-name "~1.1.4" 609 | 610 | color-name@1.1.3: 611 | version "1.1.3" 612 | resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25" 613 | integrity sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw== 614 | 615 | color-name@~1.1.4: 616 | version "1.1.4" 617 | resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" 618 | integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== 619 | 620 | commander@^2.19.0: 621 | version "2.20.3" 622 | resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.3.tgz#fd485e84c03eb4881c20722ba48035e8531aeb33" 623 | integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== 624 | 625 | concat-map@0.0.1: 626 | version "0.0.1" 627 | resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" 628 | integrity sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg== 629 | 630 | convert-source-map@^2.0.0: 631 | version "2.0.0" 632 | resolved "https://registry.yarnpkg.com/convert-source-map/-/convert-source-map-2.0.0.tgz#4b560f649fc4e918dd0ab75cf4961e8bc882d82a" 633 | integrity sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg== 634 | 635 | cross-spawn@^7.0.2: 636 | version "7.0.3" 637 | resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6" 638 | integrity sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w== 639 | dependencies: 640 | path-key "^3.1.0" 641 | shebang-command "^2.0.0" 642 | which "^2.0.1" 643 | 644 | csstype@^3.0.2: 645 | version "3.1.2" 646 | resolved "https://registry.yarnpkg.com/csstype/-/csstype-3.1.2.tgz#1d4bf9d572f11c14031f0436e1c10bc1f571f50b" 647 | integrity sha512-I7K1Uu0MBPzaFKg4nI5Q7Vs2t+3gWWW648spaF+Rg7pI9ds18Ugn+lvg4SHczUdKlHI5LWBXyqfS8+DufyBsgQ== 648 | 649 | debug@^4.1.0, debug@^4.1.1, debug@^4.3.2, debug@^4.3.4: 650 | version "4.3.4" 651 | resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865" 652 | integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ== 653 | dependencies: 654 | ms "2.1.2" 655 | 656 | deep-is@^0.1.3: 657 | version "0.1.4" 658 | resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.4.tgz#a6f2dce612fadd2ef1f519b73551f17e85199831" 659 | integrity sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ== 660 | 661 | dir-glob@^3.0.1: 662 | version "3.0.1" 663 | resolved "https://registry.yarnpkg.com/dir-glob/-/dir-glob-3.0.1.tgz#56dbf73d992a4a93ba1584f4534063fd2e41717f" 664 | integrity sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA== 665 | dependencies: 666 | path-type "^4.0.0" 667 | 668 | discontinuous-range@1.0.0: 669 | version "1.0.0" 670 | resolved "https://registry.yarnpkg.com/discontinuous-range/-/discontinuous-range-1.0.0.tgz#e38331f0844bba49b9a9cb71c771585aab1bc65a" 671 | integrity sha512-c68LpLbO+7kP/b1Hr1qs8/BJ09F5khZGTxqxZuhzxpmwJKOgRFHJWIb9/KmqnqHhLdO55aOxFH/EGBvUQbL/RQ== 672 | 673 | doctrine@^3.0.0: 674 | version "3.0.0" 675 | resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-3.0.0.tgz#addebead72a6574db783639dc87a121773973961" 676 | integrity sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w== 677 | dependencies: 678 | esutils "^2.0.2" 679 | 680 | electron-to-chromium@^1.4.535: 681 | version "1.4.557" 682 | resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.557.tgz#f3941b569c82b7bb909411855c6ff9bfe1507829" 683 | integrity sha512-6x0zsxyMXpnMJnHrondrD3SuAeKcwij9S+83j2qHAQPXbGTDDfgImzzwgGlzrIcXbHQ42tkG4qA6U860cImNhw== 684 | 685 | esbuild@^0.19.3: 686 | version "0.19.5" 687 | resolved "https://registry.yarnpkg.com/esbuild/-/esbuild-0.19.5.tgz#53a0e19dfbf61ba6c827d51a80813cf071239a8c" 688 | integrity sha512-bUxalY7b1g8vNhQKdB24QDmHeY4V4tw/s6Ak5z+jJX9laP5MoQseTOMemAr0gxssjNcH0MCViG8ONI2kksvfFQ== 689 | 690 | escalade@^3.1.1: 691 | version "3.1.1" 692 | resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" 693 | integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== 694 | 695 | escape-string-regexp@^1.0.5: 696 | version "1.0.5" 697 | resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" 698 | integrity sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg== 699 | 700 | escape-string-regexp@^4.0.0: 701 | version "4.0.0" 702 | resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz#14ba83a5d373e3d311e5afca29cf5bfad965bf34" 703 | integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== 704 | 705 | eslint-plugin-react-hooks@^4.6.0: 706 | version "4.6.0" 707 | resolved "https://registry.yarnpkg.com/eslint-plugin-react-hooks/-/eslint-plugin-react-hooks-4.6.0.tgz#4c3e697ad95b77e93f8646aaa1630c1ba607edd3" 708 | integrity sha512-oFc7Itz9Qxh2x4gNHStv3BqJq54ExXmfC+a1NjAta66IAN87Wu0R/QArgIS9qKzX3dXKPI9H5crl9QchNMY9+g== 709 | 710 | eslint-plugin-react-refresh@^0.4.3: 711 | version "0.4.3" 712 | resolved "https://registry.yarnpkg.com/eslint-plugin-react-refresh/-/eslint-plugin-react-refresh-0.4.3.tgz#59dae8c00a119f06ea16b1d3e6891df3775947c7" 713 | integrity sha512-Hh0wv8bUNY877+sI0BlCUlsS0TYYQqvzEwJsJJPM2WF4RnTStSnSR3zdJYa2nPOJgg3UghXi54lVyMSmpCalzA== 714 | 715 | eslint-scope@^7.2.2: 716 | version "7.2.2" 717 | resolved "https://registry.yarnpkg.com/eslint-scope/-/eslint-scope-7.2.2.tgz#deb4f92563390f32006894af62a22dba1c46423f" 718 | integrity sha512-dOt21O7lTMhDM+X9mB4GX+DZrZtCUJPL/wlcTqxyrx5IvO0IYtILdtrQGQp+8n5S0gwSVmOf9NQrjMOgfQZlIg== 719 | dependencies: 720 | esrecurse "^4.3.0" 721 | estraverse "^5.2.0" 722 | 723 | eslint-visitor-keys@^3.3.0, eslint-visitor-keys@^3.4.1, eslint-visitor-keys@^3.4.3: 724 | version "3.4.3" 725 | resolved "https://registry.yarnpkg.com/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz#0cd72fe8550e3c2eae156a96a4dddcd1c8ac5800" 726 | integrity sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag== 727 | 728 | eslint@^8.51.0: 729 | version "8.51.0" 730 | resolved "https://registry.yarnpkg.com/eslint/-/eslint-8.51.0.tgz#4a82dae60d209ac89a5cff1604fea978ba4950f3" 731 | integrity sha512-2WuxRZBrlwnXi+/vFSJyjMqrNjtJqiasMzehF0shoLaW7DzS3/9Yvrmq5JiT66+pNjiX4UBnLDiKHcWAr/OInA== 732 | dependencies: 733 | "@eslint-community/eslint-utils" "^4.2.0" 734 | "@eslint-community/regexpp" "^4.6.1" 735 | "@eslint/eslintrc" "^2.1.2" 736 | "@eslint/js" "8.51.0" 737 | "@humanwhocodes/config-array" "^0.11.11" 738 | "@humanwhocodes/module-importer" "^1.0.1" 739 | "@nodelib/fs.walk" "^1.2.8" 740 | ajv "^6.12.4" 741 | chalk "^4.0.0" 742 | cross-spawn "^7.0.2" 743 | debug "^4.3.2" 744 | doctrine "^3.0.0" 745 | escape-string-regexp "^4.0.0" 746 | eslint-scope "^7.2.2" 747 | eslint-visitor-keys "^3.4.3" 748 | espree "^9.6.1" 749 | esquery "^1.4.2" 750 | esutils "^2.0.2" 751 | fast-deep-equal "^3.1.3" 752 | file-entry-cache "^6.0.1" 753 | find-up "^5.0.0" 754 | glob-parent "^6.0.2" 755 | globals "^13.19.0" 756 | graphemer "^1.4.0" 757 | ignore "^5.2.0" 758 | imurmurhash "^0.1.4" 759 | is-glob "^4.0.0" 760 | is-path-inside "^3.0.3" 761 | js-yaml "^4.1.0" 762 | json-stable-stringify-without-jsonify "^1.0.1" 763 | levn "^0.4.1" 764 | lodash.merge "^4.6.2" 765 | minimatch "^3.1.2" 766 | natural-compare "^1.4.0" 767 | optionator "^0.9.3" 768 | strip-ansi "^6.0.1" 769 | text-table "^0.2.0" 770 | 771 | espree@^9.6.0, espree@^9.6.1: 772 | version "9.6.1" 773 | resolved "https://registry.yarnpkg.com/espree/-/espree-9.6.1.tgz#a2a17b8e434690a5432f2f8018ce71d331a48c6f" 774 | integrity sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ== 775 | dependencies: 776 | acorn "^8.9.0" 777 | acorn-jsx "^5.3.2" 778 | eslint-visitor-keys "^3.4.1" 779 | 780 | esquery@^1.4.2: 781 | version "1.5.0" 782 | resolved "https://registry.yarnpkg.com/esquery/-/esquery-1.5.0.tgz#6ce17738de8577694edd7361c57182ac8cb0db0b" 783 | integrity sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg== 784 | dependencies: 785 | estraverse "^5.1.0" 786 | 787 | esrecurse@^4.3.0: 788 | version "4.3.0" 789 | resolved "https://registry.yarnpkg.com/esrecurse/-/esrecurse-4.3.0.tgz#7ad7964d679abb28bee72cec63758b1c5d2c9921" 790 | integrity sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag== 791 | dependencies: 792 | estraverse "^5.2.0" 793 | 794 | estraverse@^5.1.0, estraverse@^5.2.0: 795 | version "5.3.0" 796 | resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-5.3.0.tgz#2eea5290702f26ab8fe5370370ff86c965d21123" 797 | integrity sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA== 798 | 799 | esutils@^2.0.2: 800 | version "2.0.3" 801 | resolved "https://registry.yarnpkg.com/esutils/-/esutils-2.0.3.tgz#74d2eb4de0b8da1293711910d50775b9b710ef64" 802 | integrity sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g== 803 | 804 | fast-deep-equal@^3.1.1, fast-deep-equal@^3.1.3: 805 | version "3.1.3" 806 | resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz#3a7d56b559d6cbc3eb512325244e619a65c6c525" 807 | integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== 808 | 809 | fast-glob@^3.2.9: 810 | version "3.3.1" 811 | resolved "https://registry.yarnpkg.com/fast-glob/-/fast-glob-3.3.1.tgz#784b4e897340f3dbbef17413b3f11acf03c874c4" 812 | integrity sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg== 813 | dependencies: 814 | "@nodelib/fs.stat" "^2.0.2" 815 | "@nodelib/fs.walk" "^1.2.3" 816 | glob-parent "^5.1.2" 817 | merge2 "^1.3.0" 818 | micromatch "^4.0.4" 819 | 820 | fast-json-stable-stringify@^2.0.0: 821 | version "2.1.0" 822 | resolved "https://registry.yarnpkg.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz#874bf69c6f404c2b5d99c481341399fd55892633" 823 | integrity sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw== 824 | 825 | fast-levenshtein@^2.0.6: 826 | version "2.0.6" 827 | resolved "https://registry.yarnpkg.com/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz#3d8a5c66883a16a30ca8643e851f19baa7797917" 828 | integrity sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw== 829 | 830 | fastq@^1.6.0: 831 | version "1.15.0" 832 | resolved "https://registry.yarnpkg.com/fastq/-/fastq-1.15.0.tgz#d04d07c6a2a68fe4599fea8d2e103a937fae6b3a" 833 | integrity sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw== 834 | dependencies: 835 | reusify "^1.0.4" 836 | 837 | file-entry-cache@^6.0.1: 838 | version "6.0.1" 839 | resolved "https://registry.yarnpkg.com/file-entry-cache/-/file-entry-cache-6.0.1.tgz#211b2dd9659cb0394b073e7323ac3c933d522027" 840 | integrity sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg== 841 | dependencies: 842 | flat-cache "^3.0.4" 843 | 844 | fill-range@^7.0.1: 845 | version "7.0.1" 846 | resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" 847 | integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== 848 | dependencies: 849 | to-regex-range "^5.0.1" 850 | 851 | find-up@^5.0.0: 852 | version "5.0.0" 853 | resolved "https://registry.yarnpkg.com/find-up/-/find-up-5.0.0.tgz#4c92819ecb7083561e4f4a240a86be5198f536fc" 854 | integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== 855 | dependencies: 856 | locate-path "^6.0.0" 857 | path-exists "^4.0.0" 858 | 859 | flat-cache@^3.0.4: 860 | version "3.1.1" 861 | resolved "https://registry.yarnpkg.com/flat-cache/-/flat-cache-3.1.1.tgz#a02a15fdec25a8f844ff7cc658f03dd99eb4609b" 862 | integrity sha512-/qM2b3LUIaIgviBQovTLvijfyOQXPtSRnRK26ksj2J7rzPIecePUIpJsZ4T02Qg+xiAEKIs5K8dsHEd+VaKa/Q== 863 | dependencies: 864 | flatted "^3.2.9" 865 | keyv "^4.5.3" 866 | rimraf "^3.0.2" 867 | 868 | flatted@^3.2.9: 869 | version "3.2.9" 870 | resolved "https://registry.yarnpkg.com/flatted/-/flatted-3.2.9.tgz#7eb4c67ca1ba34232ca9d2d93e9886e611ad7daf" 871 | integrity sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ== 872 | 873 | fs.realpath@^1.0.0: 874 | version "1.0.0" 875 | resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" 876 | integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw== 877 | 878 | fsevents@~2.3.2, fsevents@~2.3.3: 879 | version "2.3.3" 880 | resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.3.tgz#cac6407785d03675a2a5e1a5305c697b347d90d6" 881 | integrity sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw== 882 | 883 | gensync@^1.0.0-beta.2: 884 | version "1.0.0-beta.2" 885 | resolved "https://registry.yarnpkg.com/gensync/-/gensync-1.0.0-beta.2.tgz#32a6ee76c3d7f52d46b2b1ae5d93fea8580a25e0" 886 | integrity sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg== 887 | 888 | glob-parent@^5.1.2: 889 | version "5.1.2" 890 | resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.2.tgz#869832c58034fe68a4093c17dc15e8340d8401c4" 891 | integrity sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow== 892 | dependencies: 893 | is-glob "^4.0.1" 894 | 895 | glob-parent@^6.0.2: 896 | version "6.0.2" 897 | resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-6.0.2.tgz#6d237d99083950c79290f24c7642a3de9a28f9e3" 898 | integrity sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A== 899 | dependencies: 900 | is-glob "^4.0.3" 901 | 902 | glob@^7.1.3: 903 | version "7.2.3" 904 | resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.3.tgz#b8df0fb802bbfa8e89bd1d938b4e16578ed44f2b" 905 | integrity sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q== 906 | dependencies: 907 | fs.realpath "^1.0.0" 908 | inflight "^1.0.4" 909 | inherits "2" 910 | minimatch "^3.1.1" 911 | once "^1.3.0" 912 | path-is-absolute "^1.0.0" 913 | 914 | globals@^11.1.0: 915 | version "11.12.0" 916 | resolved "https://registry.yarnpkg.com/globals/-/globals-11.12.0.tgz#ab8795338868a0babd8525758018c2a7eb95c42e" 917 | integrity sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA== 918 | 919 | globals@^13.19.0: 920 | version "13.23.0" 921 | resolved "https://registry.yarnpkg.com/globals/-/globals-13.23.0.tgz#ef31673c926a0976e1f61dab4dca57e0c0a8af02" 922 | integrity sha512-XAmF0RjlrjY23MA51q3HltdlGxUpXPvg0GioKiD9X6HD28iMjo2dKC8Vqwm7lne4GNr78+RHTfliktR6ZH09wA== 923 | dependencies: 924 | type-fest "^0.20.2" 925 | 926 | globby@^11.1.0: 927 | version "11.1.0" 928 | resolved "https://registry.yarnpkg.com/globby/-/globby-11.1.0.tgz#bd4be98bb042f83d796f7e3811991fbe82a0d34b" 929 | integrity sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g== 930 | dependencies: 931 | array-union "^2.1.0" 932 | dir-glob "^3.0.1" 933 | fast-glob "^3.2.9" 934 | ignore "^5.2.0" 935 | merge2 "^1.4.1" 936 | slash "^3.0.0" 937 | 938 | graphemer@^1.4.0: 939 | version "1.4.0" 940 | resolved "https://registry.yarnpkg.com/graphemer/-/graphemer-1.4.0.tgz#fb2f1d55e0e3a1849aeffc90c4fa0dd53a0e66c6" 941 | integrity sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag== 942 | 943 | has-flag@^3.0.0: 944 | version "3.0.0" 945 | resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" 946 | integrity sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw== 947 | 948 | has-flag@^4.0.0: 949 | version "4.0.0" 950 | resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" 951 | integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== 952 | 953 | ignore@^5.2.0, ignore@^5.2.4: 954 | version "5.2.4" 955 | resolved "https://registry.yarnpkg.com/ignore/-/ignore-5.2.4.tgz#a291c0c6178ff1b960befe47fcdec301674a6324" 956 | integrity sha512-MAb38BcSbH0eHNBxn7ql2NH/kX33OkB3lZ1BNdh7ENeRChHTYsTvWrMubiIAMNS2llXEEgZ1MUOBtXChP3kaFQ== 957 | 958 | import-fresh@^3.2.1: 959 | version "3.3.0" 960 | resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-3.3.0.tgz#37162c25fcb9ebaa2e6e53d5b4d88ce17d9e0c2b" 961 | integrity sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw== 962 | dependencies: 963 | parent-module "^1.0.0" 964 | resolve-from "^4.0.0" 965 | 966 | imurmurhash@^0.1.4: 967 | version "0.1.4" 968 | resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea" 969 | integrity sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA== 970 | 971 | inflight@^1.0.4: 972 | version "1.0.6" 973 | resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" 974 | integrity sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA== 975 | dependencies: 976 | once "^1.3.0" 977 | wrappy "1" 978 | 979 | inherits@2: 980 | version "2.0.4" 981 | resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" 982 | integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== 983 | 984 | is-extglob@^2.1.1: 985 | version "2.1.1" 986 | resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" 987 | integrity sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ== 988 | 989 | is-glob@^4.0.0, is-glob@^4.0.1, is-glob@^4.0.3: 990 | version "4.0.3" 991 | resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.3.tgz#64f61e42cbbb2eec2071a9dac0b28ba1e65d5084" 992 | integrity sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg== 993 | dependencies: 994 | is-extglob "^2.1.1" 995 | 996 | is-number@^7.0.0: 997 | version "7.0.0" 998 | resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" 999 | integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== 1000 | 1001 | is-path-inside@^3.0.3: 1002 | version "3.0.3" 1003 | resolved "https://registry.yarnpkg.com/is-path-inside/-/is-path-inside-3.0.3.tgz#d231362e53a07ff2b0e0ea7fed049161ffd16283" 1004 | integrity sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ== 1005 | 1006 | isexe@^2.0.0: 1007 | version "2.0.0" 1008 | resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10" 1009 | integrity sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw== 1010 | 1011 | "js-tokens@^3.0.0 || ^4.0.0", js-tokens@^4.0.0: 1012 | version "4.0.0" 1013 | resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499" 1014 | integrity sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ== 1015 | 1016 | js-yaml@^4.1.0: 1017 | version "4.1.0" 1018 | resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-4.1.0.tgz#c1fb65f8f5017901cdd2c951864ba18458a10602" 1019 | integrity sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA== 1020 | dependencies: 1021 | argparse "^2.0.1" 1022 | 1023 | jsesc@^2.5.1: 1024 | version "2.5.2" 1025 | resolved "https://registry.yarnpkg.com/jsesc/-/jsesc-2.5.2.tgz#80564d2e483dacf6e8ef209650a67df3f0c283a4" 1026 | integrity sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA== 1027 | 1028 | json-buffer@3.0.1: 1029 | version "3.0.1" 1030 | resolved "https://registry.yarnpkg.com/json-buffer/-/json-buffer-3.0.1.tgz#9338802a30d3b6605fbe0613e094008ca8c05a13" 1031 | integrity sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ== 1032 | 1033 | json-schema-traverse@^0.4.1: 1034 | version "0.4.1" 1035 | resolved "https://registry.yarnpkg.com/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz#69f6a87d9513ab8bb8fe63bdb0979c448e684660" 1036 | integrity sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg== 1037 | 1038 | json-stable-stringify-without-jsonify@^1.0.1: 1039 | version "1.0.1" 1040 | resolved "https://registry.yarnpkg.com/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz#9db7b59496ad3f3cfef30a75142d2d930ad72651" 1041 | integrity sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw== 1042 | 1043 | json5@^2.2.3: 1044 | version "2.2.3" 1045 | resolved "https://registry.yarnpkg.com/json5/-/json5-2.2.3.tgz#78cd6f1a19bdc12b73db5ad0c61efd66c1e29283" 1046 | integrity sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg== 1047 | 1048 | keyv@^4.5.3: 1049 | version "4.5.4" 1050 | resolved "https://registry.yarnpkg.com/keyv/-/keyv-4.5.4.tgz#a879a99e29452f942439f2a405e3af8b31d4de93" 1051 | integrity sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw== 1052 | dependencies: 1053 | json-buffer "3.0.1" 1054 | 1055 | levn@^0.4.1: 1056 | version "0.4.1" 1057 | resolved "https://registry.yarnpkg.com/levn/-/levn-0.4.1.tgz#ae4562c007473b932a6200d403268dd2fffc6ade" 1058 | integrity sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ== 1059 | dependencies: 1060 | prelude-ls "^1.2.1" 1061 | type-check "~0.4.0" 1062 | 1063 | locate-path@^6.0.0: 1064 | version "6.0.0" 1065 | resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-6.0.0.tgz#55321eb309febbc59c4801d931a72452a681d286" 1066 | integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== 1067 | dependencies: 1068 | p-locate "^5.0.0" 1069 | 1070 | lodash.merge@^4.6.2: 1071 | version "4.6.2" 1072 | resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.2.tgz#558aa53b43b661e1925a0afdfa36a9a1085fe57a" 1073 | integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ== 1074 | 1075 | loose-envify@^1.1.0: 1076 | version "1.4.0" 1077 | resolved "https://registry.yarnpkg.com/loose-envify/-/loose-envify-1.4.0.tgz#71ee51fa7be4caec1a63839f7e682d8132d30caf" 1078 | integrity sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q== 1079 | dependencies: 1080 | js-tokens "^3.0.0 || ^4.0.0" 1081 | 1082 | lru-cache@^5.1.1: 1083 | version "5.1.1" 1084 | resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-5.1.1.tgz#1da27e6710271947695daf6848e847f01d84b920" 1085 | integrity sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w== 1086 | dependencies: 1087 | yallist "^3.0.2" 1088 | 1089 | lru-cache@^6.0.0: 1090 | version "6.0.0" 1091 | resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" 1092 | integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== 1093 | dependencies: 1094 | yallist "^4.0.0" 1095 | 1096 | merge2@^1.3.0, merge2@^1.4.1: 1097 | version "1.4.1" 1098 | resolved "https://registry.yarnpkg.com/merge2/-/merge2-1.4.1.tgz#4368892f885e907455a6fd7dc55c0c9d404990ae" 1099 | integrity sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg== 1100 | 1101 | micromatch@^4.0.4: 1102 | version "4.0.5" 1103 | resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.5.tgz#bc8999a7cbbf77cdc89f132f6e467051b49090c6" 1104 | integrity sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA== 1105 | dependencies: 1106 | braces "^3.0.2" 1107 | picomatch "^2.3.1" 1108 | 1109 | minimatch@^3.0.5, minimatch@^3.1.1, minimatch@^3.1.2: 1110 | version "3.1.2" 1111 | resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b" 1112 | integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== 1113 | dependencies: 1114 | brace-expansion "^1.1.7" 1115 | 1116 | moo@^0.5.0, moo@^0.5.1: 1117 | version "0.5.2" 1118 | resolved "https://registry.yarnpkg.com/moo/-/moo-0.5.2.tgz#f9fe82473bc7c184b0d32e2215d3f6e67278733c" 1119 | integrity sha512-iSAJLHYKnX41mKcJKjqvnAN9sf0LMDTXDEvFv+ffuRR9a1MIuXLjMNL6EsnDHSkKLTWNqQQ5uo61P4EbU4NU+Q== 1120 | 1121 | ms@2.1.2: 1122 | version "2.1.2" 1123 | resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009" 1124 | integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== 1125 | 1126 | nanoid@^3.3.6: 1127 | version "3.3.6" 1128 | resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.6.tgz#443380c856d6e9f9824267d960b4236ad583ea4c" 1129 | integrity sha512-BGcqMMJuToF7i1rt+2PWSNVnWIkGCU78jBG3RxO/bZlnZPK2Cmi2QaffxGO/2RvWi9sL+FAiRiXMgsyxQ1DIDA== 1130 | 1131 | natural-compare@^1.4.0: 1132 | version "1.4.0" 1133 | resolved "https://registry.yarnpkg.com/natural-compare/-/natural-compare-1.4.0.tgz#4abebfeed7541f2c27acfb29bdbbd15c8d5ba4f7" 1134 | integrity sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw== 1135 | 1136 | nearley@^2.19.5: 1137 | version "2.20.1" 1138 | resolved "https://registry.yarnpkg.com/nearley/-/nearley-2.20.1.tgz#246cd33eff0d012faf197ff6774d7ac78acdd474" 1139 | integrity sha512-+Mc8UaAebFzgV+KpI5n7DasuuQCHA89dmwm7JXw3TV43ukfNQ9DnBH3Mdb2g/I4Fdxc26pwimBWvjIw0UAILSQ== 1140 | dependencies: 1141 | commander "^2.19.0" 1142 | moo "^0.5.0" 1143 | railroad-diagrams "^1.0.0" 1144 | randexp "0.4.6" 1145 | 1146 | node-releases@^2.0.13: 1147 | version "2.0.13" 1148 | resolved "https://registry.yarnpkg.com/node-releases/-/node-releases-2.0.13.tgz#d5ed1627c23e3461e819b02e57b75e4899b1c81d" 1149 | integrity sha512-uYr7J37ae/ORWdZeQ1xxMJe3NtdmqMC/JZK+geofDrkLUApKRHPd18/TxtBOJ4A0/+uUIliorNrfYV6s1b02eQ== 1150 | 1151 | observable-hooks@^4.2.3: 1152 | version "4.2.3" 1153 | resolved "https://registry.yarnpkg.com/observable-hooks/-/observable-hooks-4.2.3.tgz#69e3353caafd7887ad9030bd440b053304e8d2d1" 1154 | integrity sha512-d6fYTIU+9sg1V+CT0GhgoE/ntjIqcy9DGaYGE6ELGVP4ojaWIEsaLvL/05hLOM+AL7aySN4DCTLvj6dDF9T8XA== 1155 | 1156 | once@^1.3.0: 1157 | version "1.4.0" 1158 | resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" 1159 | integrity sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w== 1160 | dependencies: 1161 | wrappy "1" 1162 | 1163 | optionator@^0.9.3: 1164 | version "0.9.3" 1165 | resolved "https://registry.yarnpkg.com/optionator/-/optionator-0.9.3.tgz#007397d44ed1872fdc6ed31360190f81814e2c64" 1166 | integrity sha512-JjCoypp+jKn1ttEFExxhetCKeJt9zhAgAve5FXHixTvFDW/5aEktX9bufBKLRRMdU7bNtpLfcGu94B3cdEJgjg== 1167 | dependencies: 1168 | "@aashutoshrathi/word-wrap" "^1.2.3" 1169 | deep-is "^0.1.3" 1170 | fast-levenshtein "^2.0.6" 1171 | levn "^0.4.1" 1172 | prelude-ls "^1.2.1" 1173 | type-check "^0.4.0" 1174 | 1175 | p-limit@^3.0.2: 1176 | version "3.1.0" 1177 | resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.1.0.tgz#e1daccbe78d0d1388ca18c64fea38e3e57e3706b" 1178 | integrity sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ== 1179 | dependencies: 1180 | yocto-queue "^0.1.0" 1181 | 1182 | p-locate@^5.0.0: 1183 | version "5.0.0" 1184 | resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-5.0.0.tgz#83c8315c6785005e3bd021839411c9e110e6d834" 1185 | integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== 1186 | dependencies: 1187 | p-limit "^3.0.2" 1188 | 1189 | parent-module@^1.0.0: 1190 | version "1.0.1" 1191 | resolved "https://registry.yarnpkg.com/parent-module/-/parent-module-1.0.1.tgz#691d2709e78c79fae3a156622452d00762caaaa2" 1192 | integrity sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g== 1193 | dependencies: 1194 | callsites "^3.0.0" 1195 | 1196 | path-exists@^4.0.0: 1197 | version "4.0.0" 1198 | resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-4.0.0.tgz#513bdbe2d3b95d7762e8c1137efa195c6c61b5b3" 1199 | integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== 1200 | 1201 | path-is-absolute@^1.0.0: 1202 | version "1.0.1" 1203 | resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" 1204 | integrity sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg== 1205 | 1206 | path-key@^3.1.0: 1207 | version "3.1.1" 1208 | resolved "https://registry.yarnpkg.com/path-key/-/path-key-3.1.1.tgz#581f6ade658cbba65a0d3380de7753295054f375" 1209 | integrity sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q== 1210 | 1211 | path-type@^4.0.0: 1212 | version "4.0.0" 1213 | resolved "https://registry.yarnpkg.com/path-type/-/path-type-4.0.0.tgz#84ed01c0a7ba380afe09d90a8c180dcd9d03043b" 1214 | integrity sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw== 1215 | 1216 | pgsql-ast-parser@^11.1.0: 1217 | version "11.1.0" 1218 | resolved "https://registry.yarnpkg.com/pgsql-ast-parser/-/pgsql-ast-parser-11.1.0.tgz#b3015171fd844e93f37368a50fdb3c06ab9e5b01" 1219 | integrity sha512-c0XnjHzUyg2Z/3iB2Akk6+jDtsza4Jqw4bC5SSt9pQ3b+K4aQC75gJQDvsNYvFqQNaPHLCUunDLPc5SZsQQLIA== 1220 | dependencies: 1221 | moo "^0.5.1" 1222 | nearley "^2.19.5" 1223 | 1224 | picocolors@^1.0.0: 1225 | version "1.0.0" 1226 | resolved "https://registry.yarnpkg.com/picocolors/-/picocolors-1.0.0.tgz#cb5bdc74ff3f51892236eaf79d68bc44564ab81c" 1227 | integrity sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ== 1228 | 1229 | picomatch@^2.3.1: 1230 | version "2.3.1" 1231 | resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.3.1.tgz#3ba3833733646d9d3e4995946c1365a67fb07a42" 1232 | integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== 1233 | 1234 | postcss@^8.4.31: 1235 | version "8.4.31" 1236 | resolved "https://registry.yarnpkg.com/postcss/-/postcss-8.4.31.tgz#92b451050a9f914da6755af352bdc0192508656d" 1237 | integrity sha512-PS08Iboia9mts/2ygV3eLpY5ghnUcfLV/EXTOW1E2qYxJKGGBUtNjN76FYHnMs36RmARn41bC0AZmn+rR0OVpQ== 1238 | dependencies: 1239 | nanoid "^3.3.6" 1240 | picocolors "^1.0.0" 1241 | source-map-js "^1.0.2" 1242 | 1243 | prelude-ls@^1.2.1: 1244 | version "1.2.1" 1245 | resolved "https://registry.yarnpkg.com/prelude-ls/-/prelude-ls-1.2.1.tgz#debc6489d7a6e6b0e7611888cec880337d316396" 1246 | integrity sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g== 1247 | 1248 | punycode@^2.1.0: 1249 | version "2.3.0" 1250 | resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.3.0.tgz#f67fa67c94da8f4d0cfff981aee4118064199b8f" 1251 | integrity sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA== 1252 | 1253 | queue-microtask@^1.2.2: 1254 | version "1.2.3" 1255 | resolved "https://registry.yarnpkg.com/queue-microtask/-/queue-microtask-1.2.3.tgz#4929228bbc724dfac43e0efb058caf7b6cfb6243" 1256 | integrity sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A== 1257 | 1258 | railroad-diagrams@^1.0.0: 1259 | version "1.0.0" 1260 | resolved "https://registry.yarnpkg.com/railroad-diagrams/-/railroad-diagrams-1.0.0.tgz#eb7e6267548ddedfb899c1b90e57374559cddb7e" 1261 | integrity sha512-cz93DjNeLY0idrCNOH6PviZGRN9GJhsdm9hpn1YCS879fj4W+x5IFJhhkRZcwVgMmFF7R82UA/7Oh+R8lLZg6A== 1262 | 1263 | randexp@0.4.6: 1264 | version "0.4.6" 1265 | resolved "https://registry.yarnpkg.com/randexp/-/randexp-0.4.6.tgz#e986ad5e5e31dae13ddd6f7b3019aa7c87f60ca3" 1266 | integrity sha512-80WNmd9DA0tmZrw9qQa62GPPWfuXJknrmVmLcxvq4uZBdYqb1wYoKTmnlGUchvVWe0XiLupYkBoXVOxz3C8DYQ== 1267 | dependencies: 1268 | discontinuous-range "1.0.0" 1269 | ret "~0.1.10" 1270 | 1271 | react-dom@^18.2.0: 1272 | version "18.2.0" 1273 | resolved "https://registry.yarnpkg.com/react-dom/-/react-dom-18.2.0.tgz#22aaf38708db2674ed9ada224ca4aa708d821e3d" 1274 | integrity sha512-6IMTriUmvsjHUjNtEDudZfuDQUoWXVxKHhlEGSk81n4YFS+r/Kl99wXiwlVXtPBtJenozv2P+hxDsw9eA7Xo6g== 1275 | dependencies: 1276 | loose-envify "^1.1.0" 1277 | scheduler "^0.23.0" 1278 | 1279 | react-refresh@^0.14.0: 1280 | version "0.14.0" 1281 | resolved "https://registry.yarnpkg.com/react-refresh/-/react-refresh-0.14.0.tgz#4e02825378a5f227079554d4284889354e5f553e" 1282 | integrity sha512-wViHqhAd8OHeLS/IRMJjTSDHF3U9eWi62F/MledQGPdJGDhodXJ9PBLNGr6WWL7qlH12Mt3TyTpbS+hGXMjCzQ== 1283 | 1284 | react@^18.2.0: 1285 | version "18.2.0" 1286 | resolved "https://registry.yarnpkg.com/react/-/react-18.2.0.tgz#555bd98592883255fa00de14f1151a917b5d77d5" 1287 | integrity sha512-/3IjMdb2L9QbBdWiW5e3P2/npwMBaU9mHCSCUzNln0ZCYbcfTsGbTJrU/kGemdH2IWmB2ioZ+zkxtmq6g09fGQ== 1288 | dependencies: 1289 | loose-envify "^1.1.0" 1290 | 1291 | resolve-from@^4.0.0: 1292 | version "4.0.0" 1293 | resolved "https://registry.yarnpkg.com/resolve-from/-/resolve-from-4.0.0.tgz#4abcd852ad32dd7baabfe9b40e00a36db5f392e6" 1294 | integrity sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g== 1295 | 1296 | ret@~0.1.10: 1297 | version "0.1.15" 1298 | resolved "https://registry.yarnpkg.com/ret/-/ret-0.1.15.tgz#b8a4825d5bdb1fc3f6f53c2bc33f81388681c7bc" 1299 | integrity sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg== 1300 | 1301 | reusify@^1.0.4: 1302 | version "1.0.4" 1303 | resolved "https://registry.yarnpkg.com/reusify/-/reusify-1.0.4.tgz#90da382b1e126efc02146e90845a88db12925d76" 1304 | integrity sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw== 1305 | 1306 | rimraf@^3.0.2: 1307 | version "3.0.2" 1308 | resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-3.0.2.tgz#f1a5402ba6220ad52cc1282bac1ae3aa49fd061a" 1309 | integrity sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA== 1310 | dependencies: 1311 | glob "^7.1.3" 1312 | 1313 | rollup@^4.1.4: 1314 | version "4.1.4" 1315 | resolved "https://registry.yarnpkg.com/rollup/-/rollup-4.1.4.tgz#cf0ab00d9183a3d11fcc5d630270463b13831221" 1316 | integrity sha512-U8Yk1lQRKqCkDBip/pMYT+IKaN7b7UesK3fLSTuHBoBJacCE+oBqo/dfG/gkUdQNNB2OBmRP98cn2C2bkYZkyw== 1317 | optionalDependencies: 1318 | fsevents "~2.3.2" 1319 | 1320 | run-parallel@^1.1.9: 1321 | version "1.2.0" 1322 | resolved "https://registry.yarnpkg.com/run-parallel/-/run-parallel-1.2.0.tgz#66d1368da7bdf921eb9d95bd1a9229e7f21a43ee" 1323 | integrity sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA== 1324 | dependencies: 1325 | queue-microtask "^1.2.2" 1326 | 1327 | rxjs@^7.8.1: 1328 | version "7.8.1" 1329 | resolved "https://registry.yarnpkg.com/rxjs/-/rxjs-7.8.1.tgz#6f6f3d99ea8044291efd92e7c7fcf562c4057543" 1330 | integrity sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg== 1331 | dependencies: 1332 | tslib "^2.1.0" 1333 | 1334 | scheduler@^0.23.0: 1335 | version "0.23.0" 1336 | resolved "https://registry.yarnpkg.com/scheduler/-/scheduler-0.23.0.tgz#ba8041afc3d30eb206a487b6b384002e4e61fdfe" 1337 | integrity sha512-CtuThmgHNg7zIZWAXi3AsyIzA3n4xx7aNyjwC2VJldO2LMVDhFK+63xGqq6CsJH4rTAt6/M+N4GhZiDYPx9eUw== 1338 | dependencies: 1339 | loose-envify "^1.1.0" 1340 | 1341 | semver@^6.3.1: 1342 | version "6.3.1" 1343 | resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.1.tgz#556d2ef8689146e46dcea4bfdd095f3434dffcb4" 1344 | integrity sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA== 1345 | 1346 | semver@^7.5.4: 1347 | version "7.5.4" 1348 | resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.4.tgz#483986ec4ed38e1c6c48c34894a9182dbff68a6e" 1349 | integrity sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA== 1350 | dependencies: 1351 | lru-cache "^6.0.0" 1352 | 1353 | shebang-command@^2.0.0: 1354 | version "2.0.0" 1355 | resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-2.0.0.tgz#ccd0af4f8835fbdc265b82461aaf0c36663f34ea" 1356 | integrity sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA== 1357 | dependencies: 1358 | shebang-regex "^3.0.0" 1359 | 1360 | shebang-regex@^3.0.0: 1361 | version "3.0.0" 1362 | resolved "https://registry.yarnpkg.com/shebang-regex/-/shebang-regex-3.0.0.tgz#ae16f1644d873ecad843b0307b143362d4c42172" 1363 | integrity sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A== 1364 | 1365 | slash@^3.0.0: 1366 | version "3.0.0" 1367 | resolved "https://registry.yarnpkg.com/slash/-/slash-3.0.0.tgz#6539be870c165adbd5240220dbe361f1bc4d4634" 1368 | integrity sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q== 1369 | 1370 | source-map-js@^1.0.2: 1371 | version "1.0.2" 1372 | resolved "https://registry.yarnpkg.com/source-map-js/-/source-map-js-1.0.2.tgz#adbc361d9c62df380125e7f161f71c826f1e490c" 1373 | integrity sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw== 1374 | 1375 | sql-template-tag@^5.1.0: 1376 | version "5.1.0" 1377 | resolved "https://registry.yarnpkg.com/sql-template-tag/-/sql-template-tag-5.1.0.tgz#15a7e153706113e06ee1364d2ca82af92fc0c008" 1378 | integrity sha512-+0uwu2fn1LJ3KzZYUrTSViBuHEkyjpAGMnJ3X7RYRFDNIMft99lLAe6kkybPPkV+8GgDrifxUmj+C4j1hpYAgQ== 1379 | 1380 | strip-ansi@^6.0.1: 1381 | version "6.0.1" 1382 | resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" 1383 | integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== 1384 | dependencies: 1385 | ansi-regex "^5.0.1" 1386 | 1387 | strip-json-comments@^3.1.1: 1388 | version "3.1.1" 1389 | resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" 1390 | integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== 1391 | 1392 | supports-color@^5.3.0: 1393 | version "5.5.0" 1394 | resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" 1395 | integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== 1396 | dependencies: 1397 | has-flag "^3.0.0" 1398 | 1399 | supports-color@^7.1.0: 1400 | version "7.2.0" 1401 | resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.2.0.tgz#1b7dcdcb32b8138801b3e478ba6a51caa89648da" 1402 | integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== 1403 | dependencies: 1404 | has-flag "^4.0.0" 1405 | 1406 | text-table@^0.2.0: 1407 | version "0.2.0" 1408 | resolved "https://registry.yarnpkg.com/text-table/-/text-table-0.2.0.tgz#7f5ee823ae805207c00af2df4a84ec3fcfa570b4" 1409 | integrity sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw== 1410 | 1411 | to-fast-properties@^2.0.0: 1412 | version "2.0.0" 1413 | resolved "https://registry.yarnpkg.com/to-fast-properties/-/to-fast-properties-2.0.0.tgz#dc5e698cbd079265bc73e0377681a4e4e83f616e" 1414 | integrity sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog== 1415 | 1416 | to-regex-range@^5.0.1: 1417 | version "5.0.1" 1418 | resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" 1419 | integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== 1420 | dependencies: 1421 | is-number "^7.0.0" 1422 | 1423 | ts-api-utils@^1.0.1: 1424 | version "1.0.3" 1425 | resolved "https://registry.yarnpkg.com/ts-api-utils/-/ts-api-utils-1.0.3.tgz#f12c1c781d04427313dbac808f453f050e54a331" 1426 | integrity sha512-wNMeqtMz5NtwpT/UZGY5alT+VoKdSsOOP/kqHFcUW1P/VRhH2wJ48+DN2WwUliNbQ976ETwDL0Ifd2VVvgonvg== 1427 | 1428 | tslib@^2.1.0: 1429 | version "2.6.2" 1430 | resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.6.2.tgz#703ac29425e7b37cd6fd456e92404d46d1f3e4ae" 1431 | integrity sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q== 1432 | 1433 | type-check@^0.4.0, type-check@~0.4.0: 1434 | version "0.4.0" 1435 | resolved "https://registry.yarnpkg.com/type-check/-/type-check-0.4.0.tgz#07b8203bfa7056c0657050e3ccd2c37730bab8f1" 1436 | integrity sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew== 1437 | dependencies: 1438 | prelude-ls "^1.2.1" 1439 | 1440 | type-fest@^0.20.2: 1441 | version "0.20.2" 1442 | resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.20.2.tgz#1bf207f4b28f91583666cb5fbd327887301cd5f4" 1443 | integrity sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ== 1444 | 1445 | typescript@^5.2.2: 1446 | version "5.2.2" 1447 | resolved "https://registry.yarnpkg.com/typescript/-/typescript-5.2.2.tgz#5ebb5e5a5b75f085f22bc3f8460fba308310fa78" 1448 | integrity sha512-mI4WrpHsbCIcwT9cF4FZvr80QUeKvsUsUvKDoR+X/7XHQH98xYD8YHZg7ANtz2GtZt/CBq2QJ0thkGJMHfqc1w== 1449 | 1450 | update-browserslist-db@^1.0.13: 1451 | version "1.0.13" 1452 | resolved "https://registry.yarnpkg.com/update-browserslist-db/-/update-browserslist-db-1.0.13.tgz#3c5e4f5c083661bd38ef64b6328c26ed6c8248c4" 1453 | integrity sha512-xebP81SNcPuNpPP3uzeW1NYXxI3rxyJzF3pD6sH4jE7o/IX+WtSpwnVU+qIsDPyk0d3hmFQ7mjqc6AtV604hbg== 1454 | dependencies: 1455 | escalade "^3.1.1" 1456 | picocolors "^1.0.0" 1457 | 1458 | uri-js@^4.2.2: 1459 | version "4.4.1" 1460 | resolved "https://registry.yarnpkg.com/uri-js/-/uri-js-4.4.1.tgz#9b1a52595225859e55f669d928f88c6c57f2a77e" 1461 | integrity sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg== 1462 | dependencies: 1463 | punycode "^2.1.0" 1464 | 1465 | vite@^5.0.0-beta.7: 1466 | version "5.0.0-beta.10" 1467 | resolved "https://registry.yarnpkg.com/vite/-/vite-5.0.0-beta.10.tgz#b40c9c0c3580980e135da0e36666870b8d374b67" 1468 | integrity sha512-8aqMPLJnbQf8IFG+o/EMihZ+1RtTD6VoP2OJgUZfmaylR+hNyO0DBhWliWmrHXjOarDDuT1kJjowwS+XRWZ+EQ== 1469 | dependencies: 1470 | esbuild "^0.19.3" 1471 | postcss "^8.4.31" 1472 | rollup "^4.1.4" 1473 | optionalDependencies: 1474 | fsevents "~2.3.3" 1475 | 1476 | which@^2.0.1: 1477 | version "2.0.2" 1478 | resolved "https://registry.yarnpkg.com/which/-/which-2.0.2.tgz#7c6a8dd0a636a0327e10b59c9286eee93f3f51b1" 1479 | integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA== 1480 | dependencies: 1481 | isexe "^2.0.0" 1482 | 1483 | wrappy@1: 1484 | version "1.0.2" 1485 | resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" 1486 | integrity sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ== 1487 | 1488 | yallist@^3.0.2: 1489 | version "3.1.1" 1490 | resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.1.1.tgz#dbb7daf9bfd8bac9ab45ebf602b8cbad0d5d08fd" 1491 | integrity sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g== 1492 | 1493 | yallist@^4.0.0: 1494 | version "4.0.0" 1495 | resolved "https://registry.yarnpkg.com/yallist/-/yallist-4.0.0.tgz#9bb92790d9c0effec63be73519e11a35019a3a72" 1496 | integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== 1497 | 1498 | yocto-queue@^0.1.0: 1499 | version "0.1.0" 1500 | resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" 1501 | integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== 1502 | --------------------------------------------------------------------------------