UNPKG

12.2 kBJavaScriptView Raw
1"use strict";
2// *****************************************************************************
3// Copyright (C) 2017 TypeFox and others.
4//
5// This program and the accompanying materials are made available under the
6// terms of the Eclipse Public License v. 2.0 which is available at
7// http://www.eclipse.org/legal/epl-2.0.
8//
9// This Source Code may also be made available under the following Secondary
10// Licenses when the conditions for such availability set forth in the Eclipse
11// Public License v. 2.0 are satisfied: GNU General Public License, version 2
12// with the GNU Classpath Exception which is available at
13// https://www.gnu.org/software/classpath/license.html.
14//
15// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
16// *****************************************************************************
17var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
18 var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
19 if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
20 else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
21 return c > 3 && r && Object.defineProperty(target, key, r), r;
22};
23var __metadata = (this && this.__metadata) || function (k, v) {
24 if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
25};
26var __param = (this && this.__param) || function (paramIndex, decorator) {
27 return function (target, key) { decorator(target, key, paramIndex); }
28};
29Object.defineProperty(exports, "__esModule", { value: true });
30exports.createUntitledURI = exports.UntitledResource = exports.UntitledResourceResolver = exports.UNTITLED_SCHEME = exports.InMemoryTextResourceResolver = exports.InMemoryTextResource = exports.MEMORY_TEXT = exports.InMemoryResources = exports.ReferenceMutableResource = exports.MutableResource = exports.DefaultResourceProvider = exports.ResourceProvider = exports.ResourceResolver = exports.ResourceError = exports.Resource = void 0;
31const inversify_1 = require("inversify");
32const uri_1 = require("../common/uri");
33const contribution_provider_1 = require("./contribution-provider");
34const event_1 = require("./event");
35const application_error_1 = require("./application-error");
36const stream_1 = require("./stream");
37const reference_1 = require("./reference");
38var Resource;
39(function (Resource) {
40 async function save(resource, context, token) {
41 if (!resource.saveContents) {
42 return;
43 }
44 if (await trySaveContentChanges(resource, context)) {
45 return;
46 }
47 if (token && token.isCancellationRequested) {
48 return;
49 }
50 if (typeof context.content !== 'string' && resource.saveStream) {
51 await resource.saveStream(context.content, context.options);
52 }
53 else {
54 const content = typeof context.content === 'string' ? context.content : stream_1.Readable.toString(context.content);
55 await resource.saveContents(content, context.options);
56 }
57 }
58 Resource.save = save;
59 async function trySaveContentChanges(resource, context) {
60 if (!context.changes || !resource.saveContentChanges || shouldSaveContent(resource, context)) {
61 return false;
62 }
63 try {
64 await resource.saveContentChanges(context.changes, context.options);
65 return true;
66 }
67 catch (e) {
68 if (!ResourceError.NotFound.is(e) && !ResourceError.OutOfSync.is(e)) {
69 console.error(`Failed to apply incremental changes to '${resource.uri.toString()}':`, e);
70 }
71 return false;
72 }
73 }
74 Resource.trySaveContentChanges = trySaveContentChanges;
75 function shouldSaveContent(resource, { contentLength, changes }) {
76 if (!changes || (resource.saveStream && contentLength > 32 * 1024 * 1024)) {
77 return true;
78 }
79 let contentChangesLength = 0;
80 for (const change of changes) {
81 contentChangesLength += JSON.stringify(change).length;
82 if (contentChangesLength > contentLength) {
83 return true;
84 }
85 }
86 return contentChangesLength > contentLength;
87 }
88 Resource.shouldSaveContent = shouldSaveContent;
89})(Resource = exports.Resource || (exports.Resource = {}));
90var ResourceError;
91(function (ResourceError) {
92 ResourceError.NotFound = application_error_1.ApplicationError.declare(-40000, (raw) => raw);
93 ResourceError.OutOfSync = application_error_1.ApplicationError.declare(-40001, (raw) => raw);
94})(ResourceError = exports.ResourceError || (exports.ResourceError = {}));
95exports.ResourceResolver = Symbol('ResourceResolver');
96exports.ResourceProvider = Symbol('ResourceProvider');
97let DefaultResourceProvider = class DefaultResourceProvider {
98 constructor(resolversProvider) {
99 this.resolversProvider = resolversProvider;
100 }
101 /**
102 * Reject if a resource cannot be provided.
103 */
104 async get(uri) {
105 const resolvers = this.resolversProvider.getContributions();
106 for (const resolver of resolvers) {
107 try {
108 return await resolver.resolve(uri);
109 }
110 catch (err) {
111 // no-op
112 }
113 }
114 return Promise.reject(new Error(`A resource provider for '${uri.toString()}' is not registered.`));
115 }
116};
117DefaultResourceProvider = __decorate([
118 (0, inversify_1.injectable)(),
119 __param(0, (0, inversify_1.inject)(contribution_provider_1.ContributionProvider)),
120 __param(0, (0, inversify_1.named)(exports.ResourceResolver)),
121 __metadata("design:paramtypes", [Object])
122], DefaultResourceProvider);
123exports.DefaultResourceProvider = DefaultResourceProvider;
124class MutableResource {
125 constructor(uri) {
126 this.uri = uri;
127 this.contents = '';
128 this.onDidChangeContentsEmitter = new event_1.Emitter();
129 this.onDidChangeContents = this.onDidChangeContentsEmitter.event;
130 }
131 dispose() { }
132 async readContents() {
133 return this.contents;
134 }
135 async saveContents(contents) {
136 this.contents = contents;
137 this.fireDidChangeContents();
138 }
139 fireDidChangeContents() {
140 this.onDidChangeContentsEmitter.fire(undefined);
141 }
142}
143exports.MutableResource = MutableResource;
144class ReferenceMutableResource {
145 constructor(reference) {
146 this.reference = reference;
147 }
148 get uri() {
149 return this.reference.object.uri;
150 }
151 get onDidChangeContents() {
152 return this.reference.object.onDidChangeContents;
153 }
154 dispose() {
155 this.reference.dispose();
156 }
157 readContents() {
158 return this.reference.object.readContents();
159 }
160 saveContents(contents) {
161 return this.reference.object.saveContents(contents);
162 }
163}
164exports.ReferenceMutableResource = ReferenceMutableResource;
165let InMemoryResources = class InMemoryResources {
166 constructor() {
167 this.resources = new reference_1.SyncReferenceCollection(uri => new MutableResource(new uri_1.default(uri)));
168 }
169 add(uri, contents) {
170 const resourceUri = uri.toString();
171 if (this.resources.has(resourceUri)) {
172 throw new Error(`Cannot add already existing in-memory resource '${resourceUri}'`);
173 }
174 const resource = this.acquire(resourceUri);
175 resource.saveContents(contents);
176 return resource;
177 }
178 update(uri, contents) {
179 const resourceUri = uri.toString();
180 const resource = this.resources.get(resourceUri);
181 if (!resource) {
182 throw new Error(`Cannot update non-existed in-memory resource '${resourceUri}'`);
183 }
184 resource.saveContents(contents);
185 return resource;
186 }
187 resolve(uri) {
188 const uriString = uri.toString();
189 if (!this.resources.has(uriString)) {
190 throw new Error(`In memory '${uriString}' resource does not exist.`);
191 }
192 return this.acquire(uriString);
193 }
194 acquire(uri) {
195 const reference = this.resources.acquire(uri);
196 return new ReferenceMutableResource(reference);
197 }
198};
199InMemoryResources = __decorate([
200 (0, inversify_1.injectable)()
201], InMemoryResources);
202exports.InMemoryResources = InMemoryResources;
203exports.MEMORY_TEXT = 'mem-txt';
204/**
205 * Resource implementation for 'mem-txt' URI scheme where content is saved in URI query.
206 */
207class InMemoryTextResource {
208 constructor(uri) {
209 this.uri = uri;
210 }
211 async readContents(options) {
212 return this.uri.query;
213 }
214 dispose() { }
215}
216exports.InMemoryTextResource = InMemoryTextResource;
217/**
218 * ResourceResolver implementation for 'mem-txt' URI scheme.
219 */
220let InMemoryTextResourceResolver = class InMemoryTextResourceResolver {
221 resolve(uri) {
222 if (uri.scheme !== exports.MEMORY_TEXT) {
223 throw new Error(`Expected a URI with ${exports.MEMORY_TEXT} scheme. Was: ${uri}.`);
224 }
225 return new InMemoryTextResource(uri);
226 }
227};
228InMemoryTextResourceResolver = __decorate([
229 (0, inversify_1.injectable)()
230], InMemoryTextResourceResolver);
231exports.InMemoryTextResourceResolver = InMemoryTextResourceResolver;
232exports.UNTITLED_SCHEME = 'untitled';
233let untitledResourceSequenceIndex = 0;
234let UntitledResourceResolver = class UntitledResourceResolver {
235 constructor() {
236 this.resources = new Map();
237 }
238 async resolve(uri) {
239 if (uri.scheme !== exports.UNTITLED_SCHEME) {
240 throw new Error('The given uri is not untitled file uri: ' + uri);
241 }
242 else {
243 const untitledResource = this.resources.get(uri.toString());
244 if (!untitledResource) {
245 return this.createUntitledResource('', '', uri);
246 }
247 else {
248 return untitledResource;
249 }
250 }
251 }
252 async createUntitledResource(content, extension, uri) {
253 return new UntitledResource(this.resources, uri ? uri : new uri_1.default().withScheme(exports.UNTITLED_SCHEME).withPath(`/Untitled-${untitledResourceSequenceIndex++}${extension !== null && extension !== void 0 ? extension : ''}`), content);
254 }
255};
256UntitledResourceResolver = __decorate([
257 (0, inversify_1.injectable)()
258], UntitledResourceResolver);
259exports.UntitledResourceResolver = UntitledResourceResolver;
260class UntitledResource {
261 constructor(resources, uri, content) {
262 this.resources = resources;
263 this.uri = uri;
264 this.content = content;
265 this.onDidChangeContentsEmitter = new event_1.Emitter();
266 this.resources.set(this.uri.toString(), this);
267 }
268 get onDidChangeContents() {
269 return this.onDidChangeContentsEmitter.event;
270 }
271 dispose() {
272 this.resources.delete(this.uri.toString());
273 this.onDidChangeContentsEmitter.dispose();
274 }
275 async readContents(options) {
276 if (this.content) {
277 return this.content;
278 }
279 else {
280 return '';
281 }
282 }
283 async saveContents(content, options) {
284 // This function must exist to ensure readOnly is false for the Monaco editor.
285 // However it should not be called because saving 'untitled' is always processed as 'Save As'.
286 throw Error('Untitled resources cannot be saved.');
287 }
288 fireDidChangeContents() {
289 this.onDidChangeContentsEmitter.fire(undefined);
290 }
291 get version() {
292 return undefined;
293 }
294 get encoding() {
295 return undefined;
296 }
297}
298exports.UntitledResource = UntitledResource;
299function createUntitledURI(extension, parent) {
300 const name = `Untitled-${untitledResourceSequenceIndex++}${extension !== null && extension !== void 0 ? extension : ''}`;
301 if (parent) {
302 return parent.resolve(name).withScheme(exports.UNTITLED_SCHEME);
303 }
304 return new uri_1.default().resolve(name).withScheme(exports.UNTITLED_SCHEME);
305}
306exports.createUntitledURI = createUntitledURI;
307//# sourceMappingURL=resource.js.map
\No newline at end of file