Skip to content

Commit

Permalink
Fix #60955
Browse files Browse the repository at this point in the history
  • Loading branch information
sandy081 committed Oct 15, 2018
1 parent c19f675 commit 409e61c
Show file tree
Hide file tree
Showing 17 changed files with 190 additions and 39 deletions.
32 changes: 19 additions & 13 deletions src/vs/editor/common/services/modelServiceImpl.ts
Expand Up @@ -27,6 +27,7 @@ import { ITextModel, IModelDeltaDecoration, IModelDecorationOptions, TrackedRang
import { isFalsyOrEmpty } from 'vs/base/common/arrays';
import { basename } from 'vs/base/common/paths';
import { isThenable } from 'vs/base/common/async';
import { ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';

function MODEL_ID(resource: URI): string {
return resource.toString();
Expand Down Expand Up @@ -206,18 +207,18 @@ class ModelMarkerHandler {
}
}

interface IRawEditorConfig {
tabSize?: any;
insertSpaces?: any;
detectIndentation?: any;
trimAutoWhitespace?: any;
creationOptions?: any;
largeFileOptimizations?: any;
}

interface IRawConfig {
files?: {
eol?: any;
};
editor?: {
tabSize?: any;
insertSpaces?: any;
detectIndentation?: any;
trimAutoWhitespace?: any;
creationOptions?: any;
largeFileOptimizations?: any;
};
eol?: any;
editor?: IRawEditorConfig;
}

const DEFAULT_EOL = (platform.isLinux || platform.isMacintosh) ? DefaultEndOfLine.LF : DefaultEndOfLine.CRLF;
Expand All @@ -229,6 +230,7 @@ export class ModelServiceImpl extends Disposable implements IModelService {
private _markerServiceSubscription: IDisposable;
private _configurationService: IConfigurationService;
private _configurationServiceSubscription: IDisposable;
private _resourcePropertiesService: ITextResourcePropertiesService;

private readonly _onModelAdded: Emitter<ITextModel> = this._register(new Emitter<ITextModel>());
public readonly onModelAdded: Event<ITextModel> = this._onModelAdded.event;
Expand All @@ -251,10 +253,12 @@ export class ModelServiceImpl extends Disposable implements IModelService {
constructor(
@IMarkerService markerService: IMarkerService,
@IConfigurationService configurationService: IConfigurationService,
@ITextResourcePropertiesService resourcePropertiesService: ITextResourcePropertiesService,
) {
super();
this._markerService = markerService;
this._configurationService = configurationService;
this._resourcePropertiesService = resourcePropertiesService;
this._models = {};
this._modelCreationOptionsByLanguageAndResource = Object.create(null);

Expand Down Expand Up @@ -284,7 +288,7 @@ export class ModelServiceImpl extends Disposable implements IModelService {
}

let newDefaultEOL = DEFAULT_EOL;
const eol = config.files && config.files.eol;
const eol = config.eol;
if (eol === '\r\n') {
newDefaultEOL = DefaultEndOfLine.CRLF;
} else if (eol === '\n') {
Expand Down Expand Up @@ -320,7 +324,9 @@ export class ModelServiceImpl extends Disposable implements IModelService {
public getCreationOptions(language: string, resource: URI, isForSimpleWidget: boolean): ITextModelCreationOptions {
let creationOptions = this._modelCreationOptionsByLanguageAndResource[language + resource];
if (!creationOptions) {
creationOptions = ModelServiceImpl._readModelOptions(this._configurationService.getValue({ overrideIdentifier: language, resource }), isForSimpleWidget);
const editor = this._configurationService.getValue<IRawEditorConfig>('editor', { overrideIdentifier: language, resource });
const eol = this._resourcePropertiesService.getEOL(resource);
creationOptions = ModelServiceImpl._readModelOptions({ editor, eol }, isForSimpleWidget);
this._modelCreationOptionsByLanguageAndResource[language + resource] = creationOptions;
}
return creationOptions;
Expand Down
12 changes: 12 additions & 0 deletions src/vs/editor/common/services/resourceConfiguration.ts
Expand Up @@ -32,4 +32,16 @@ export interface ITextResourceConfigurationService {
getValue<T>(resource: URI, section?: string): T;
getValue<T>(resource: URI, position?: IPosition, section?: string): T;

}

export const ITextResourcePropertiesService = createDecorator<ITextResourcePropertiesService>('textResourcePropertiesService');

export interface ITextResourcePropertiesService {

_serviceBrand: any;

/**
* Returns the End of Line characters for the given resource
*/
getEOL(resource: URI): string;
}
Expand Up @@ -13,6 +13,9 @@ import { LanguageConfigurationRegistry } from 'vs/editor/common/modes/languageCo
import { ModelServiceImpl } from 'vs/editor/common/services/modelServiceImpl';
import { TestConfigurationService } from 'vs/platform/configuration/test/common/testConfigurationService';
import { javascriptOnEnterRules } from 'vs/editor/test/common/modes/supports/javascriptOnEnterRules';
import { ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
import { isLinux, isMacintosh } from 'vs/base/common/platform';

class MockJSMode extends MockMode {

Expand Down Expand Up @@ -40,7 +43,8 @@ suite('TokenSelectionSupport', () => {
let mode: MockJSMode | null = null;

setup(() => {
modelService = new ModelServiceImpl(null, new TestConfigurationService());
const configurationService = new TestConfigurationService();
modelService = new ModelServiceImpl(null, configurationService, new TestTextResourcePropertiesService(configurationService));
tokenSelectionSupport = new TokenSelectionSupport(modelService);
mode = new MockJSMode();
});
Expand Down Expand Up @@ -161,3 +165,24 @@ suite('TokenSelectionSupport', () => {
]);
});
});

class TestTextResourcePropertiesService implements ITextResourcePropertiesService {

_serviceBrand: any;

constructor(
@IConfigurationService private configurationService: IConfigurationService,
) {
}

getEOL(resource: URI): string {
const filesConfiguration = this.configurationService.getValue<{ eol: string }>('files');
if (filesConfiguration && filesConfiguration.eol) {
if (filesConfiguration.eol !== 'auto') {
return filesConfiguration.eol;
}
}
return (isLinux || isMacintosh) ? '\n' : '\r\n';
}
}

24 changes: 22 additions & 2 deletions src/vs/editor/standalone/browser/simpleServices.ts
Expand Up @@ -21,7 +21,7 @@ import { Event, Emitter } from 'vs/base/common/event';
import { Configuration, DefaultConfigurationModel, ConfigurationModel } from 'vs/platform/configuration/common/configurationModels';
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
import { IProgressService, IProgressRunner } from 'vs/platform/progress/common/progress';
import { ITextResourceConfigurationService } from 'vs/editor/common/services/resourceConfiguration';
import { ITextResourceConfigurationService, ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
import { ITextModelService, ITextModelContentProvider, ITextEditorModel } from 'vs/editor/common/services/resolverService';
import { IDisposable, IReference, ImmortalReference, combinedDisposable, toDisposable } from 'vs/base/common/lifecycle';
import * as dom from 'vs/base/browser/dom';
Expand All @@ -32,7 +32,7 @@ import { Menu } from 'vs/platform/actions/common/menu';
import { ITelemetryService, ITelemetryInfo } from 'vs/platform/telemetry/common/telemetry';
import { ResolvedKeybinding, Keybinding, createKeybinding, SimpleKeybinding } from 'vs/base/common/keyCodes';
import { ResolvedKeybindingItem } from 'vs/platform/keybinding/common/resolvedKeybindingItem';
import { OS } from 'vs/base/common/platform';
import { OS, isLinux, isMacintosh } from 'vs/base/common/platform';
import { Range } from 'vs/editor/common/core/range';
import { ITextModel } from 'vs/editor/common/model';
import { INotificationService, INotification, INotificationHandle, NoOpNotification, IPromptChoice, IPromptOptions } from 'vs/platform/notification/common/notification';
Expand Down Expand Up @@ -459,6 +459,26 @@ export class SimpleResourceConfigurationService implements ITextResourceConfigur
}
}

export class SimpleResourcePropertiesService implements ITextResourcePropertiesService {

_serviceBrand: any;

constructor(
@IConfigurationService private configurationService: IConfigurationService,
) {
}

getEOL(resource: URI): string {
const filesConfiguration = this.configurationService.getValue<{ eol: string }>('files');
if (filesConfiguration && filesConfiguration.eol) {
if (filesConfiguration.eol !== 'auto') {
return filesConfiguration.eol;
}
}
return (isLinux || isMacintosh) ? '\n' : '\r\n';
}
}

export class SimpleMenuService implements IMenuService {

_serviceBrand: any;
Expand Down
8 changes: 5 additions & 3 deletions src/vs/editor/standalone/browser/standaloneServices.ts
Expand Up @@ -23,7 +23,7 @@ import { IWorkspaceContextService } from 'vs/platform/workspace/common/workspace
import { ICodeEditorService } from 'vs/editor/browser/services/codeEditorService';
import { IEditorWorkerService } from 'vs/editor/common/services/editorWorkerService';
import { EditorWorkerServiceImpl } from 'vs/editor/common/services/editorWorkerServiceImpl';
import { ITextResourceConfigurationService } from 'vs/editor/common/services/resourceConfiguration';
import { ITextResourceConfigurationService, ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
import { IModeService } from 'vs/editor/common/services/modeService';
import { ModeServiceImpl } from 'vs/editor/common/services/modeServiceImpl';
import { IModelService } from 'vs/editor/common/services/modelService';
Expand All @@ -32,7 +32,7 @@ import { StandaloneCodeEditorServiceImpl } from 'vs/editor/standalone/browser/st
import {
SimpleConfigurationService, SimpleResourceConfigurationService, SimpleMenuService,
SimpleProgressService, StandaloneCommandService, StandaloneKeybindingService, SimpleNotificationService,
StandaloneTelemetryService, SimpleWorkspaceContextService, SimpleDialogService, SimpleBulkEditService, SimpleUriLabelService
StandaloneTelemetryService, SimpleWorkspaceContextService, SimpleDialogService, SimpleBulkEditService, SimpleUriLabelService, SimpleResourcePropertiesService
} from 'vs/editor/standalone/browser/simpleServices';
import { ContextKeyService } from 'vs/platform/contextkey/browser/contextKeyService';
import { IMenuService } from 'vs/platform/actions/common/actions';
Expand Down Expand Up @@ -120,6 +120,8 @@ export module StaticServices {

export const resourceConfigurationService = define(ITextResourceConfigurationService, () => new SimpleResourceConfigurationService(configurationServiceImpl));

export const resourcePropertiesService = define(ITextResourcePropertiesService, () => new SimpleResourcePropertiesService(configurationServiceImpl));

export const contextService = define(IWorkspaceContextService, () => new SimpleWorkspaceContextService());

export const labelService = define(ILabelService, () => new SimpleUriLabelService());
Expand All @@ -134,7 +136,7 @@ export module StaticServices {

export const modeService = define(IModeService, (o) => new ModeServiceImpl());

export const modelService = define(IModelService, (o) => new ModelServiceImpl(markerService.get(o), configurationService.get(o)));
export const modelService = define(IModelService, (o) => new ModelServiceImpl(markerService.get(o), configurationService.get(o), resourcePropertiesService.get(o)));

export const editorWorkerService = define(IEditorWorkerService, (o) => new EditorWorkerServiceImpl(modelService.get(o), resourceConfigurationService.get(o)));

Expand Down
24 changes: 23 additions & 1 deletion src/vs/editor/test/common/services/modelService.test.ts
Expand Up @@ -13,6 +13,8 @@ import { EditOperation } from 'vs/editor/common/core/editOperation';
import { Range } from 'vs/editor/common/core/range';
import { CharCode } from 'vs/base/common/charCode';
import { createStringBuilder } from 'vs/editor/common/core/stringBuilder';
import { ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';

const GENERATE_TESTS = false;

Expand All @@ -24,7 +26,7 @@ suite('ModelService', () => {
configService.setUserConfiguration('files', { 'eol': '\n' });
configService.setUserConfiguration('files', { 'eol': '\r\n' }, URI.file(platform.isWindows ? 'c:\\myroot' : '/myroot'));

modelService = new ModelServiceImpl(null, configService);
modelService = new ModelServiceImpl(null, configService, new TestTextResourcePropertiesService(configService));
});

teardown(() => {
Expand Down Expand Up @@ -361,3 +363,23 @@ assertComputeEdits(file1, file2);
}
}
}

class TestTextResourcePropertiesService implements ITextResourcePropertiesService {

_serviceBrand: any;

constructor(
@IConfigurationService private configurationService: IConfigurationService,
) {
}

getEOL(resource: URI): string {
const filesConfiguration = this.configurationService.getValue<{ eol: string }>('files');
if (filesConfiguration && filesConfiguration.eol) {
if (filesConfiguration.eol !== 'auto') {
return filesConfiguration.eol;
}
}
return (platform.isLinux || platform.isMacintosh) ? '\n' : '\r\n';
}
}
9 changes: 6 additions & 3 deletions src/vs/workbench/electron-browser/shell.ts
Expand Up @@ -65,7 +65,7 @@ import { restoreFontInfo, readFontInfo, saveFontInfo } from 'vs/editor/browser/c
import * as browser from 'vs/base/browser/browser';
import { IWorkbenchThemeService } from 'vs/workbench/services/themes/common/workbenchThemeService';
import { WorkbenchThemeService } from 'vs/workbench/services/themes/electron-browser/workbenchThemeService';
import { ITextResourceConfigurationService } from 'vs/editor/common/services/resourceConfiguration';
import { ITextResourceConfigurationService, ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
import { TextResourceConfigurationService } from 'vs/editor/common/services/resourceConfigurationImpl';
import { registerThemingParticipant, ITheme, ICssStyleCollector, HIGH_CONTRAST } from 'vs/platform/theme/common/themeService';
import { foreground, selectionBackground, focusBorder, scrollbarShadow, scrollbarSliderActiveBackground, scrollbarSliderBackground, scrollbarSliderHoverBackground, listHighlightForeground, inputPlaceholderForeground } from 'vs/platform/theme/common/colorRegistry';
Expand Down Expand Up @@ -98,6 +98,7 @@ import { ILabelService, LabelService } from 'vs/platform/label/common/label';
import { IDownloadService } from 'vs/platform/download/common/download';
import { DownloadService } from 'vs/platform/download/node/downloadService';
import { runWhenIdle } from 'vs/base/common/async';
import { TextResourcePropertiesService } from 'vs/workbench/services/textfile/electron-browser/textResourcePropertiesService';

/**
* Services that we require for the Shell
Expand Down Expand Up @@ -368,10 +369,12 @@ export class WorkbenchShell extends Disposable {

serviceCollection.set(IModeService, new SyncDescriptor(WorkbenchModeServiceImpl));

serviceCollection.set(IModelService, new SyncDescriptor(ModelServiceImpl));

serviceCollection.set(ITextResourceConfigurationService, new SyncDescriptor(TextResourceConfigurationService));

serviceCollection.set(ITextResourcePropertiesService, new SyncDescriptor(TextResourcePropertiesService));

serviceCollection.set(IModelService, new SyncDescriptor(ModelServiceImpl));

serviceCollection.set(IEditorWorkerService, new SyncDescriptor(EditorWorkerServiceImpl));

serviceCollection.set(IUntitledEditorService, new SyncDescriptor(UntitledEditorService));
Expand Down
6 changes: 5 additions & 1 deletion src/vs/workbench/parts/debug/node/debugger.ts
Expand Up @@ -23,13 +23,17 @@ import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
import { memoize } from 'vs/base/common/decorators';
import { TaskDefinitionRegistry } from 'vs/workbench/parts/tasks/common/taskDefinitionRegistry';
import { getPathFromAmdModule } from 'vs/base/common/amd';
import { ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
import { URI } from 'vs/base/common/uri';
import { Schemas } from 'vs/base/common/network';

export class Debugger implements IDebugger {

private mergedExtensionDescriptions: IExtensionDescription[];

constructor(private configurationManager: IConfigurationManager, private debuggerContribution: IDebuggerContribution, public extensionDescription: IExtensionDescription,
@IConfigurationService private configurationService: IConfigurationService,
@ITextResourcePropertiesService private resourcePropertiesService: ITextResourcePropertiesService,
@ICommandService private commandService: ICommandService,
@IConfigurationResolverService private configurationResolverService: IConfigurationResolverService,
@ITelemetryService private telemetryService: ITelemetryService,
Expand Down Expand Up @@ -153,7 +157,7 @@ export class Debugger implements IDebugger {
initialConfigurations = initialConfigurations.concat(initialConfigs);
}

const eol = this.configurationService.getValue<string>('files.eol') === '\r\n' ? '\r\n' : '\n';
const eol = this.resourcePropertiesService.getEOL(URI.from({ scheme: Schemas.untitled, path: '1' })) === '\r\n' ? '\r\n' : '\n';
const configs = JSON.stringify(initialConfigurations, null, '\t').split('\n').map(line => '\t' + line).join(eol).trim();
const comment1 = nls.localize('launch.config.comment1', "Use IntelliSense to learn about possible attributes.");
const comment2 = nls.localize('launch.config.comment2', "Hover to view descriptions of existing attributes.");
Expand Down
2 changes: 1 addition & 1 deletion src/vs/workbench/parts/debug/test/node/debugger.test.ts
Expand Up @@ -123,7 +123,7 @@ suite('Debug - Debugger', () => {
};

setup(() => {
_debugger = new Debugger(configurationManager, debuggerContribution, extensionDescriptor0, new TestConfigurationService(), undefined, undefined, undefined);
_debugger = new Debugger(configurationManager, debuggerContribution, extensionDescriptor0, new TestConfigurationService(), undefined, undefined, undefined, undefined);
});

teardown(() => {
Expand Down
Expand Up @@ -238,13 +238,15 @@ configurationRegistry.registerConfiguration({
'type': 'string',
'enum': [
'\n',
'\r\n'
'\r\n',
'auto'
],
'enumDescriptions': [
nls.localize('eol.LF', "LF"),
nls.localize('eol.CRLF', "CRLF")
nls.localize('eol.CRLF', "CRLF"),
nls.localize('eol.auto', "Uses operating system specific end of line character.")
],
'default': (platform.isLinux || platform.isMacintosh) ? '\n' : '\r\n',
'default': 'auto',
'description': nls.localize('eol', "The default end of line character."),
'scope': ConfigurationScope.RESOURCE
},
Expand Down
Expand Up @@ -531,8 +531,8 @@ export class PreferencesService extends Disposable implements IPreferencesServic
const languageKey = `[${language}]`;
let setting = settingsModel.getPreference(languageKey);
const model = codeEditor.getModel();
const configuration = this.configurationService.getValue<{ editor: { tabSize: number; insertSpaces: boolean }, files: { eol: string } }>();
const eol = configuration.files && configuration.files.eol;
const configuration = this.configurationService.getValue<{ editor: { tabSize: number; insertSpaces: boolean } }>();
const eol = model.getEOL();
if (setting) {
if (setting.overrides.length) {
const lastSetting = setting.overrides[setting.overrides.length - 1];
Expand Down
@@ -0,0 +1,27 @@
/*---------------------------------------------------------------------------------------------
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/

import { URI } from 'vs/base/common/uri';
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
import { ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
import { OperatingSystem, OS } from 'vs/base/common/platform';

export class TextResourcePropertiesService implements ITextResourcePropertiesService {

_serviceBrand: any;

constructor(
@IConfigurationService private configurationService: IConfigurationService
) { }

getEOL(resource: URI): string {
const filesConfiguration = this.configurationService.getValue<{ eol: string }>('files');
if (filesConfiguration && filesConfiguration.eol && filesConfiguration.eol !== 'auto') {
return filesConfiguration.eol;
}
return OS === OperatingSystem.Linux || OS === OperatingSystem.Macintosh ? '\n' : '\r\n';
}

}

0 comments on commit 409e61c

Please sign in to comment.