Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
gitpod-io
GitHub Repository: gitpod-io/gitpod
Path: blob/main/components/gitpod-protocol/src/util/async-iterator.ts
2500 views
1
/**
2
* Copyright (c) 2020 Gitpod GmbH. All rights reserved.
3
* Licensed under the GNU Affero General Public License (AGPL).
4
* See License.AGPL.txt in the project root for license information.
5
*/
6
7
// Use asyncIterators with es2015
8
if (typeof (Symbol as any).asyncIterator === "undefined") {
9
(Symbol as any).asyncIterator = Symbol.asyncIterator || Symbol("asyncIterator");
10
}
11
12
export async function find<T>(it: AsyncIterableIterator<T>, predicate: (value: T) => boolean): Promise<T | undefined> {
13
for await (const t of it) {
14
if (predicate(t)) {
15
return t;
16
}
17
}
18
return undefined;
19
}
20
export async function filter<T>(it: AsyncIterableIterator<T>, predicate: (value: T) => boolean): Promise<T[]> {
21
const result = [];
22
for await (const t of it) {
23
if (predicate(t)) {
24
result.push(t);
25
}
26
}
27
return result;
28
}
29
30
export interface AsyncCachingIterator<T> extends AsyncIterableIterator<T> {
31
resetCursor(): void;
32
}
33
export class AsyncCachingIteratorImpl<T> implements AsyncIterableIterator<T>, AsyncCachingIterator<T> {
34
protected cache: T[] = [];
35
protected cursor = 0;
36
protected cacheRead = false;
37
38
constructor(protected readonly iterable: AsyncIterableIterator<T>) {}
39
40
public resetCursor() {
41
this.cursor = 0;
42
this.cacheRead = false;
43
}
44
45
public async next(value?: any): Promise<IteratorResult<T>> {
46
if (!this.cacheRead && this.cursor < this.cache.length) {
47
return {
48
done: false,
49
value: this.cache[this.cursor++],
50
};
51
}
52
this.cacheRead = true;
53
54
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument
55
const result = await this.iterable.next(value);
56
if (!result.done) {
57
this.cache.push(result.value);
58
}
59
return result;
60
}
61
62
[Symbol.asyncIterator]() {
63
return this;
64
}
65
}
66
67