Skip to content

Commit

Permalink
improve coverage and testability of config.ts
Browse files Browse the repository at this point in the history
  • Loading branch information
brendandburns committed Mar 4, 2025
1 parent f9b0d97 commit 30460bc
Show file tree
Hide file tree
Showing 2 changed files with 79 additions and 9 deletions.
29 changes: 20 additions & 9 deletions src/config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -394,7 +394,11 @@ export class KubeConfig implements SecurityAuthentication {
this.contexts.push(ctx);
}

public loadFromDefault(opts?: Partial<ConfigOptions>, contextFromStartingConfig: boolean = false): void {
public loadFromDefault(
opts?: Partial<ConfigOptions>,
contextFromStartingConfig: boolean = false,
platform: string = process.platform,
): void {
if (process.env.KUBECONFIG && process.env.KUBECONFIG.length > 0) {
const files = process.env.KUBECONFIG.split(path.delimiter).filter((filename: string) => filename);
this.loadFromFile(files[0], opts);
Expand All @@ -405,23 +409,23 @@ export class KubeConfig implements SecurityAuthentication {
}
return;
}
const home = findHomeDir();
const home = findHomeDir(platform);
if (home) {
const config = path.join(home, '.kube', 'config');
if (fileExists(config)) {
this.loadFromFile(config, opts);
return;
}
}
if (process.platform === 'win32') {
if (platform === 'win32') {
try {
const envKubeconfigPathResult = child_process.spawnSync('wsl.exe', [
const envKubeconfigPathResult = this.spawnSync('wsl.exe', [
'bash',
'-c',
'printenv KUBECONFIG',
]);
if (envKubeconfigPathResult.status === 0 && envKubeconfigPathResult.stdout.length > 0) {
const result = child_process.spawnSync('wsl.exe', [
const result = this.spawnSync('wsl.exe', [
'cat',
envKubeconfigPathResult.stdout.toString('utf8'),
]);
Expand All @@ -434,10 +438,10 @@ export class KubeConfig implements SecurityAuthentication {
// Falling back to default kubeconfig
}
try {
const configResult = child_process.spawnSync('wsl.exe', ['cat', '~/.kube/config']);
const configResult = this.spawnSync('wsl.exe', ['cat', '~/.kube/config']);
if (configResult.status === 0) {
this.loadFromString(configResult.stdout.toString('utf8'), opts);
const result = child_process.spawnSync('wsl.exe', ['wslpath', '-w', '~/.kube']);
const result = this.spawnSync('wsl.exe', ['wslpath', '-w', '~/.kube']);
if (result.status === 0) {
this.makePathsAbsolute(result.stdout.toString('utf8'));
}
Expand Down Expand Up @@ -593,6 +597,13 @@ export class KubeConfig implements SecurityAuthentication {
this.applyHTTPSOptions(opts);
await this.applyAuthorizationHeader(opts);
}

private spawnSync(
command: string,
args: string[],
): { status: number | null; stdout: Buffer; stderr: Buffer } {
return child_process.spawnSync(command, args);
}
}

export type ApiConstructor<T extends ApiType> = new (config: Configuration) => T;
Expand Down Expand Up @@ -628,8 +639,8 @@ function dropDuplicatesAndNils(a: string[]): string[] {
}

// Only public for testing.
export function findHomeDir(): string | null {
if (process.platform !== 'win32') {
export function findHomeDir(platform: string = process.platform): string | null {
if (platform !== 'win32') {
if (process.env.HOME) {
try {
fs.accessSync(process.env.HOME);
Expand Down
59 changes: 59 additions & 0 deletions src/config_test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -301,8 +301,10 @@ describe('KubeConfig', () => {
const kc = new KubeConfig();
kc.loadFromFile(kcTlsServerNameFileName);

const requestContext = new RequestContext('https://kube.example.com', HttpMethod.GET);
const opts: https.RequestOptions = {};
await kc.applyToHTTPSOptions(opts);
await kc.applySecurityAuthentication(requestContext);

const expectedAgent = new https.Agent({
ca: Buffer.from('CADATA2', 'utf-8'),
Expand All @@ -322,6 +324,8 @@ describe('KubeConfig', () => {
};

assertRequestOptionsEqual(opts, expectedOptions);
console.log(requestContext.getAgent());
strictEqual((requestContext.getAgent()! as any).options.servername, 'kube.example2.com');
});
it('should apply cert configs', async () => {
const kc = new KubeConfig();
Expand Down Expand Up @@ -1630,5 +1634,60 @@ describe('KubeConfig', () => {
strictEqual(inputData!.toString(), data);
mockfs.restore();
});
it('should try to load from WSL on Windows with wsl.exe not working', () => {
const kc = new KubeConfig();
const commands: { command: string; args: string[] }[] = [];
(kc as any).spawnSync = (cmd: string, args: string[]) => {
commands.push({ command: cmd, args });
return { status: 1, stderr: 'some error' };
};
kc.loadFromDefault(undefined, false, 'win32');
strictEqual(commands.length, 2);
for (let i = 0; i < commands.length; i++) {
strictEqual(commands[i].command, 'wsl.exe');
}
});
it('should try to load from WSL on Windows with $KUBECONFIG', () => {
const kc = new KubeConfig();
const test_path = 'C:\\Users\\user\\.kube\\config';
const configData = readFileSync(kcFileName);
const commands: { command: string; args: string[] }[] = [];
const results: { status: number; stderr: string; stdout: string }[] = [
{ status: 0, stderr: '', stdout: test_path },
{ status: 0, stderr: '', stdout: configData.toString() },
];
let ix = 0;
(kc as any).spawnSync = (cmd: string, args: string[]) => {
commands.push({ command: cmd, args });
return results[ix++];
};
kc.loadFromDefault(undefined, false, 'win32');
strictEqual(commands.length, 2);
for (let i = 0; i < commands.length; i++) {
strictEqual(commands[i].command, 'wsl.exe');
}
validateFileLoad(kc);
});
it('should try to load from WSL on Windows without $KUBECONFIG', () => {
const kc = new KubeConfig();
const configData = readFileSync(kcFileName);
const commands: { command: string; args: string[] }[] = [];
const results: { status: number; stderr: string; stdout: string }[] = [
{ status: 1, stderr: 'Some Error', stdout: '' },
{ status: 0, stderr: '', stdout: configData.toString() },
{ status: 0, stderr: '', stdout: 'C:\\wsldata\\.kube' },
];
let ix = 0;
(kc as any).spawnSync = (cmd: string, args: string[]) => {
commands.push({ command: cmd, args });
return results[ix++];
};
kc.loadFromDefault(undefined, false, 'win32');
strictEqual(commands.length, 3);
for (let i = 0; i < commands.length; i++) {
strictEqual(commands[i].command, 'wsl.exe');
}
validateFileLoad(kc);
});
});
});

0 comments on commit 30460bc

Please sign in to comment.