Expand VS Code generated SSH config paths
ci / test (push) Canceled after 0s
ci / fuzz-smoke (push) Canceled after 0s
ci / macos-client (macos-aarch64, macos-14) (push) Canceled after 0s
ci / macos-client (macos-x86_64, macos-13) (push) Canceled after 0s
ci / windows-client (push) Canceled after 0s
ci / package-release (linux-x86_64, ubuntu-latest, , , ) (push) Canceled after 0s
ci / package-release (macos-aarch64, macos-14, , , ) (push) Canceled after 0s
ci / package-release (macos-x86_64, macos-13, , , ) (push) Canceled after 0s
ci / package-release (windows-aarch64, windows-latest, aarch64, windows, aarch64-pc-windows-msvc) (push) Canceled after 0s
ci / package-release (windows-x86_64, windows-latest, , , ) (push) Canceled after 0s
ci / remote-bench (push) Canceled after 0s
ci / publish-gitea-release (push) Canceled after 0s
ci / test (push) Canceled after 0s
ci / fuzz-smoke (push) Canceled after 0s
ci / macos-client (macos-aarch64, macos-14) (push) Canceled after 0s
ci / macos-client (macos-x86_64, macos-13) (push) Canceled after 0s
ci / windows-client (push) Canceled after 0s
ci / package-release (linux-x86_64, ubuntu-latest, , , ) (push) Canceled after 0s
ci / package-release (macos-aarch64, macos-14, , , ) (push) Canceled after 0s
ci / package-release (macos-x86_64, macos-13, , , ) (push) Canceled after 0s
ci / package-release (windows-aarch64, windows-latest, aarch64, windows, aarch64-pc-windows-msvc) (push) Canceled after 0s
ci / package-release (windows-x86_64, windows-latest, , , ) (push) Canceled after 0s
ci / remote-bench (push) Canceled after 0s
ci / publish-gitea-release (push) Canceled after 0s
This commit is contained in:
@@ -84,7 +84,11 @@ async function configureHost() {
|
|||||||
});
|
});
|
||||||
const sshDir = path.join(os.homedir(), '.ssh');
|
const sshDir = path.join(os.homedir(), '.ssh');
|
||||||
fs.mkdirSync(sshDir, { recursive: true });
|
fs.mkdirSync(sshDir, { recursive: true });
|
||||||
const generatedPath = config.get('generatedSshConfig') || path.join(sshDir, 'config.dosh');
|
const generatedPath = expandHomePath(
|
||||||
|
config.get('generatedSshConfig') || path.join(sshDir, 'config.dosh'),
|
||||||
|
os.homedir(),
|
||||||
|
process.platform
|
||||||
|
);
|
||||||
const mainConfig = path.join(sshDir, 'config');
|
const mainConfig = path.join(sshDir, 'config');
|
||||||
ensureInclude(mainConfig, sshIncludeTarget(mainConfig, generatedPath, process.platform));
|
ensureInclude(mainConfig, sshIncludeTarget(mainConfig, generatedPath, process.platform));
|
||||||
upsertBlock(generatedPath, alias, block);
|
upsertBlock(generatedPath, alias, block);
|
||||||
@@ -116,6 +120,10 @@ function sshBlock(options) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function ensureInclude(configPath, includeFile) {
|
function ensureInclude(configPath, includeFile) {
|
||||||
|
const dir = path.dirname(configPath);
|
||||||
|
if (dir && dir !== '.') {
|
||||||
|
fs.mkdirSync(dir, { recursive: true });
|
||||||
|
}
|
||||||
const raw = fs.existsSync(configPath) ? fs.readFileSync(configPath, 'utf8') : '';
|
const raw = fs.existsSync(configPath) ? fs.readFileSync(configPath, 'utf8') : '';
|
||||||
if (raw.split(/\r?\n/).some((line) => line.trim().toLowerCase() === `include ${includeFile}`.toLowerCase())) {
|
if (raw.split(/\r?\n/).some((line) => line.trim().toLowerCase() === `include ${includeFile}`.toLowerCase())) {
|
||||||
return;
|
return;
|
||||||
@@ -136,6 +144,10 @@ function sshIncludeTarget(mainConfigPath, generatedPath, platform = process.plat
|
|||||||
}
|
}
|
||||||
|
|
||||||
function upsertBlock(configPath, alias, block) {
|
function upsertBlock(configPath, alias, block) {
|
||||||
|
const dir = path.dirname(configPath);
|
||||||
|
if (dir && dir !== '.') {
|
||||||
|
fs.mkdirSync(dir, { recursive: true });
|
||||||
|
}
|
||||||
const raw = fs.existsSync(configPath) ? fs.readFileSync(configPath, 'utf8') : '';
|
const raw = fs.existsSync(configPath) ? fs.readFileSync(configPath, 'utf8') : '';
|
||||||
const begin = `# BEGIN DOSH ${alias}`;
|
const begin = `# BEGIN DOSH ${alias}`;
|
||||||
const end = `# END DOSH ${alias}`;
|
const end = `# END DOSH ${alias}`;
|
||||||
@@ -173,7 +185,11 @@ async function showSshConfig() {
|
|||||||
const api = requireVscode();
|
const api = requireVscode();
|
||||||
const config = api.workspace.getConfiguration('dosh');
|
const config = api.workspace.getConfiguration('dosh');
|
||||||
const sshDir = path.join(os.homedir(), '.ssh');
|
const sshDir = path.join(os.homedir(), '.ssh');
|
||||||
const generatedPath = config.get('generatedSshConfig') || path.join(sshDir, 'config.dosh');
|
const generatedPath = expandHomePath(
|
||||||
|
config.get('generatedSshConfig') || path.join(sshDir, 'config.dosh'),
|
||||||
|
os.homedir(),
|
||||||
|
process.platform
|
||||||
|
);
|
||||||
if (!fs.existsSync(generatedPath)) {
|
if (!fs.existsSync(generatedPath)) {
|
||||||
api.window.showWarningMessage('No generated Dosh SSH config yet.');
|
api.window.showWarningMessage('No generated Dosh SSH config yet.');
|
||||||
return;
|
return;
|
||||||
@@ -213,6 +229,17 @@ function normalizeCase(value, platform) {
|
|||||||
return platform === 'win32' ? value.toLowerCase() : value;
|
return platform === 'win32' ? value.toLowerCase() : value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function expandHomePath(value, home = os.homedir(), platform = process.platform) {
|
||||||
|
if (value === '~') {
|
||||||
|
return home;
|
||||||
|
}
|
||||||
|
if (value.startsWith('~/') || value.startsWith('~\\')) {
|
||||||
|
const pathApi = platform === 'win32' ? path.win32 : path;
|
||||||
|
return pathApi.join(home, value.slice(2));
|
||||||
|
}
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
function windowsCommandWord(value) {
|
function windowsCommandWord(value) {
|
||||||
let out = '"';
|
let out = '"';
|
||||||
let backslashes = 0;
|
let backslashes = 0;
|
||||||
@@ -241,10 +268,13 @@ function deactivate() {}
|
|||||||
module.exports = {
|
module.exports = {
|
||||||
activate,
|
activate,
|
||||||
deactivate,
|
deactivate,
|
||||||
|
expandHomePath,
|
||||||
|
ensureInclude,
|
||||||
sshBlock,
|
sshBlock,
|
||||||
sshConfigPathWord,
|
sshConfigPathWord,
|
||||||
shellQuote,
|
shellQuote,
|
||||||
sshIncludeTarget,
|
sshIncludeTarget,
|
||||||
sshConfigWord,
|
sshConfigWord,
|
||||||
|
upsertBlock,
|
||||||
windowsCommandWord
|
windowsCommandWord
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,12 +1,18 @@
|
|||||||
const test = require('node:test');
|
const test = require('node:test');
|
||||||
const assert = require('node:assert/strict');
|
const assert = require('node:assert/strict');
|
||||||
|
const fs = require('node:fs');
|
||||||
|
const os = require('node:os');
|
||||||
|
const path = require('node:path');
|
||||||
|
|
||||||
const {
|
const {
|
||||||
|
expandHomePath,
|
||||||
|
ensureInclude,
|
||||||
shellQuote,
|
shellQuote,
|
||||||
sshBlock,
|
sshBlock,
|
||||||
sshConfigPathWord,
|
sshConfigPathWord,
|
||||||
sshIncludeTarget,
|
sshIncludeTarget,
|
||||||
sshConfigWord,
|
sshConfigWord,
|
||||||
|
upsertBlock,
|
||||||
windowsCommandWord
|
windowsCommandWord
|
||||||
} = require('./extension');
|
} = require('./extension');
|
||||||
|
|
||||||
@@ -83,3 +89,35 @@ test('ssh include target handles Windows custom generated config paths', () => {
|
|||||||
'C:/Users/palav/.ssh/config.dosh'
|
'C:/Users/palav/.ssh/config.dosh'
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('home-relative generated config paths expand for POSIX and Windows', () => {
|
||||||
|
assert.equal(
|
||||||
|
expandHomePath('~/Library/Application Support/Dosh/config.dosh', '/Users/palav', 'darwin'),
|
||||||
|
'/Users/palav/Library/Application Support/Dosh/config.dosh'
|
||||||
|
);
|
||||||
|
assert.equal(
|
||||||
|
expandHomePath('~\\.ssh\\config.dosh', 'C:\\Users\\palav', 'win32'),
|
||||||
|
'C:\\Users\\palav\\.ssh\\config.dosh'
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('config writers create missing parent directories', () => {
|
||||||
|
const root = fs.mkdtempSync(path.join(os.tmpdir(), 'dosh-vscode-'));
|
||||||
|
const mainConfig = path.join(root, 'ssh', 'config');
|
||||||
|
const generatedConfig = path.join(root, 'generated', 'config.dosh');
|
||||||
|
|
||||||
|
ensureInclude(mainConfig, '../generated/config.dosh');
|
||||||
|
upsertBlock(
|
||||||
|
generatedConfig,
|
||||||
|
'dosh-test',
|
||||||
|
[
|
||||||
|
'# BEGIN DOSH dosh-test',
|
||||||
|
'Host dosh-test',
|
||||||
|
' ProxyCommand dosh proxy-stdio test %h %p',
|
||||||
|
'# END DOSH dosh-test'
|
||||||
|
].join('\n')
|
||||||
|
);
|
||||||
|
|
||||||
|
assert.equal(fs.readFileSync(mainConfig, 'utf8'), 'Include ../generated/config.dosh\n');
|
||||||
|
assert.match(fs.readFileSync(generatedConfig, 'utf8'), /Host dosh-test/);
|
||||||
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user