code-server/src/nls.ts

81 lines
2.8 KiB
TypeScript

import * as fs from "fs";
import * as path from "path";
import * as util from "util";
import { getPathFromAmdModule } from "vs/base/common/amd";
import * as lp from "vs/base/node/languagePacks";
import product from "vs/platform/product/node/product";
import { Translations } from "vs/workbench/services/extensions/common/extensionPoints";
const configurations = new Map<string, Promise<lp.NLSConfiguration>>();
const metadataPath = path.join(getPathFromAmdModule(require, ""), "nls.metadata.json");
export const isInternalConfiguration = (config: lp.NLSConfiguration): config is lp.InternalNLSConfiguration => {
return config && !!(<lp.InternalNLSConfiguration>config)._languagePackId;
};
const DefaultConfiguration = {
locale: "en",
availableLanguages: {},
};
export const getNlsConfiguration = async (locale: string, userDataPath: string): Promise<lp.NLSConfiguration> => {
const id = `${locale}: ${userDataPath}`;
if (!configurations.has(id)) {
configurations.set(id, new Promise(async (resolve) => {
const config = product.commit && await util.promisify(fs.exists)(metadataPath)
? await lp.getNLSConfiguration(product.commit, userDataPath, metadataPath, locale)
: DefaultConfiguration;
if (isInternalConfiguration(config)) {
config._languagePackSupport = true;
}
resolve(config);
}));
}
return configurations.get(id)!;
};
export const getTranslations = async (locale: string, userDataPath: string): Promise<Translations> => {
const config = await getNlsConfiguration(locale, userDataPath);
if (isInternalConfiguration(config)) {
try {
return JSON.parse(await util.promisify(fs.readFile)(config._translationsConfigFile, "utf8"));
} catch (error) { /* Nothing yet. */}
}
return {};
};
export const getLocaleFromConfig = async (userDataPath: string): Promise<string> => {
let locale = "en";
try {
const localeConfigUri = path.join(userDataPath, "User/locale.json");
const content = stripComments(await util.promisify(fs.readFile)(localeConfigUri, "utf8"));
locale = JSON.parse(content).locale;
} catch (error) { /* Ignore. */ }
return locale;
};
// Taken from src/main.js in the main VS Code source.
const stripComments = (content: string): string => {
const regexp = /("(?:[^\\"]*(?:\\.)?)*")|('(?:[^\\']*(?:\\.)?)*')|(\/\*(?:\r?\n|.)*?\*\/)|(\/{2,}.*?(?:(?:\r?\n)|$))/g;
return content.replace(regexp, (match, _m1, _m2, m3, m4) => {
// Only one of m1, m2, m3, m4 matches
if (m3) {
// A block comment. Replace with nothing
return '';
} else if (m4) {
// A line comment. If it ends in \r?\n then keep it.
const length_1 = m4.length;
if (length_1 > 2 && m4[length_1 - 1] === '\n') {
return m4[length_1 - 2] === '\r' ? '\r\n' : '\n';
}
else {
return '';
}
} else {
// We match a string
return match;
}
});
};