react-native-epson-escposprinter
Version:
A Turbo Module wrapper for the Epson ePOS Printer SDK.
121 lines (111 loc) • 2.87 kB
JavaScript
;
import { Queue } from "./Queue.js";
/** Indicates the iterator is still in active state. */
const returnSymbol = Symbol.for("AsyncIterator.return");
/**
* Async iterator with manual resolvers exposed.
*
* The Promise.withResolvers counterpart for async iterators.
*/
/**
* Options for async iterator with resolvers.
*/
/**
* Create an async iterator for deferred iterator.
*/
export const asyncIteratorWithResolvers = options => {
const queue = new Queue();
let frontPressure = 0;
let returnPromise;
return {
async [Symbol.asyncDispose]() {
await this.return();
await options?.dispose?.();
},
async return(value, force = true) {
if (returnPromise === undefined) {
returnPromise = Promise.resolve(value);
// Release pending consumers
while (queue.locked) {
queue.push(returnSymbol);
}
// Clear pending values
while (queue.size > 0) {
if (!force) {
await new Promise(resolve => setTimeout(resolve, 100));
} else {
await queue.pop();
}
}
// compat for runtimes without `await using`
// 1. Users must call return() manually
// 2. 100ms should be enough for multiple macrotasks
if (options?.dispose && !("asyncDispose" in Symbol)) {
setTimeout(() => options?.dispose?.(), 100);
}
}
return {
done: true,
value: await returnPromise
};
},
async next() {
if (returnPromise !== undefined && queue.size === 0) {
return {
done: true,
value: await returnPromise
};
}
frontPressure++;
const value = await queue.pop();
frontPressure--;
if (value === returnSymbol) {
return {
done: true,
value: await returnPromise
};
}
return {
done: false,
value: value
};
},
push(value) {
if (value instanceof Promise) {
queue.push(value);
} else {
queue.push(Promise.resolve(value));
}
},
get active() {
return returnPromise === undefined;
},
get backPressure() {
return queue.size;
},
get frontPressure() {
return frontPressure;
}
};
};
/**
* Async iterable iterator with manual resolvers exposed.
*/
/**
* Create an async iterator for deferred iterable.
*
* Manually push values to the iterator and closes it when done.
*/
export const asyncIterableIteratorWithResolvers = options => {
if (Symbol.asyncIterator === undefined) {
throw new Error(`AsyncIterator is not supported.`);
}
const iterator = asyncIteratorWithResolvers(options);
return {
...iterator,
[Symbol.asyncIterator]() {
return this;
}
};
};
//# sourceMappingURL=asyncIterator.js.map