-
-
Notifications
You must be signed in to change notification settings - Fork 435
/
Copy pathprogressible.ts
91 lines (87 loc) · 2.67 KB
/
progressible.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
import { ApplicationError } from '@theia/core/lib/common/application-error';
import type { CancellationToken } from '@theia/core/lib/common/cancellation';
import { CancellationTokenSource } from '@theia/core/lib/common/cancellation';
import type { MessageService } from '@theia/core/lib/common/message-service';
import type { Progress } from '@theia/core/lib/common/message-service-protocol';
import { userAbort } from '../nls';
import type { ResponseServiceClient } from './response-service';
export const UserAbortApplicationError = ApplicationError.declare(
9999,
(message: string, uri: string) => {
return {
message,
data: { uri },
};
}
);
export class UserAbortError extends Error {
constructor() {
super(userAbort);
Object.setPrototypeOf(this, UserAbortError.prototype);
}
}
export namespace ExecuteWithProgress {
export async function doWithProgress<T>(options: {
run: ({
progressId,
cancellationToken,
}: {
progressId: string;
cancellationToken?: CancellationToken;
}) => Promise<T>;
messageService: MessageService;
responseService: ResponseServiceClient;
progressText: string;
keepOutput?: boolean;
cancelable?: boolean;
}): Promise<T> {
return withProgress(
options.progressText,
options.messageService,
// eslint-disable-next-line @typescript-eslint/no-unused-vars
async (progress, token) => {
const progressId = progress.id;
const toDispose = options.responseService.onProgressDidChange(
(progressMessage) => {
if (progressId === progressMessage.progressId) {
const { message, work } = progressMessage;
progress.report({ message, work });
}
}
);
try {
if (!options.keepOutput) {
options.responseService.clearOutput();
}
const result = await options.run({
progressId,
cancellationToken: token,
});
return result;
} finally {
toDispose.dispose();
}
},
options.cancelable
);
}
export async function withProgress<T>(
text: string,
messageService: MessageService,
cb: (progress: Progress, token: CancellationToken) => Promise<T>,
cancelable = false
): Promise<T> {
const cancellationSource = new CancellationTokenSource();
const { token } = cancellationSource;
const progress = await messageService.showProgress(
{ text, options: { cancelable } },
() => cancellationSource.cancel()
);
try {
const result = await cb(progress, token);
return result;
} finally {
progress.cancel();
}
}
}