UNPKG

monaco-editor-core

Version:

A browser based code editor

90 lines (89 loc) 4.32 kB
/*--------------------------------------------------------------------------------------------- * Copyright (c) Microsoft Corporation. All rights reserved. * Licensed under the MIT License. See License.txt in the project root for license information. *--------------------------------------------------------------------------------------------*/ import { Emitter, Event } from '../../../base/common/event.js'; import { Disposable } from '../../../base/common/lifecycle.js'; import { LanguagesRegistry } from './languagesRegistry.js'; import { firstOrDefault } from '../../../base/common/arrays.js'; import { TokenizationRegistry } from '../languages.js'; import { PLAINTEXT_LANGUAGE_ID } from '../languages/modesRegistry.js'; import { observableFromEvent } from '../../../base/common/observable.js'; export class LanguageService extends Disposable { static { this.instanceCount = 0; } constructor(warnOnOverwrite = false) { super(); this._onDidRequestBasicLanguageFeatures = this._register(new Emitter()); this.onDidRequestBasicLanguageFeatures = this._onDidRequestBasicLanguageFeatures.event; this._onDidRequestRichLanguageFeatures = this._register(new Emitter()); this.onDidRequestRichLanguageFeatures = this._onDidRequestRichLanguageFeatures.event; this._onDidChange = this._register(new Emitter({ leakWarningThreshold: 200 /* https://github.com/microsoft/vscode/issues/119968 */ })); this.onDidChange = this._onDidChange.event; this._requestedBasicLanguages = new Set(); this._requestedRichLanguages = new Set(); LanguageService.instanceCount++; this._registry = this._register(new LanguagesRegistry(true, warnOnOverwrite)); this.languageIdCodec = this._registry.languageIdCodec; this._register(this._registry.onDidChange(() => this._onDidChange.fire())); } dispose() { LanguageService.instanceCount--; super.dispose(); } isRegisteredLanguageId(languageId) { return this._registry.isRegisteredLanguageId(languageId); } getLanguageIdByLanguageName(languageName) { return this._registry.getLanguageIdByLanguageName(languageName); } getLanguageIdByMimeType(mimeType) { return this._registry.getLanguageIdByMimeType(mimeType); } guessLanguageIdByFilepathOrFirstLine(resource, firstLine) { const languageIds = this._registry.guessLanguageIdByFilepathOrFirstLine(resource, firstLine); return firstOrDefault(languageIds, null); } createById(languageId) { return new LanguageSelection(this.onDidChange, () => { return this._createAndGetLanguageIdentifier(languageId); }); } createByFilepathOrFirstLine(resource, firstLine) { return new LanguageSelection(this.onDidChange, () => { const languageId = this.guessLanguageIdByFilepathOrFirstLine(resource, firstLine); return this._createAndGetLanguageIdentifier(languageId); }); } _createAndGetLanguageIdentifier(languageId) { if (!languageId || !this.isRegisteredLanguageId(languageId)) { // Fall back to plain text if language is unknown languageId = PLAINTEXT_LANGUAGE_ID; } return languageId; } requestBasicLanguageFeatures(languageId) { if (!this._requestedBasicLanguages.has(languageId)) { this._requestedBasicLanguages.add(languageId); this._onDidRequestBasicLanguageFeatures.fire(languageId); } } requestRichLanguageFeatures(languageId) { if (!this._requestedRichLanguages.has(languageId)) { this._requestedRichLanguages.add(languageId); // Ensure basic features are requested this.requestBasicLanguageFeatures(languageId); // Ensure tokenizers are created TokenizationRegistry.getOrCreate(languageId); this._onDidRequestRichLanguageFeatures.fire(languageId); } } } class LanguageSelection { constructor(onDidChangeLanguages, selector) { this._value = observableFromEvent(this, onDidChangeLanguages, () => selector()); this.onDidChange = Event.fromObservable(this._value); } get languageId() { return this._value.get(); } }