В VSCode существует несколько способов хранить настройки пользователя. До прихода версии 1.53.0 конфиденциальную информацию приходилось сохранять в Memento объектах в workspaceState и globalState или например keytar. А хранение паролей с токенами в стандартном конфигурационном файле или с помощью переменных окружения, являлось не самой лучшей идеей, так как эти данные могли быть прочитаны и кэшированы другими расширениями.
В статье мы посмотрим на способы чтения данных из settings.json и environment variables. А затем создадим класс с минимальным функционалом, отвечающий за хранение и отдачу ключей со значениями из VSCode SecretStorage.

Проект мы условно назовем fancycolor. Процесс инициализации проекта подробно расписан в документации VSCode Extensions, поэтому сразу приступим к интересному.
settings.json
Все настройки от всех VSCode extensions хранятся в общем файле settings.json и соответственно могут быть доступны из любого расширения. К примеру, из нашего приложения fancycolor мы можем легко прочитать список всех хостов и соответствующие им платформы из нашего конфига другого популярного приложения SSH - Remote.
const configurationWorkspace = workspace.getConfiguration() const sshRemotePlatform: string | undefined = configurationWorkspace.get( "remote.SSH.remotePlatform" ) console.log(sshRemotePlatform)
Данный код выведет список вашей конфигурации для расширения SSH - Remote.
Proxy {ubuntu: 'linux', home: 'linux', raspberry: 'linux'}
environment variables
VSCode расширения по умолчанию имеют доступ к переменным окружения пользователя. Все переменные которые вы сохранили в .bashrc в Linux или User.Environment в Windows можно получить с помощью глобального объекта process.env.
Например создадим файл /home/ubuntu/.env с переменной ACCESS_TOKEN_ENV и добавим его в .bashrc.
echo 'export ACCESS_TOKEN_ENV="d8aba3b2-fda0-414a-b867-4798b7892bb4"' >> /home/ubuntu/.env echo "source /home/ubuntu/.env" >> /home/ubuntu/.bashrc
В Windows тоже самое достигается через Powershell.
[System.Environment]::SetEnvironmentVariable('ACCESS_TOKEN_ENV', 'd8aba3b2-fda0-414a-b867-4798b7892bb4', [System.EnvironmentVariableTarget]::User)
Теперь прочитаем его в VSCode fancycolor extension.
import * as process from "process" export const accessTokenEnv = process.env["ACCESS_TOKEN_ENV"] console.log(accessTokenEnv)
В выводе мы видим наш токен.
d8aba3b2-fda0-414a-b867-4798b7892bb4
SecretStorage
На сегодняшний день является лучшим способом хранения паролей, логинов, токенов и другой конфиденциальной информации в VSCode. Для демонстрации создадим простенький класс AuthSettings, где будем хранить fancycolor_token, с минимально необходимыми методами:
initдля инициализации нашего SecretStoragegetter
instancestoreAuthDataдля записи в SecretStoragegetAuthDataдля извлечения данных из SecretStorage
import { ExtensionContext, SecretStorage } from "vscode" export default class AuthSettings { private static _instance: AuthSettings constructor(private secretStorage: SecretStorage) {} static init(context: ExtensionContext): void { /* Create instance of new AuthSettings. */ AuthSettings._instance = new AuthSettings(context.secrets) } static get instance(): AuthSettings { /* Getter of our AuthSettings existing instance. */ return AuthSettings._instance } async storeAuthData(token?: string): Promise<void> { /* Update values in bugout_auth secret storage. */ if (token) { this.secretStorage.store("fancycolor_token", token) } } async getAuthData(): Promise<string | undefined> { /* Retrieve data from secret storage. */ return await this.secretStorage.get("fancycolor_token") } }
В extension.ts напишем функционал позволяющий добавлять и извлекать токен с помощью команд в Command Palette.
import * as vscode from "vscode" import AuthSettings from "./settings" export function activate(context: vscode.ExtensionContext) { // Initialize and get current instance of our Secret Storage AuthSettings.init(context) const settings = AuthSettings.instance // Register commands to save and retrieve token vscode.commands.registerCommand("fancycolor.setToken", async () => { const tokenInput = await vscode.window.showInputBox() await settings.storeAuthData(tokenInput) }) vscode.commands.registerCommand("fancycolor.getToken", async () => { const tokenOutput = await settings.getAuthData() console.log(tokenOutput) }) } export function deactivate() {}
Останется только в package.json зарегистрировать команды fancycolor.setToken и fancycolor.getToken. В последствии при р��боте с VSCode SecretStorage, мы сможем обратиться исключительно к конкретному SecretStorage созданному для нашего приложения, которому будет присвоен свой _id: 'undefined_publisher.fancycolor'.
