@codingame/monaco-vscode-notebook-service-override 1.85.2 → 1.85.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@codingame/monaco-vscode-notebook-service-override",
|
|
3
|
-
"version": "1.85.
|
|
3
|
+
"version": "1.85.3",
|
|
4
4
|
"keywords": [],
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "CodinGame",
|
|
@@ -18,7 +18,7 @@
|
|
|
18
18
|
"module": "index.js",
|
|
19
19
|
"types": "index.d.ts",
|
|
20
20
|
"dependencies": {
|
|
21
|
-
"vscode": "npm:@codingame/monaco-vscode-api@1.85.
|
|
21
|
+
"vscode": "npm:@codingame/monaco-vscode-api@1.85.3",
|
|
22
22
|
"monaco-editor": "0.45.0"
|
|
23
23
|
},
|
|
24
24
|
"exports": {
|
|
@@ -2,7 +2,7 @@ import { __decorate, __param } from '../../../../../../../external/tslib/tslib.e
|
|
|
2
2
|
import { localizeWithPath } from 'monaco-editor/esm/vs/nls.js';
|
|
3
3
|
import { DisposableStore, dispose } from 'monaco-editor/esm/vs/base/common/lifecycle.js';
|
|
4
4
|
import { Emitter, Event } from 'monaco-editor/esm/vs/base/common/event.js';
|
|
5
|
-
import { StoredFileWorkingCopy } from '
|
|
5
|
+
import { StoredFileWorkingCopy } from 'vscode/vscode/vs/workbench/services/workingCopy/common/storedFileWorkingCopy';
|
|
6
6
|
import { ResourceMap } from 'monaco-editor/esm/vs/base/common/map.js';
|
|
7
7
|
import { ResourceQueue, Promises } from 'monaco-editor/esm/vs/base/common/async.js';
|
|
8
8
|
import { IFileService } from 'monaco-editor/esm/vs/platform/files/common/files.js';
|
|
@@ -1,706 +0,0 @@
|
|
|
1
|
-
import { __decorate, __param } from '../../../../../../../external/tslib/tslib.es6.js';
|
|
2
|
-
import { localizeWithPath } from 'monaco-editor/esm/vs/nls.js';
|
|
3
|
-
import { Emitter, Event } from 'monaco-editor/esm/vs/base/common/event.js';
|
|
4
|
-
import { CancellationToken, CancellationTokenSource } from 'monaco-editor/esm/vs/base/common/cancellation.js';
|
|
5
|
-
import { ETAG_DISABLED, NotModifiedSinceFileOperationError, IFileService } from 'monaco-editor/esm/vs/platform/files/common/files.js';
|
|
6
|
-
import { IWorkingCopyService } from 'vscode/vscode/vs/workbench/services/workingCopy/common/workingCopyService';
|
|
7
|
-
import { TaskSequentializer, raceCancellation, timeout } from 'monaco-editor/esm/vs/base/common/async.js';
|
|
8
|
-
import { ILogService } from 'monaco-editor/esm/vs/platform/log/common/log.js';
|
|
9
|
-
import { assertIsDefined } from 'monaco-editor/esm/vs/base/common/types.js';
|
|
10
|
-
import { IWorkingCopyFileService } from 'vscode/vscode/vs/workbench/services/workingCopy/common/workingCopyFileService';
|
|
11
|
-
import { IFilesConfigurationService } from 'vscode/vscode/vs/workbench/services/filesConfiguration/common/filesConfigurationService';
|
|
12
|
-
import { IWorkingCopyBackupService } from 'vscode/vscode/vs/workbench/services/workingCopy/common/workingCopyBackup';
|
|
13
|
-
import { Severity, INotificationService } from 'monaco-editor/esm/vs/platform/notification/common/notification.js';
|
|
14
|
-
import { hash } from 'monaco-editor/esm/vs/base/common/hash.js';
|
|
15
|
-
import { isErrorWithActions, toErrorMessage } from 'monaco-editor/esm/vs/base/common/errorMessage.js';
|
|
16
|
-
import { toAction } from 'monaco-editor/esm/vs/base/common/actions.js';
|
|
17
|
-
import { isWindows } from 'monaco-editor/esm/vs/base/common/platform.js';
|
|
18
|
-
import { IWorkingCopyEditorService } from 'vscode/vscode/vs/workbench/services/workingCopy/common/workingCopyEditorService';
|
|
19
|
-
import { IEditorService } from 'vscode/vscode/vs/workbench/services/editor/common/editorService';
|
|
20
|
-
import { IElevatedFileService } from 'vscode/vscode/vs/workbench/services/files/common/elevatedFileService';
|
|
21
|
-
import { ResourceWorkingCopy } from 'vscode/vscode/vs/workbench/services/workingCopy/common/resourceWorkingCopy';
|
|
22
|
-
|
|
23
|
-
var StoredFileWorkingCopy_1;
|
|
24
|
-
let StoredFileWorkingCopy = class StoredFileWorkingCopy extends ResourceWorkingCopy {
|
|
25
|
-
static { StoredFileWorkingCopy_1 = this; }
|
|
26
|
-
get model() { return this._model; }
|
|
27
|
-
constructor(typeId, resource, name, modelFactory, externalResolver, fileService, logService, workingCopyFileService, filesConfigurationService, workingCopyBackupService, workingCopyService, notificationService, workingCopyEditorService, editorService, elevatedFileService) {
|
|
28
|
-
super(resource, fileService);
|
|
29
|
-
this.typeId = typeId;
|
|
30
|
-
this.name = name;
|
|
31
|
-
this.modelFactory = modelFactory;
|
|
32
|
-
this.externalResolver = externalResolver;
|
|
33
|
-
this.logService = logService;
|
|
34
|
-
this.workingCopyFileService = workingCopyFileService;
|
|
35
|
-
this.filesConfigurationService = filesConfigurationService;
|
|
36
|
-
this.workingCopyBackupService = workingCopyBackupService;
|
|
37
|
-
this.notificationService = notificationService;
|
|
38
|
-
this.workingCopyEditorService = workingCopyEditorService;
|
|
39
|
-
this.editorService = editorService;
|
|
40
|
-
this.elevatedFileService = elevatedFileService;
|
|
41
|
-
this.capabilities = 0 ;
|
|
42
|
-
this._model = undefined;
|
|
43
|
-
this._onDidChangeContent = this._register(( new Emitter()));
|
|
44
|
-
this.onDidChangeContent = this._onDidChangeContent.event;
|
|
45
|
-
this._onDidResolve = this._register(( new Emitter()));
|
|
46
|
-
this.onDidResolve = this._onDidResolve.event;
|
|
47
|
-
this._onDidChangeDirty = this._register(( new Emitter()));
|
|
48
|
-
this.onDidChangeDirty = this._onDidChangeDirty.event;
|
|
49
|
-
this._onDidSaveError = this._register(( new Emitter()));
|
|
50
|
-
this.onDidSaveError = this._onDidSaveError.event;
|
|
51
|
-
this._onDidSave = this._register(( new Emitter()));
|
|
52
|
-
this.onDidSave = this._onDidSave.event;
|
|
53
|
-
this._onDidRevert = this._register(( new Emitter()));
|
|
54
|
-
this.onDidRevert = this._onDidRevert.event;
|
|
55
|
-
this._onDidChangeReadonly = this._register(( new Emitter()));
|
|
56
|
-
this.onDidChangeReadonly = this._onDidChangeReadonly.event;
|
|
57
|
-
this.dirty = false;
|
|
58
|
-
this.ignoreDirtyOnModelContentChange = false;
|
|
59
|
-
this.versionId = 0;
|
|
60
|
-
this.lastContentChangeFromUndoRedo = undefined;
|
|
61
|
-
this.saveSequentializer = ( new TaskSequentializer());
|
|
62
|
-
this.ignoreSaveFromSaveParticipants = false;
|
|
63
|
-
this.inConflictMode = false;
|
|
64
|
-
this.inErrorMode = false;
|
|
65
|
-
this._register(workingCopyService.registerWorkingCopy(this));
|
|
66
|
-
this.registerListeners();
|
|
67
|
-
}
|
|
68
|
-
registerListeners() {
|
|
69
|
-
this._register(this.filesConfigurationService.onReadonlyChange(() => this._onDidChangeReadonly.fire()));
|
|
70
|
-
}
|
|
71
|
-
isDirty() {
|
|
72
|
-
return this.dirty;
|
|
73
|
-
}
|
|
74
|
-
markModified() {
|
|
75
|
-
this.setDirty(true);
|
|
76
|
-
}
|
|
77
|
-
setDirty(dirty) {
|
|
78
|
-
if (!this.isResolved()) {
|
|
79
|
-
return;
|
|
80
|
-
}
|
|
81
|
-
const wasDirty = this.dirty;
|
|
82
|
-
this.doSetDirty(dirty);
|
|
83
|
-
if (dirty !== wasDirty) {
|
|
84
|
-
this._onDidChangeDirty.fire();
|
|
85
|
-
}
|
|
86
|
-
}
|
|
87
|
-
doSetDirty(dirty) {
|
|
88
|
-
const wasDirty = this.dirty;
|
|
89
|
-
const wasInConflictMode = this.inConflictMode;
|
|
90
|
-
const wasInErrorMode = this.inErrorMode;
|
|
91
|
-
const oldSavedVersionId = this.savedVersionId;
|
|
92
|
-
if (!dirty) {
|
|
93
|
-
this.dirty = false;
|
|
94
|
-
this.inConflictMode = false;
|
|
95
|
-
this.inErrorMode = false;
|
|
96
|
-
if (this.isResolved()) {
|
|
97
|
-
this.savedVersionId = this.model.versionId;
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
else {
|
|
101
|
-
this.dirty = true;
|
|
102
|
-
}
|
|
103
|
-
return () => {
|
|
104
|
-
this.dirty = wasDirty;
|
|
105
|
-
this.inConflictMode = wasInConflictMode;
|
|
106
|
-
this.inErrorMode = wasInErrorMode;
|
|
107
|
-
this.savedVersionId = oldSavedVersionId;
|
|
108
|
-
};
|
|
109
|
-
}
|
|
110
|
-
isResolved() {
|
|
111
|
-
return !!this.model;
|
|
112
|
-
}
|
|
113
|
-
async resolve(options) {
|
|
114
|
-
this.trace('resolve() - enter');
|
|
115
|
-
if (this.isDisposed()) {
|
|
116
|
-
this.trace('resolve() - exit - without resolving because file working copy is disposed');
|
|
117
|
-
return;
|
|
118
|
-
}
|
|
119
|
-
if (!options?.contents && (this.dirty || this.saveSequentializer.isRunning())) {
|
|
120
|
-
this.trace('resolve() - exit - without resolving because file working copy is dirty or being saved');
|
|
121
|
-
return;
|
|
122
|
-
}
|
|
123
|
-
return this.doResolve(options);
|
|
124
|
-
}
|
|
125
|
-
async doResolve(options) {
|
|
126
|
-
if (options?.contents) {
|
|
127
|
-
return this.resolveFromBuffer(options.contents);
|
|
128
|
-
}
|
|
129
|
-
const isNew = !this.isResolved();
|
|
130
|
-
if (isNew) {
|
|
131
|
-
const resolvedFromBackup = await this.resolveFromBackup();
|
|
132
|
-
if (resolvedFromBackup) {
|
|
133
|
-
return;
|
|
134
|
-
}
|
|
135
|
-
}
|
|
136
|
-
return this.resolveFromFile(options);
|
|
137
|
-
}
|
|
138
|
-
async resolveFromBuffer(buffer) {
|
|
139
|
-
this.trace('resolveFromBuffer()');
|
|
140
|
-
let mtime;
|
|
141
|
-
let ctime;
|
|
142
|
-
let size;
|
|
143
|
-
let etag;
|
|
144
|
-
try {
|
|
145
|
-
const metadata = await this.fileService.stat(this.resource);
|
|
146
|
-
mtime = metadata.mtime;
|
|
147
|
-
ctime = metadata.ctime;
|
|
148
|
-
size = metadata.size;
|
|
149
|
-
etag = metadata.etag;
|
|
150
|
-
this.setOrphaned(false);
|
|
151
|
-
}
|
|
152
|
-
catch (error) {
|
|
153
|
-
mtime = Date.now();
|
|
154
|
-
ctime = Date.now();
|
|
155
|
-
size = 0;
|
|
156
|
-
etag = ETAG_DISABLED;
|
|
157
|
-
this.setOrphaned(error.fileOperationResult === 1 );
|
|
158
|
-
}
|
|
159
|
-
return this.resolveFromContent({
|
|
160
|
-
resource: this.resource,
|
|
161
|
-
name: this.name,
|
|
162
|
-
mtime,
|
|
163
|
-
ctime,
|
|
164
|
-
size,
|
|
165
|
-
etag,
|
|
166
|
-
value: buffer,
|
|
167
|
-
readonly: false,
|
|
168
|
-
locked: false
|
|
169
|
-
}, true );
|
|
170
|
-
}
|
|
171
|
-
async resolveFromBackup() {
|
|
172
|
-
const backup = await this.workingCopyBackupService.resolve(this);
|
|
173
|
-
const isNew = !this.isResolved();
|
|
174
|
-
if (!isNew) {
|
|
175
|
-
this.trace('resolveFromBackup() - exit - withoutresolving because previously new file working copy got created meanwhile');
|
|
176
|
-
return true;
|
|
177
|
-
}
|
|
178
|
-
if (backup) {
|
|
179
|
-
await this.doResolveFromBackup(backup);
|
|
180
|
-
return true;
|
|
181
|
-
}
|
|
182
|
-
return false;
|
|
183
|
-
}
|
|
184
|
-
async doResolveFromBackup(backup) {
|
|
185
|
-
this.trace('doResolveFromBackup()');
|
|
186
|
-
await this.resolveFromContent({
|
|
187
|
-
resource: this.resource,
|
|
188
|
-
name: this.name,
|
|
189
|
-
mtime: backup.meta ? backup.meta.mtime : Date.now(),
|
|
190
|
-
ctime: backup.meta ? backup.meta.ctime : Date.now(),
|
|
191
|
-
size: backup.meta ? backup.meta.size : 0,
|
|
192
|
-
etag: backup.meta ? backup.meta.etag : ETAG_DISABLED,
|
|
193
|
-
value: backup.value,
|
|
194
|
-
readonly: false,
|
|
195
|
-
locked: false
|
|
196
|
-
}, true );
|
|
197
|
-
if (backup.meta && backup.meta.orphaned) {
|
|
198
|
-
this.setOrphaned(true);
|
|
199
|
-
}
|
|
200
|
-
}
|
|
201
|
-
async resolveFromFile(options) {
|
|
202
|
-
this.trace('resolveFromFile()');
|
|
203
|
-
const forceReadFromFile = options?.forceReadFromFile;
|
|
204
|
-
let etag;
|
|
205
|
-
if (forceReadFromFile) {
|
|
206
|
-
etag = ETAG_DISABLED;
|
|
207
|
-
}
|
|
208
|
-
else if (this.lastResolvedFileStat) {
|
|
209
|
-
etag = this.lastResolvedFileStat.etag;
|
|
210
|
-
}
|
|
211
|
-
const currentVersionId = this.versionId;
|
|
212
|
-
try {
|
|
213
|
-
const content = await this.fileService.readFileStream(this.resource, { etag });
|
|
214
|
-
this.setOrphaned(false);
|
|
215
|
-
if (currentVersionId !== this.versionId) {
|
|
216
|
-
this.trace('resolveFromFile() - exit - without resolving because file working copy content changed');
|
|
217
|
-
return;
|
|
218
|
-
}
|
|
219
|
-
await this.resolveFromContent(content, false );
|
|
220
|
-
}
|
|
221
|
-
catch (error) {
|
|
222
|
-
const result = error.fileOperationResult;
|
|
223
|
-
this.setOrphaned(result === 1 );
|
|
224
|
-
if (this.isResolved() && result === 2 ) {
|
|
225
|
-
if (error instanceof NotModifiedSinceFileOperationError) {
|
|
226
|
-
this.updateLastResolvedFileStat(error.stat);
|
|
227
|
-
}
|
|
228
|
-
return;
|
|
229
|
-
}
|
|
230
|
-
if (this.isResolved() && result === 1 && !forceReadFromFile) {
|
|
231
|
-
return;
|
|
232
|
-
}
|
|
233
|
-
throw error;
|
|
234
|
-
}
|
|
235
|
-
}
|
|
236
|
-
async resolveFromContent(content, dirty) {
|
|
237
|
-
this.trace('resolveFromContent() - enter');
|
|
238
|
-
if (this.isDisposed()) {
|
|
239
|
-
this.trace('resolveFromContent() - exit - because working copy is disposed');
|
|
240
|
-
return;
|
|
241
|
-
}
|
|
242
|
-
this.updateLastResolvedFileStat({
|
|
243
|
-
resource: this.resource,
|
|
244
|
-
name: content.name,
|
|
245
|
-
mtime: content.mtime,
|
|
246
|
-
ctime: content.ctime,
|
|
247
|
-
size: content.size,
|
|
248
|
-
etag: content.etag,
|
|
249
|
-
readonly: content.readonly,
|
|
250
|
-
locked: content.locked,
|
|
251
|
-
isFile: true,
|
|
252
|
-
isDirectory: false,
|
|
253
|
-
isSymbolicLink: false,
|
|
254
|
-
children: undefined
|
|
255
|
-
});
|
|
256
|
-
if (this.isResolved()) {
|
|
257
|
-
await this.doUpdateModel(content.value);
|
|
258
|
-
}
|
|
259
|
-
else {
|
|
260
|
-
await this.doCreateModel(content.value);
|
|
261
|
-
}
|
|
262
|
-
this.setDirty(!!dirty);
|
|
263
|
-
this._onDidResolve.fire();
|
|
264
|
-
}
|
|
265
|
-
async doCreateModel(contents) {
|
|
266
|
-
this.trace('doCreateModel()');
|
|
267
|
-
this._model = this._register(await this.modelFactory.createModel(this.resource, contents, CancellationToken.None));
|
|
268
|
-
this.installModelListeners(this._model);
|
|
269
|
-
}
|
|
270
|
-
async doUpdateModel(contents) {
|
|
271
|
-
this.trace('doUpdateModel()');
|
|
272
|
-
this.ignoreDirtyOnModelContentChange = true;
|
|
273
|
-
try {
|
|
274
|
-
await this.model?.update(contents, CancellationToken.None);
|
|
275
|
-
}
|
|
276
|
-
finally {
|
|
277
|
-
this.ignoreDirtyOnModelContentChange = false;
|
|
278
|
-
}
|
|
279
|
-
}
|
|
280
|
-
installModelListeners(model) {
|
|
281
|
-
this._register(model.onDidChangeContent(e => this.onModelContentChanged(model, e.isUndoing || e.isRedoing)));
|
|
282
|
-
this._register(model.onWillDispose(() => this.dispose()));
|
|
283
|
-
}
|
|
284
|
-
onModelContentChanged(model, isUndoingOrRedoing) {
|
|
285
|
-
this.trace(`onModelContentChanged() - enter`);
|
|
286
|
-
this.versionId++;
|
|
287
|
-
this.trace(`onModelContentChanged() - new versionId ${this.versionId}`);
|
|
288
|
-
if (isUndoingOrRedoing) {
|
|
289
|
-
this.lastContentChangeFromUndoRedo = Date.now();
|
|
290
|
-
}
|
|
291
|
-
if (!this.ignoreDirtyOnModelContentChange && !this.isReadonly()) {
|
|
292
|
-
if (model.versionId === this.savedVersionId) {
|
|
293
|
-
this.trace('onModelContentChanged() - model content changed back to last saved version');
|
|
294
|
-
const wasDirty = this.dirty;
|
|
295
|
-
this.setDirty(false);
|
|
296
|
-
if (wasDirty) {
|
|
297
|
-
this._onDidRevert.fire();
|
|
298
|
-
}
|
|
299
|
-
}
|
|
300
|
-
else {
|
|
301
|
-
this.trace('onModelContentChanged() - model content changed and marked as dirty');
|
|
302
|
-
this.setDirty(true);
|
|
303
|
-
}
|
|
304
|
-
}
|
|
305
|
-
this._onDidChangeContent.fire();
|
|
306
|
-
}
|
|
307
|
-
async forceResolveFromFile() {
|
|
308
|
-
if (this.isDisposed()) {
|
|
309
|
-
return;
|
|
310
|
-
}
|
|
311
|
-
await this.externalResolver({
|
|
312
|
-
forceReadFromFile: true
|
|
313
|
-
});
|
|
314
|
-
}
|
|
315
|
-
get backupDelay() {
|
|
316
|
-
return this.model?.configuration?.backupDelay;
|
|
317
|
-
}
|
|
318
|
-
async backup(token) {
|
|
319
|
-
let meta = undefined;
|
|
320
|
-
if (this.lastResolvedFileStat) {
|
|
321
|
-
meta = {
|
|
322
|
-
mtime: this.lastResolvedFileStat.mtime,
|
|
323
|
-
ctime: this.lastResolvedFileStat.ctime,
|
|
324
|
-
size: this.lastResolvedFileStat.size,
|
|
325
|
-
etag: this.lastResolvedFileStat.etag,
|
|
326
|
-
orphaned: this.isOrphaned()
|
|
327
|
-
};
|
|
328
|
-
}
|
|
329
|
-
let content = undefined;
|
|
330
|
-
if (this.isResolved()) {
|
|
331
|
-
content = await raceCancellation(this.model.snapshot(token), token);
|
|
332
|
-
}
|
|
333
|
-
return { meta, content };
|
|
334
|
-
}
|
|
335
|
-
static { this.UNDO_REDO_SAVE_PARTICIPANTS_AUTO_SAVE_THROTTLE_THRESHOLD = 500; }
|
|
336
|
-
async save(options = Object.create(null)) {
|
|
337
|
-
if (!this.isResolved()) {
|
|
338
|
-
return false;
|
|
339
|
-
}
|
|
340
|
-
if (this.isReadonly()) {
|
|
341
|
-
this.trace('save() - ignoring request for readonly resource');
|
|
342
|
-
return false;
|
|
343
|
-
}
|
|
344
|
-
if ((this.hasState(3 ) || this.hasState(5 )) &&
|
|
345
|
-
((options.reason === 2 || options.reason === 3 || options.reason === 4) )) {
|
|
346
|
-
this.trace('save() - ignoring auto save request for file working copy that is in conflict or error');
|
|
347
|
-
return false;
|
|
348
|
-
}
|
|
349
|
-
this.trace('save() - enter');
|
|
350
|
-
await this.doSave(options);
|
|
351
|
-
this.trace('save() - exit');
|
|
352
|
-
return this.hasState(0 );
|
|
353
|
-
}
|
|
354
|
-
async doSave(options) {
|
|
355
|
-
if (typeof options.reason !== 'number') {
|
|
356
|
-
options.reason = 1 ;
|
|
357
|
-
}
|
|
358
|
-
let versionId = this.versionId;
|
|
359
|
-
this.trace(`doSave(${versionId}) - enter with versionId ${versionId}`);
|
|
360
|
-
if (this.ignoreSaveFromSaveParticipants) {
|
|
361
|
-
this.trace(`doSave(${versionId}) - exit - refusing to save() recursively from save participant`);
|
|
362
|
-
return;
|
|
363
|
-
}
|
|
364
|
-
if (this.saveSequentializer.isRunning(versionId)) {
|
|
365
|
-
this.trace(`doSave(${versionId}) - exit - found a running save for versionId ${versionId}`);
|
|
366
|
-
return this.saveSequentializer.running;
|
|
367
|
-
}
|
|
368
|
-
if (!options.force && !this.dirty) {
|
|
369
|
-
this.trace(`doSave(${versionId}) - exit - because not dirty and/or versionId is different (this.isDirty: ${this.dirty}, this.versionId: ${this.versionId})`);
|
|
370
|
-
return;
|
|
371
|
-
}
|
|
372
|
-
if (this.saveSequentializer.isRunning()) {
|
|
373
|
-
this.trace(`doSave(${versionId}) - exit - because busy saving`);
|
|
374
|
-
this.saveSequentializer.cancelRunning();
|
|
375
|
-
return this.saveSequentializer.queue(() => this.doSave(options));
|
|
376
|
-
}
|
|
377
|
-
if (this.isResolved()) {
|
|
378
|
-
this.model.pushStackElement();
|
|
379
|
-
}
|
|
380
|
-
const saveCancellation = ( new CancellationTokenSource());
|
|
381
|
-
return this.saveSequentializer.run(versionId, (async () => {
|
|
382
|
-
if (this.isResolved() && !options.skipSaveParticipants && this.workingCopyFileService.hasSaveParticipants) {
|
|
383
|
-
try {
|
|
384
|
-
if (options.reason === 2 && typeof this.lastContentChangeFromUndoRedo === 'number') {
|
|
385
|
-
const timeFromUndoRedoToSave = Date.now() - this.lastContentChangeFromUndoRedo;
|
|
386
|
-
if (timeFromUndoRedoToSave < StoredFileWorkingCopy_1.UNDO_REDO_SAVE_PARTICIPANTS_AUTO_SAVE_THROTTLE_THRESHOLD) {
|
|
387
|
-
await timeout(StoredFileWorkingCopy_1.UNDO_REDO_SAVE_PARTICIPANTS_AUTO_SAVE_THROTTLE_THRESHOLD - timeFromUndoRedoToSave);
|
|
388
|
-
}
|
|
389
|
-
}
|
|
390
|
-
if (!saveCancellation.token.isCancellationRequested) {
|
|
391
|
-
this.ignoreSaveFromSaveParticipants = true;
|
|
392
|
-
try {
|
|
393
|
-
await this.workingCopyFileService.runSaveParticipants(this, { reason: options.reason ?? 1 }, saveCancellation.token);
|
|
394
|
-
}
|
|
395
|
-
finally {
|
|
396
|
-
this.ignoreSaveFromSaveParticipants = false;
|
|
397
|
-
}
|
|
398
|
-
}
|
|
399
|
-
}
|
|
400
|
-
catch (error) {
|
|
401
|
-
this.logService.error(`[stored file working copy] runSaveParticipants(${versionId}) - resulted in an error: ${( error.toString())}`, ( this.resource.toString()), this.typeId);
|
|
402
|
-
}
|
|
403
|
-
}
|
|
404
|
-
if (saveCancellation.token.isCancellationRequested) {
|
|
405
|
-
return;
|
|
406
|
-
}
|
|
407
|
-
if (this.isDisposed()) {
|
|
408
|
-
return;
|
|
409
|
-
}
|
|
410
|
-
if (!this.isResolved()) {
|
|
411
|
-
return;
|
|
412
|
-
}
|
|
413
|
-
versionId = this.versionId;
|
|
414
|
-
this.inErrorMode = false;
|
|
415
|
-
this.trace(`doSave(${versionId}) - before write()`);
|
|
416
|
-
const lastResolvedFileStat = assertIsDefined(this.lastResolvedFileStat);
|
|
417
|
-
const resolvedFileWorkingCopy = this;
|
|
418
|
-
return this.saveSequentializer.run(versionId, (async () => {
|
|
419
|
-
try {
|
|
420
|
-
const writeFileOptions = {
|
|
421
|
-
mtime: lastResolvedFileStat.mtime,
|
|
422
|
-
etag: (options.ignoreModifiedSince || !this.filesConfigurationService.preventSaveConflicts(lastResolvedFileStat.resource)) ? ETAG_DISABLED : lastResolvedFileStat.etag,
|
|
423
|
-
unlock: options.writeUnlock
|
|
424
|
-
};
|
|
425
|
-
let stat;
|
|
426
|
-
if (typeof resolvedFileWorkingCopy.model.save === 'function') {
|
|
427
|
-
stat = await resolvedFileWorkingCopy.model.save(writeFileOptions, saveCancellation.token);
|
|
428
|
-
}
|
|
429
|
-
else {
|
|
430
|
-
const snapshot = await raceCancellation(resolvedFileWorkingCopy.model.snapshot(saveCancellation.token), saveCancellation.token);
|
|
431
|
-
if (saveCancellation.token.isCancellationRequested) {
|
|
432
|
-
return;
|
|
433
|
-
}
|
|
434
|
-
else {
|
|
435
|
-
saveCancellation.dispose();
|
|
436
|
-
}
|
|
437
|
-
if (options?.writeElevated && this.elevatedFileService.isSupported(lastResolvedFileStat.resource)) {
|
|
438
|
-
stat = await this.elevatedFileService.writeFileElevated(lastResolvedFileStat.resource, assertIsDefined(snapshot), writeFileOptions);
|
|
439
|
-
}
|
|
440
|
-
else {
|
|
441
|
-
stat = await this.fileService.writeFile(lastResolvedFileStat.resource, assertIsDefined(snapshot), writeFileOptions);
|
|
442
|
-
}
|
|
443
|
-
}
|
|
444
|
-
this.handleSaveSuccess(stat, versionId, options);
|
|
445
|
-
}
|
|
446
|
-
catch (error) {
|
|
447
|
-
this.handleSaveError(error, versionId, options);
|
|
448
|
-
}
|
|
449
|
-
})(), () => saveCancellation.cancel());
|
|
450
|
-
})(), () => saveCancellation.cancel());
|
|
451
|
-
}
|
|
452
|
-
handleSaveSuccess(stat, versionId, options) {
|
|
453
|
-
this.updateLastResolvedFileStat(stat);
|
|
454
|
-
if (versionId === this.versionId) {
|
|
455
|
-
this.trace(`handleSaveSuccess(${versionId}) - setting dirty to false because versionId did not change`);
|
|
456
|
-
this.setDirty(false);
|
|
457
|
-
}
|
|
458
|
-
else {
|
|
459
|
-
this.trace(`handleSaveSuccess(${versionId}) - not setting dirty to false because versionId did change meanwhile`);
|
|
460
|
-
}
|
|
461
|
-
this.setOrphaned(false);
|
|
462
|
-
this._onDidSave.fire({ reason: options.reason, stat, source: options.source });
|
|
463
|
-
}
|
|
464
|
-
handleSaveError(error, versionId, options) {
|
|
465
|
-
(options.ignoreErrorHandler ? this.logService.trace : this.logService.error).apply(this.logService, [`[stored file working copy] handleSaveError(${versionId}) - exit - resulted in a save error: ${( error.toString())}`, ( this.resource.toString()), this.typeId]);
|
|
466
|
-
if (options.ignoreErrorHandler) {
|
|
467
|
-
throw error;
|
|
468
|
-
}
|
|
469
|
-
this.setDirty(true);
|
|
470
|
-
this.inErrorMode = true;
|
|
471
|
-
if (error.fileOperationResult === 3 ) {
|
|
472
|
-
this.inConflictMode = true;
|
|
473
|
-
}
|
|
474
|
-
this.doHandleSaveError(error);
|
|
475
|
-
this._onDidSaveError.fire();
|
|
476
|
-
}
|
|
477
|
-
doHandleSaveError(error) {
|
|
478
|
-
const fileOperationError = error;
|
|
479
|
-
const primaryActions = [];
|
|
480
|
-
let message;
|
|
481
|
-
if (fileOperationError.fileOperationResult === 3 ) {
|
|
482
|
-
message = ( localizeWithPath(
|
|
483
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
484
|
-
'staleSaveError',
|
|
485
|
-
"Failed to save '{0}': The content of the file is newer. Do you want to overwrite the file with your changes?",
|
|
486
|
-
this.name
|
|
487
|
-
));
|
|
488
|
-
primaryActions.push(toAction({ id: 'fileWorkingCopy.overwrite', label: ( localizeWithPath(
|
|
489
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
490
|
-
'overwrite',
|
|
491
|
-
"Overwrite"
|
|
492
|
-
)), run: () => this.save({ ignoreModifiedSince: true }) }));
|
|
493
|
-
primaryActions.push(toAction({ id: 'fileWorkingCopy.revert', label: ( localizeWithPath(
|
|
494
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
495
|
-
'discard',
|
|
496
|
-
"Discard"
|
|
497
|
-
)), run: () => this.revert() }));
|
|
498
|
-
}
|
|
499
|
-
else {
|
|
500
|
-
const isWriteLocked = fileOperationError.fileOperationResult === 5 ;
|
|
501
|
-
const triedToUnlock = isWriteLocked && fileOperationError.options?.unlock;
|
|
502
|
-
const isPermissionDenied = fileOperationError.fileOperationResult === 6 ;
|
|
503
|
-
const canSaveElevated = this.elevatedFileService.isSupported(this.resource);
|
|
504
|
-
if (isErrorWithActions(error)) {
|
|
505
|
-
primaryActions.push(...error.actions);
|
|
506
|
-
}
|
|
507
|
-
if (canSaveElevated && (isPermissionDenied || triedToUnlock)) {
|
|
508
|
-
primaryActions.push(toAction({
|
|
509
|
-
id: 'fileWorkingCopy.saveElevated',
|
|
510
|
-
label: triedToUnlock ?
|
|
511
|
-
isWindows ? ( localizeWithPath(
|
|
512
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
513
|
-
'overwriteElevated',
|
|
514
|
-
"Overwrite as Admin..."
|
|
515
|
-
)) : ( localizeWithPath(
|
|
516
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
517
|
-
'overwriteElevatedSudo',
|
|
518
|
-
"Overwrite as Sudo..."
|
|
519
|
-
)) :
|
|
520
|
-
isWindows ? ( localizeWithPath(
|
|
521
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
522
|
-
'saveElevated',
|
|
523
|
-
"Retry as Admin..."
|
|
524
|
-
)) : ( localizeWithPath(
|
|
525
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
526
|
-
'saveElevatedSudo',
|
|
527
|
-
"Retry as Sudo..."
|
|
528
|
-
)),
|
|
529
|
-
run: () => {
|
|
530
|
-
this.save({ writeElevated: true, writeUnlock: triedToUnlock, reason: 1 });
|
|
531
|
-
}
|
|
532
|
-
}));
|
|
533
|
-
}
|
|
534
|
-
else if (isWriteLocked) {
|
|
535
|
-
primaryActions.push(toAction({ id: 'fileWorkingCopy.unlock', label: ( localizeWithPath(
|
|
536
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
537
|
-
'overwrite',
|
|
538
|
-
"Overwrite"
|
|
539
|
-
)), run: () => this.save({ writeUnlock: true, reason: 1 }) }));
|
|
540
|
-
}
|
|
541
|
-
else {
|
|
542
|
-
primaryActions.push(toAction({ id: 'fileWorkingCopy.retry', label: ( localizeWithPath(
|
|
543
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
544
|
-
'retry',
|
|
545
|
-
"Retry"
|
|
546
|
-
)), run: () => this.save({ reason: 1 }) }));
|
|
547
|
-
}
|
|
548
|
-
primaryActions.push(toAction({
|
|
549
|
-
id: 'fileWorkingCopy.saveAs',
|
|
550
|
-
label: ( localizeWithPath(
|
|
551
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
552
|
-
'saveAs',
|
|
553
|
-
"Save As..."
|
|
554
|
-
)),
|
|
555
|
-
run: async () => {
|
|
556
|
-
const editor = this.workingCopyEditorService.findEditor(this);
|
|
557
|
-
if (editor) {
|
|
558
|
-
const result = await this.editorService.save(editor, { saveAs: true, reason: 1 });
|
|
559
|
-
if (!result.success) {
|
|
560
|
-
this.doHandleSaveError(error);
|
|
561
|
-
}
|
|
562
|
-
}
|
|
563
|
-
}
|
|
564
|
-
}));
|
|
565
|
-
primaryActions.push(toAction({ id: 'fileWorkingCopy.revert', label: ( localizeWithPath(
|
|
566
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
567
|
-
'discard',
|
|
568
|
-
"Discard"
|
|
569
|
-
)), run: () => this.revert() }));
|
|
570
|
-
if (isWriteLocked) {
|
|
571
|
-
if (triedToUnlock && canSaveElevated) {
|
|
572
|
-
message = isWindows ?
|
|
573
|
-
( localizeWithPath(
|
|
574
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
575
|
-
'readonlySaveErrorAdmin',
|
|
576
|
-
"Failed to save '{0}': File is read-only. Select 'Overwrite as Admin' to retry as administrator.",
|
|
577
|
-
this.name
|
|
578
|
-
)) :
|
|
579
|
-
( localizeWithPath(
|
|
580
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
581
|
-
'readonlySaveErrorSudo',
|
|
582
|
-
"Failed to save '{0}': File is read-only. Select 'Overwrite as Sudo' to retry as superuser.",
|
|
583
|
-
this.name
|
|
584
|
-
));
|
|
585
|
-
}
|
|
586
|
-
else {
|
|
587
|
-
message = ( localizeWithPath(
|
|
588
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
589
|
-
'readonlySaveError',
|
|
590
|
-
"Failed to save '{0}': File is read-only. Select 'Overwrite' to attempt to make it writeable.",
|
|
591
|
-
this.name
|
|
592
|
-
));
|
|
593
|
-
}
|
|
594
|
-
}
|
|
595
|
-
else if (canSaveElevated && isPermissionDenied) {
|
|
596
|
-
message = isWindows ?
|
|
597
|
-
( localizeWithPath(
|
|
598
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
599
|
-
'permissionDeniedSaveError',
|
|
600
|
-
"Failed to save '{0}': Insufficient permissions. Select 'Retry as Admin' to retry as administrator.",
|
|
601
|
-
this.name
|
|
602
|
-
)) :
|
|
603
|
-
( localizeWithPath(
|
|
604
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
605
|
-
'permissionDeniedSaveErrorSudo',
|
|
606
|
-
"Failed to save '{0}': Insufficient permissions. Select 'Retry as Sudo' to retry as superuser.",
|
|
607
|
-
this.name
|
|
608
|
-
));
|
|
609
|
-
}
|
|
610
|
-
else {
|
|
611
|
-
message = ( localizeWithPath(
|
|
612
|
-
'vs/workbench/services/workingCopy/common/storedFileWorkingCopy',
|
|
613
|
-
{ key: 'genericSaveError', comment: ['{0} is the resource that failed to save and {1} the error message'] },
|
|
614
|
-
"Failed to save '{0}': {1}",
|
|
615
|
-
this.name,
|
|
616
|
-
toErrorMessage(error, false)
|
|
617
|
-
));
|
|
618
|
-
}
|
|
619
|
-
}
|
|
620
|
-
const handle = this.notificationService.notify({ id: `${hash(( this.resource.toString()))}`, severity: Severity.Error, message, actions: { primary: primaryActions } });
|
|
621
|
-
const listener = this._register(Event.once(Event.any(this.onDidSave, this.onDidRevert))(() => handle.close()));
|
|
622
|
-
this._register(Event.once(handle.onDidClose)(() => listener.dispose()));
|
|
623
|
-
}
|
|
624
|
-
updateLastResolvedFileStat(newFileStat) {
|
|
625
|
-
const oldReadonly = this.isReadonly();
|
|
626
|
-
if (!this.lastResolvedFileStat) {
|
|
627
|
-
this.lastResolvedFileStat = newFileStat;
|
|
628
|
-
}
|
|
629
|
-
else if (this.lastResolvedFileStat.mtime <= newFileStat.mtime) {
|
|
630
|
-
this.lastResolvedFileStat = newFileStat;
|
|
631
|
-
}
|
|
632
|
-
if (this.isReadonly() !== oldReadonly) {
|
|
633
|
-
this._onDidChangeReadonly.fire();
|
|
634
|
-
}
|
|
635
|
-
}
|
|
636
|
-
async revert(options) {
|
|
637
|
-
if (!this.isResolved() || (!this.dirty && !options?.force)) {
|
|
638
|
-
return;
|
|
639
|
-
}
|
|
640
|
-
this.trace('revert()');
|
|
641
|
-
const wasDirty = this.dirty;
|
|
642
|
-
const undoSetDirty = this.doSetDirty(false);
|
|
643
|
-
const softUndo = options?.soft;
|
|
644
|
-
if (!softUndo) {
|
|
645
|
-
try {
|
|
646
|
-
await this.forceResolveFromFile();
|
|
647
|
-
}
|
|
648
|
-
catch (error) {
|
|
649
|
-
if (error.fileOperationResult !== 1 ) {
|
|
650
|
-
undoSetDirty();
|
|
651
|
-
throw error;
|
|
652
|
-
}
|
|
653
|
-
}
|
|
654
|
-
}
|
|
655
|
-
this._onDidRevert.fire();
|
|
656
|
-
if (wasDirty) {
|
|
657
|
-
this._onDidChangeDirty.fire();
|
|
658
|
-
}
|
|
659
|
-
}
|
|
660
|
-
hasState(state) {
|
|
661
|
-
switch (state) {
|
|
662
|
-
case 3 :
|
|
663
|
-
return this.inConflictMode;
|
|
664
|
-
case 1 :
|
|
665
|
-
return this.dirty;
|
|
666
|
-
case 5 :
|
|
667
|
-
return this.inErrorMode;
|
|
668
|
-
case 4 :
|
|
669
|
-
return this.isOrphaned();
|
|
670
|
-
case 2 :
|
|
671
|
-
return this.saveSequentializer.isRunning();
|
|
672
|
-
case 0 :
|
|
673
|
-
return !this.dirty;
|
|
674
|
-
}
|
|
675
|
-
}
|
|
676
|
-
async joinState(state) {
|
|
677
|
-
return this.saveSequentializer.running;
|
|
678
|
-
}
|
|
679
|
-
isReadonly() {
|
|
680
|
-
return this.filesConfigurationService.isReadonly(this.resource, this.lastResolvedFileStat);
|
|
681
|
-
}
|
|
682
|
-
trace(msg) {
|
|
683
|
-
this.logService.trace(`[stored file working copy] ${msg}`, ( this.resource.toString()), this.typeId);
|
|
684
|
-
}
|
|
685
|
-
dispose() {
|
|
686
|
-
this.trace('dispose()');
|
|
687
|
-
this.inConflictMode = false;
|
|
688
|
-
this.inErrorMode = false;
|
|
689
|
-
this._model = undefined;
|
|
690
|
-
super.dispose();
|
|
691
|
-
}
|
|
692
|
-
};
|
|
693
|
-
StoredFileWorkingCopy = StoredFileWorkingCopy_1 = ( __decorate([
|
|
694
|
-
( __param(5, IFileService)),
|
|
695
|
-
( __param(6, ILogService)),
|
|
696
|
-
( __param(7, IWorkingCopyFileService)),
|
|
697
|
-
( __param(8, IFilesConfigurationService)),
|
|
698
|
-
( __param(9, IWorkingCopyBackupService)),
|
|
699
|
-
( __param(10, IWorkingCopyService)),
|
|
700
|
-
( __param(11, INotificationService)),
|
|
701
|
-
( __param(12, IWorkingCopyEditorService)),
|
|
702
|
-
( __param(13, IEditorService)),
|
|
703
|
-
( __param(14, IElevatedFileService))
|
|
704
|
-
], StoredFileWorkingCopy));
|
|
705
|
-
|
|
706
|
-
export { StoredFileWorkingCopy };
|