Code improvements.

This commit is contained in:
hediet
2020-08-14 16:10:45 +02:00
parent 7ba2428819
commit 24aa6857e5
25 changed files with 635 additions and 447 deletions

View File

@@ -0,0 +1,120 @@
import { Uri, workspace, ConfigurationTarget, Disposable } from "vscode";
import { fromResource } from "mobx-utils";
import { computed, runInAction } from "mobx";
import { EventEmitter } from "@hediet/std/events";
export interface Serializer<T> {
deserialize: (val: any) => T;
serializer: (val: T) => any;
}
export function serializerWithDefault<T>(defaultValue: T): Serializer<T> {
return {
deserialize: val => (val === undefined ? defaultValue : val),
serializer: val => val,
};
}
export class VsCodeSetting<T> {
public get T(): T {
throw new Error();
}
public readonly serializer: Serializer<T>;
public readonly scope: Uri | undefined;
private readonly settingResource: VsCodeSettingResource;
public constructor(
public readonly id: string,
options: {
serializer?: Serializer<T>;
scope?: Uri;
} = {}
) {
this.scope = options.scope;
this.serializer = options.serializer || {
deserialize: val => val,
serializer: val => val,
};
this.settingResource = new VsCodeSettingResource(this.id, this.scope);
}
public get(): T {
const result = this.settingResource.value;
return this.serializer.deserialize(result);
}
public async set(value: T): Promise<void> {
const value2 = this.serializer.serializer(value);
const c = workspace.getConfiguration(undefined, this.scope);
const result = c.inspect(this.id);
let target: ConfigurationTarget;
if (
result &&
[result.workspaceFolderValue].some(i => i !== undefined)
) {
target = ConfigurationTarget.WorkspaceFolder;
}
if (result && [result.workspaceValue].some(i => i !== undefined)) {
target = ConfigurationTarget.Workspace;
} else {
target = ConfigurationTarget.Global;
}
await c.update(this.id, value2, target);
}
}
class VsCodeSettingResource {
public static onConfigChange = new EventEmitter();
private subscription: Disposable | undefined;
private readonly resource = fromResource<any>(
update => {
update(this.readValue());
this.subscription = VsCodeSettingResource.onConfigChange.sub(() => {
update(this.readValue());
});
},
() => this.subscription!.dispose(),
this.readValue()
);
constructor(
private readonly id: string,
private readonly scope: Uri | undefined
) {}
private readValue(): any {
const val = workspace
.getConfiguration(undefined, this.scope)
.get(this.id);
return val;
}
/**
* This improves change detection.
*/
private readonly stringifiedSettingValue = computed(
() => JSON.stringify(this.resource.current()),
{
name: `VsCodeSettingResource[${this.id}].value`,
context: this,
}
);
public get value() {
const v = this.stringifiedSettingValue.get();
if (v === undefined) {
return undefined;
}
return JSON.parse(v);
}
}
workspace.onDidChangeConfiguration(() => {
runInAction("Update Configuration", () => {
VsCodeSettingResource.onConfigChange.emit();
});
});