1
0

run npm install to generate a package lock

This commit is contained in:
sashinexists
2024-12-07 13:18:31 +11:00
parent e7d08a91b5
commit 23437d228e
2501 changed files with 290663 additions and 0 deletions

10
node_modules/stubborn-fs/.editorconfig generated vendored Normal file
View File

@@ -0,0 +1,10 @@
root = true
[*]
charset = utf-8
end_of_line = lf
indent_size = 2
indent_style = space
insert_final_newline = true
trim_trailing_whitespace = true

3
node_modules/stubborn-fs/dist/attemptify.d.ts generated vendored Normal file
View File

@@ -0,0 +1,3 @@
declare const attemptifyAsync: <FN extends Function>(fn: FN, onError: (error: unknown) => undefined) => FN;
declare const attemptifySync: <FN extends Function>(fn: FN, onError: (error: unknown) => undefined) => FN;
export { attemptifyAsync, attemptifySync };

19
node_modules/stubborn-fs/dist/attemptify.js generated vendored Normal file
View File

@@ -0,0 +1,19 @@
/* MAIN */
//FIXME: The return type of these functions is wrong, it doesn't account for returning "undefined", but a correct type cannot be written because generics cannot be extended properly, it seems
const attemptifyAsync = (fn, onError) => {
return function attemptified(...args) {
return fn.apply(undefined, args).catch(onError);
};
};
const attemptifySync = (fn, onError) => {
return function attemptified(...args) {
try {
return fn.apply(undefined, args);
}
catch (error) {
return onError(error);
}
};
};
/* EXPORT */
export { attemptifyAsync, attemptifySync };

4
node_modules/stubborn-fs/dist/constants.d.ts generated vendored Normal file
View File

@@ -0,0 +1,4 @@
declare const IS_USER_ROOT: boolean;
declare const LIMIT_FILES_DESCRIPTORS = 10000;
declare const NOOP: () => undefined;
export { IS_USER_ROOT, LIMIT_FILES_DESCRIPTORS, NOOP };

8
node_modules/stubborn-fs/dist/constants.js generated vendored Normal file
View File

@@ -0,0 +1,8 @@
/* IMPORT */
import process from 'node:process';
/* MAIN */
const IS_USER_ROOT = process.getuid ? !process.getuid() : false;
const LIMIT_FILES_DESCRIPTORS = 10000; //TODO: Fetch the real limit from the filesystem, somehow
const NOOP = () => undefined;
/* EXPORT */
export { IS_USER_ROOT, LIMIT_FILES_DESCRIPTORS, NOOP };

8
node_modules/stubborn-fs/dist/handlers.d.ts generated vendored Normal file
View File

@@ -0,0 +1,8 @@
/// <reference types="node" />
declare const Handlers: {
isChangeErrorOk: (error: unknown) => boolean;
isNodeError: (error: unknown) => error is NodeJS.ErrnoException;
isRetriableError: (error: unknown) => boolean;
onChangeError: (error: unknown) => undefined;
};
export default Handlers;

36
node_modules/stubborn-fs/dist/handlers.js generated vendored Normal file
View File

@@ -0,0 +1,36 @@
/* IMPORT */
import { IS_USER_ROOT } from './constants.js';
/* MAIN */
const Handlers = {
/* API */
isChangeErrorOk: (error) => {
if (!Handlers.isNodeError(error))
return false;
const { code } = error;
if (code === 'ENOSYS')
return true;
if (!IS_USER_ROOT && (code === 'EINVAL' || code === 'EPERM'))
return true;
return false;
},
isNodeError: (error) => {
return (error instanceof Error);
},
isRetriableError: (error) => {
if (!Handlers.isNodeError(error))
return false;
const { code } = error;
if (code === 'EMFILE' || code === 'ENFILE' || code === 'EAGAIN' || code === 'EBUSY' || code === 'EACCESS' || code === 'EACCES' || code === 'EACCS' || code === 'EPERM')
return true;
return false;
},
onChangeError: (error) => {
if (!Handlers.isNodeError(error))
throw error;
if (Handlers.isChangeErrorOk(error))
return;
throw error;
}
};
/* EXPORT */
export default Handlers;

42
node_modules/stubborn-fs/dist/index.d.ts generated vendored Normal file
View File

@@ -0,0 +1,42 @@
/// <reference types="node" />
import fs from 'node:fs';
declare const FS: {
attempt: {
chmod: typeof fs.chmod.__promisify__;
chown: typeof fs.chown.__promisify__;
close: typeof fs.close.__promisify__;
fsync: typeof fs.fsync.__promisify__;
mkdir: typeof fs.mkdir.__promisify__;
realpath: typeof fs.realpath.__promisify__;
stat: typeof fs.stat.__promisify__;
unlink: typeof fs.unlink.__promisify__;
chmodSync: typeof fs.chmodSync;
chownSync: typeof fs.chownSync;
closeSync: typeof fs.closeSync;
existsSync: typeof fs.existsSync;
fsyncSync: typeof fs.fsync;
mkdirSync: typeof fs.mkdirSync;
realpathSync: typeof fs.realpathSync;
statSync: fs.StatSyncFn;
unlinkSync: typeof fs.unlinkSync;
};
retry: {
close: (timeout: number) => typeof fs.close.__promisify__;
fsync: (timeout: number) => typeof fs.fsync.__promisify__;
open: (timeout: number) => typeof fs.open.__promisify__;
readFile: (timeout: number) => typeof fs.readFile.__promisify__;
rename: (timeout: number) => typeof fs.rename.__promisify__;
stat: (timeout: number) => typeof fs.stat.__promisify__;
write: (timeout: number) => typeof fs.write.__promisify__;
writeFile: (timeout: number) => typeof fs.writeFile.__promisify__;
closeSync: (timeout: number) => typeof fs.closeSync;
fsyncSync: (timeout: number) => typeof fs.fsyncSync;
openSync: (timeout: number) => typeof fs.openSync;
readFileSync: (timeout: number) => typeof fs.readFileSync;
renameSync: (timeout: number) => typeof fs.renameSync;
statSync: (timeout: number) => fs.StatSyncFn;
writeSync: (timeout: number) => typeof fs.writeSync;
writeFileSync: (timeout: number) => typeof fs.writeFileSync;
};
};
export default FS;

53
node_modules/stubborn-fs/dist/index.js generated vendored Normal file
View File

@@ -0,0 +1,53 @@
/* IMPORT */
import fs from 'node:fs';
import { promisify } from 'node:util';
import { attemptifyAsync, attemptifySync } from './attemptify.js';
import { NOOP } from './constants.js';
import Handlers from './handlers.js';
import { retryifyAsync, retryifySync } from './retryify.js';
/* MAIN */
const FS = {
attempt: {
/* ASYNC */
chmod: attemptifyAsync(promisify(fs.chmod), Handlers.onChangeError),
chown: attemptifyAsync(promisify(fs.chown), Handlers.onChangeError),
close: attemptifyAsync(promisify(fs.close), NOOP),
fsync: attemptifyAsync(promisify(fs.fsync), NOOP),
mkdir: attemptifyAsync(promisify(fs.mkdir), NOOP),
realpath: attemptifyAsync(promisify(fs.realpath), NOOP),
stat: attemptifyAsync(promisify(fs.stat), NOOP),
unlink: attemptifyAsync(promisify(fs.unlink), NOOP),
/* SYNC */
chmodSync: attemptifySync(fs.chmodSync, Handlers.onChangeError),
chownSync: attemptifySync(fs.chownSync, Handlers.onChangeError),
closeSync: attemptifySync(fs.closeSync, NOOP),
existsSync: attemptifySync(fs.existsSync, NOOP),
fsyncSync: attemptifySync(fs.fsync, NOOP),
mkdirSync: attemptifySync(fs.mkdirSync, NOOP),
realpathSync: attemptifySync(fs.realpathSync, NOOP),
statSync: attemptifySync(fs.statSync, NOOP),
unlinkSync: attemptifySync(fs.unlinkSync, NOOP)
},
retry: {
/* ASYNC */
close: retryifyAsync(promisify(fs.close), Handlers.isRetriableError),
fsync: retryifyAsync(promisify(fs.fsync), Handlers.isRetriableError),
open: retryifyAsync(promisify(fs.open), Handlers.isRetriableError),
readFile: retryifyAsync(promisify(fs.readFile), Handlers.isRetriableError),
rename: retryifyAsync(promisify(fs.rename), Handlers.isRetriableError),
stat: retryifyAsync(promisify(fs.stat), Handlers.isRetriableError),
write: retryifyAsync(promisify(fs.write), Handlers.isRetriableError),
writeFile: retryifyAsync(promisify(fs.writeFile), Handlers.isRetriableError),
/* SYNC */
closeSync: retryifySync(fs.closeSync, Handlers.isRetriableError),
fsyncSync: retryifySync(fs.fsyncSync, Handlers.isRetriableError),
openSync: retryifySync(fs.openSync, Handlers.isRetriableError),
readFileSync: retryifySync(fs.readFileSync, Handlers.isRetriableError),
renameSync: retryifySync(fs.renameSync, Handlers.isRetriableError),
statSync: retryifySync(fs.statSync, Handlers.isRetriableError),
writeSync: retryifySync(fs.writeSync, Handlers.isRetriableError),
writeFileSync: retryifySync(fs.writeFileSync, Handlers.isRetriableError)
}
};
/* EXPORT */
export default FS;

3
node_modules/stubborn-fs/dist/retryify.d.ts generated vendored Normal file
View File

@@ -0,0 +1,3 @@
declare const retryifyAsync: <FN extends Function>(fn: FN, isRetriableError: (error: unknown) => boolean | void) => (timeout: number) => FN;
declare const retryifySync: <FN extends Function>(fn: FN, isRetriableError: (error: unknown) => boolean | void) => (timeout: number) => FN;
export { retryifyAsync, retryifySync };

46
node_modules/stubborn-fs/dist/retryify.js generated vendored Normal file
View File

@@ -0,0 +1,46 @@
/* IMPORT */
import RetryfyQueue from './retryify_queue.js';
/* MAIN */
//FIXME: There are a boatload of anys here, but apparently generics cannot be extended properly, so...
const retryifyAsync = (fn, isRetriableError) => {
return function retrified(timestamp) {
return function attempt(...args) {
return RetryfyQueue.schedule().then(cleanup => {
const onResolve = (result) => {
cleanup();
return result;
};
const onReject = (error) => {
cleanup();
if (Date.now() >= timestamp)
throw error;
if (isRetriableError(error)) {
const delay = Math.round(100 * Math.random());
const delayPromise = new Promise(resolve => setTimeout(resolve, delay));
return delayPromise.then(() => attempt.apply(undefined, args));
}
throw error;
};
return fn.apply(undefined, args).then(onResolve, onReject);
});
};
};
};
const retryifySync = (fn, isRetriableError) => {
return function retrified(timestamp) {
return function attempt(...args) {
try {
return fn.apply(undefined, args);
}
catch (error) {
if (Date.now() > timestamp)
throw error;
if (isRetriableError(error))
return attempt.apply(undefined, args);
throw error;
}
};
};
};
/* EXPORT */
export { retryifyAsync, retryifySync };

15
node_modules/stubborn-fs/dist/retryify_queue.d.ts generated vendored Normal file
View File

@@ -0,0 +1,15 @@
declare class RetryfyQueue {
private interval;
private intervalId?;
private limit;
private queueActive;
private queueWaiting;
init: () => void;
reset: () => void;
add: (fn: Function) => void;
remove: (fn: Function) => void;
schedule: () => Promise<Function>;
tick: () => void;
}
declare const _default: RetryfyQueue;
export default _default;

62
node_modules/stubborn-fs/dist/retryify_queue.js generated vendored Normal file
View File

@@ -0,0 +1,62 @@
/* IMPORT */
import { LIMIT_FILES_DESCRIPTORS } from './constants.js';
/* MAIN */
class RetryfyQueue {
constructor() {
/* VARIABLES */
this.interval = 25;
this.intervalId = undefined;
this.limit = LIMIT_FILES_DESCRIPTORS;
this.queueActive = new Set();
this.queueWaiting = new Set();
/* LIFECYCLE API */
this.init = () => {
if (this.intervalId)
return;
this.intervalId = setInterval(this.tick, this.interval);
};
this.reset = () => {
if (!this.intervalId)
return;
clearInterval(this.intervalId);
delete this.intervalId;
};
/* API */
this.add = (fn) => {
this.queueWaiting.add(fn);
if (this.queueActive.size < (this.limit / 2)) { // Active queue not under preassure, executing immediately
this.tick();
}
else {
this.init();
}
};
this.remove = (fn) => {
this.queueWaiting.delete(fn);
this.queueActive.delete(fn);
};
this.schedule = () => {
return new Promise(resolve => {
const cleanup = () => this.remove(resolver);
const resolver = () => resolve(cleanup);
this.add(resolver);
});
};
this.tick = () => {
if (this.queueActive.size >= this.limit)
return;
if (!this.queueWaiting.size)
return this.reset();
for (const fn of this.queueWaiting) {
if (this.queueActive.size >= this.limit)
break;
this.queueWaiting.delete(fn);
this.queueActive.add(fn);
fn();
}
};
}
}
;
/* EXPORT */
export default new RetryfyQueue();

21
node_modules/stubborn-fs/license generated vendored Normal file
View File

@@ -0,0 +1,21 @@
The MIT License (MIT)
Copyright (c) 2022-present Fabio Spampinato
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the "Software"),
to deal in the Software without restriction, including without limitation
the rights to use, copy, modify, merge, publish, distribute, sublicense,
and/or sell copies of the Software, and to permit persons to whom the
Software is furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
DEALINGS IN THE SOFTWARE.

28
node_modules/stubborn-fs/package.json generated vendored Executable file
View File

@@ -0,0 +1,28 @@
{
"name": "stubborn-fs",
"repository": "github:fabiospampinato/stubborn-fs",
"description": "Stubborn versions of Node's fs functions that try really hard to do their job.",
"version": "1.2.5",
"type": "module",
"main": "dist/index.js",
"exports": "./dist/index.js",
"types": "./dist/index.d.ts",
"scripts": {
"clean": "tsex clean",
"compile": "tsex compile",
"compile:watch": "tsex compile --watch",
"prepublishOnly": "tsex prepare"
},
"keywords": [
"fs",
"attempt",
"retry",
"stubborn",
"reliable"
],
"devDependencies": {
"@types/node": "^18.13.0",
"tsex": "^2.1.0",
"typescript": "^4.9.5"
}
}

69
node_modules/stubborn-fs/readme.md generated vendored Normal file
View File

@@ -0,0 +1,69 @@
# Stubborn FS
Stubborn versions of Node's `fs` functions that try really hard to do their job.
## Install
```sh
npm install --save stubborn-fs
```
## Usage
The following functions are currently provided, if you need others please open an issue.
- `attempt` functions swallow some errors that may occur.
- `retry` functions are executed in a loop until they succeed or the timeout is reached, in which case an error is thrown.
```ts
import fs from 'stubborn-fs';
// Attempt functions (async)
fs.attempt.chmod;
fs.attempt.chown;
fs.attempt.close;
fs.attempt.fsync;
fs.attempt.mkdir;
fs.attempt.realpath;
fs.attempt.stat;
fs.attempt.unlink;
// Attempt functions (sync)
fs.attempt.chmodSync;
fs.attempt.chownSync;
fs.attempt.closeSync;
fs.attempt.existsSync;
fs.attempt.fsyncSync;
fs.attempt.mkdirSync;
fs.attempt.realpathSync;
fs.attempt.statSync;
fs.attempt.unlinkSync;
// Retry functions (async)
fs.retry.close;
fs.retry.fsync;
fs.retry.open;
fs.retry.readFile;
fs.retry.rename;
fs.retry.stat;
fs.retry.write;
fs.retry.writeFile;
// Retry functions (sync)
fs.retry.closeSync;
fs.retry.fsyncSync;
fs.retry.openSync;
fs.retry.readFileSync;
fs.retry.renameSync;
fs.retry.statSync;
fs.retry.writeSync;
fs.retry.writeFileSync;
```
## License
MIT © Fabio Spampinato

36
node_modules/stubborn-fs/src/attemptify.ts generated vendored Normal file
View File

@@ -0,0 +1,36 @@
/* MAIN */
//FIXME: The return type of these functions is wrong, it doesn't account for returning "undefined", but a correct type cannot be written because generics cannot be extended properly, it seems
const attemptifyAsync = <FN extends Function> ( fn: FN, onError: (( error: unknown ) => undefined) ): FN => {
return function attemptified ( ...args: any ): any {
return fn.apply ( undefined, args ).catch ( onError );
} as any;
};
const attemptifySync = <FN extends Function> ( fn: FN, onError: (( error: unknown ) => undefined) ): FN => {
return function attemptified ( ...args: any ): any {
try {
return fn.apply ( undefined, args );
} catch ( error: unknown ) {
return onError ( error );
}
} as any;
};
/* EXPORT */
export {attemptifyAsync, attemptifySync};

16
node_modules/stubborn-fs/src/constants.ts generated vendored Normal file
View File

@@ -0,0 +1,16 @@
/* IMPORT */
import process from 'node:process';
/* MAIN */
const IS_USER_ROOT = process.getuid ? !process.getuid () : false;
const LIMIT_FILES_DESCRIPTORS = 10_000; //TODO: Fetch the real limit from the filesystem, somehow
const NOOP = () => undefined;
/* EXPORT */
export {IS_USER_ROOT, LIMIT_FILES_DESCRIPTORS, NOOP};

58
node_modules/stubborn-fs/src/handlers.ts generated vendored Normal file
View File

@@ -0,0 +1,58 @@
/* IMPORT */
import {IS_USER_ROOT} from './constants';
/* MAIN */
const Handlers = {
/* API */
isChangeErrorOk: ( error: unknown ): boolean => { //URL: https://github.com/isaacs/node-graceful-fs/blob/master/polyfills.js#L315-L342
if ( !Handlers.isNodeError ( error ) ) return false;
const {code} = error;
if ( code === 'ENOSYS' ) return true;
if ( !IS_USER_ROOT && ( code === 'EINVAL' || code === 'EPERM' ) ) return true;
return false;
},
isNodeError: ( error: unknown ): error is NodeJS.ErrnoException => {
return ( error instanceof Error );
},
isRetriableError: ( error: unknown ): boolean => {
if ( !Handlers.isNodeError ( error ) ) return false;
const {code} = error;
if ( code === 'EMFILE' || code === 'ENFILE' || code === 'EAGAIN' || code === 'EBUSY' || code === 'EACCESS' || code === 'EACCES' || code === 'EACCS' || code === 'EPERM' ) return true;
return false;
},
onChangeError: ( error: unknown ): undefined => {
if ( !Handlers.isNodeError ( error ) ) throw error;
if ( Handlers.isChangeErrorOk ( error ) ) return;
throw error;
}
};
/* EXPORT */
export default Handlers;

59
node_modules/stubborn-fs/src/index.ts generated vendored Normal file
View File

@@ -0,0 +1,59 @@
/* IMPORT */
import fs from 'node:fs';
import {promisify} from 'node:util';
import {attemptifyAsync, attemptifySync} from './attemptify';
import {NOOP} from './constants';
import Handlers from './handlers';
import {retryifyAsync, retryifySync} from './retryify';
/* MAIN */
const FS = {
attempt: {
/* ASYNC */
chmod: attemptifyAsync ( promisify ( fs.chmod ), Handlers.onChangeError ),
chown: attemptifyAsync ( promisify ( fs.chown ), Handlers.onChangeError ),
close: attemptifyAsync ( promisify ( fs.close ), NOOP ),
fsync: attemptifyAsync ( promisify ( fs.fsync ), NOOP ),
mkdir: attemptifyAsync ( promisify ( fs.mkdir ), NOOP ),
realpath: attemptifyAsync ( promisify ( fs.realpath ), NOOP ),
stat: attemptifyAsync ( promisify ( fs.stat ), NOOP ),
unlink: attemptifyAsync ( promisify ( fs.unlink ), NOOP ),
/* SYNC */
chmodSync: attemptifySync ( fs.chmodSync, Handlers.onChangeError ),
chownSync: attemptifySync ( fs.chownSync, Handlers.onChangeError ),
closeSync: attemptifySync ( fs.closeSync, NOOP ),
existsSync: attemptifySync ( fs.existsSync, NOOP ),
fsyncSync: attemptifySync ( fs.fsync, NOOP ),
mkdirSync: attemptifySync ( fs.mkdirSync, NOOP ),
realpathSync: attemptifySync ( fs.realpathSync, NOOP ),
statSync: attemptifySync ( fs.statSync, NOOP ),
unlinkSync: attemptifySync ( fs.unlinkSync, NOOP )
},
retry: {
/* ASYNC */
close: retryifyAsync ( promisify ( fs.close ), Handlers.isRetriableError ),
fsync: retryifyAsync ( promisify ( fs.fsync ), Handlers.isRetriableError ),
open: retryifyAsync ( promisify ( fs.open ), Handlers.isRetriableError ),
readFile: retryifyAsync ( promisify ( fs.readFile ), Handlers.isRetriableError ),
rename: retryifyAsync ( promisify ( fs.rename ), Handlers.isRetriableError ),
stat: retryifyAsync ( promisify ( fs.stat ), Handlers.isRetriableError ),
write: retryifyAsync ( promisify ( fs.write ), Handlers.isRetriableError ),
writeFile: retryifyAsync ( promisify ( fs.writeFile ), Handlers.isRetriableError ),
/* SYNC */
closeSync: retryifySync ( fs.closeSync, Handlers.isRetriableError ),
fsyncSync: retryifySync ( fs.fsyncSync, Handlers.isRetriableError ),
openSync: retryifySync ( fs.openSync, Handlers.isRetriableError ),
readFileSync: retryifySync ( fs.readFileSync, Handlers.isRetriableError ),
renameSync: retryifySync ( fs.renameSync, Handlers.isRetriableError ),
statSync: retryifySync ( fs.statSync, Handlers.isRetriableError ),
writeSync: retryifySync ( fs.writeSync, Handlers.isRetriableError ),
writeFileSync: retryifySync ( fs.writeFileSync, Handlers.isRetriableError )
}
};
/* EXPORT */
export default FS;

83
node_modules/stubborn-fs/src/retryify.ts generated vendored Normal file
View File

@@ -0,0 +1,83 @@
/* IMPORT */
import RetryfyQueue from './retryify_queue';
/* MAIN */
//FIXME: There are a boatload of anys here, but apparently generics cannot be extended properly, so...
const retryifyAsync = <FN extends Function> ( fn: FN, isRetriableError: (( error: unknown ) => boolean | void) ): (( timeout: number ) => FN) => {
return function retrified ( timestamp: number ) {
return function attempt ( ...args: any ): any {
return RetryfyQueue.schedule ().then ( cleanup => {
const onResolve = ( result: any ): Promise<any> => {
cleanup ();
return result;
};
const onReject = ( error: unknown ): Promise<any> => {
cleanup ();
if ( Date.now () >= timestamp ) throw error;
if ( isRetriableError ( error ) ) {
const delay = Math.round ( 100 * Math.random () );
const delayPromise = new Promise ( resolve => setTimeout ( resolve, delay ) );
return delayPromise.then ( () => attempt.apply ( undefined, args ) );
}
throw error;
};
return fn.apply ( undefined, args ).then ( onResolve, onReject );
});
} as any;
};
};
const retryifySync = <FN extends Function> ( fn: FN, isRetriableError: (( error: unknown ) => boolean | void) ): (( timeout: number ) => FN) => {
return function retrified ( timestamp: number ) {
return function attempt ( ...args: any ): any {
try {
return fn.apply ( undefined, args );
} catch ( error: unknown ) {
if ( Date.now () > timestamp ) throw error;
if ( isRetriableError ( error ) ) return attempt.apply ( undefined, args );
throw error;
}
} as any;
};
};
/* EXPORT */
export {retryifyAsync, retryifySync};

101
node_modules/stubborn-fs/src/retryify_queue.ts generated vendored Normal file
View File

@@ -0,0 +1,101 @@
/* IMPORT */
import {LIMIT_FILES_DESCRIPTORS} from './constants';
/* MAIN */
class RetryfyQueue {
/* VARIABLES */
private interval: number = 25;
private intervalId?: NodeJS.Timeout = undefined;
private limit: number = LIMIT_FILES_DESCRIPTORS;
private queueActive: Set<Function> = new Set ();
private queueWaiting: Set<Function> = new Set ();
/* LIFECYCLE API */
init = (): void => {
if ( this.intervalId ) return;
this.intervalId = setInterval ( this.tick, this.interval );
};
reset = (): void => {
if ( !this.intervalId ) return;
clearInterval ( this.intervalId );
delete this.intervalId;
};
/* API */
add = ( fn: Function ): void => {
this.queueWaiting.add ( fn );
if ( this.queueActive.size < ( this.limit / 2 ) ) { // Active queue not under preassure, executing immediately
this.tick ();
} else {
this.init ();
}
};
remove = ( fn: Function ): void => {
this.queueWaiting.delete ( fn );
this.queueActive.delete ( fn );
};
schedule = (): Promise<Function> => {
return new Promise ( resolve => {
const cleanup = () => this.remove ( resolver );
const resolver = () => resolve ( cleanup );
this.add ( resolver );
});
};
tick = (): void => {
if ( this.queueActive.size >= this.limit ) return;
if ( !this.queueWaiting.size ) return this.reset ();
for ( const fn of this.queueWaiting ) {
if ( this.queueActive.size >= this.limit ) break;
this.queueWaiting.delete ( fn );
this.queueActive.add ( fn );
fn ();
}
};
};
/* EXPORT */
export default new RetryfyQueue ();

3
node_modules/stubborn-fs/tsconfig.json generated vendored Executable file
View File

@@ -0,0 +1,3 @@
{
"extends": "tsex/tsconfig.json"
}