1
0
mirror of https://github.com/lensapp/lens.git synced 2025-05-20 05:10:56 +00:00

Add unit tests for validateKubeConfig

Signed-off-by: Lauri Nevala <lauri.nevala@gmail.com>
This commit is contained in:
Lauri Nevala 2021-01-15 11:31:09 +02:00
parent 1cbac447b6
commit 7c8ca4085a
2 changed files with 127 additions and 15 deletions

View File

@ -0,0 +1,120 @@
import { KubeConfig } from "@kubernetes/client-node";
import { validateKubeConfig } from "../kube-helpers";
const validKubeconfig = `
apiVersion: v1
clusters:
- cluster:
server: https://localhost
name: test
contexts:
- context:
cluster: test
user: test
name: valid
- context:
cluster: test2
user: test
name: invalidCluster
- context:
cluster: test
user: test2
name: invalidUser
- context:
cluster: test
user: invalidExec
name: invalidExec
current-context: test
kind: Config
preferences: {}
users:
- name: test
user:
exec:
command: echo
- name: invalidExec
user:
exec:
command: foo
`;
describe("validateKubeconfig", () => {
describe("with default validation options", () => {
describe("with valid kubeconfig", () => {
it("does not raise exceptions", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "valid");}).not.toThrow();
});
});
describe("with invalid context object", () => {
it("it raises exception", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "invalid");}).toThrow("No valid context object provided in kubeconfig for context 'invalid'");
});
});
describe("with invalid cluster object", () => {
it("it raises exception", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "invalidCluster");}).toThrow("No valid cluster object provided in kubeconfig for context 'invalidCluster'");
});
});
describe("with invalid user object", () => {
it("it raises exception", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "invalidUser");}).toThrow("No valid user object provided in kubeconfig for context 'invalidUser'");
});
});
describe("with invalid exec command", () => {
it("it raises exception", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "invalidExec");}).toThrow("User Exec command \"foo\" not found on host. Please ensure binary is found in PATH or use absolute path to binary in Kubeconfig");
});
});
});
describe("with validateCluster as false", () => {
describe("with invalid cluster object", () => {
it("does not raise exception", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "invalidCluster", { validateCluster: false });}).not.toThrow();
});
});
});
describe("with validateUser as false", () => {
describe("with invalid user object", () => {
it("does not raise excpetions", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "invalidUser", { validateUser: false });}).not.toThrow();
});
});
});
describe("with validateExec as false", () => {
describe("with invalid exec object", () => {
it("does not raise excpetions", () => {
const kc = new KubeConfig();
kc.loadFromString(validKubeconfig);
expect(() => { validateKubeConfig(kc, "invalidExec", { validateExec: false });}).not.toThrow();
});
});
});
});

View File

@ -151,20 +151,14 @@ export function getNodeWarningConditions(node: V1Node) {
}
/**
* Validates kubeconfig supplied in the add clusters screen. Additionally this will just validate
* the User struct, specifically the command passed to the exec substructure.
* Validates Context, User and Cluster sructs in given kubeconfig. Additionally this will validate
* the command passed to the exec substructure.
*/
export function validateKubeConfig (config: KubeConfig, contextName: string, validationOpts?: { validateCluster?: boolean, validateUser?: boolean, validateExec?: boolean}) {
// we only receive a single context, cluster & user object here so lets validate them as this
// will be called when we add a new cluster to Lens
logger.debug(`validateKubeConfig: validating kubeconfig - ${JSON.stringify(config)}`);
const defaultOpts = {
validateContext: true,
validateUser: true,
validateCluster: true,
validateExec: true
};
const opts = {...defaultOpts, ...validationOpts };
const opts = validationOpts || {};
const { validateUser = true, validateCluster = true, validateExec = true } = opts;
const contextObject = config.getContextObject(contextName);
@ -174,26 +168,24 @@ export function validateKubeConfig (config: KubeConfig, contextName: string, val
}
// Validate the Cluster Object
if (opts.validateCluster && !config.getCluster(contextObject.cluster)) {
if (validateCluster && !config.getCluster(contextObject.cluster)) {
throw new Error(`No valid cluster object provided in kubeconfig for context '${contextName}'`);
}
const user = config.getUser(contextObject.user);
// Validate the User Object
if (opts.validateUser && !user) {
if (validateUser && !user) {
throw new Error(`No valid user object provided in kubeconfig for context '${contextName}'`);
}
// Validate exec command if present
if (opts.validateExec && user.exec) {
if (validateExec && user?.exec) {
const execCommand = user.exec["command"];
// check if the command is absolute or not
const isAbsolute = path.isAbsolute(execCommand);
// validate the exec struct in the user object, start with the command field
logger.debug(`validateKubeConfig: validating user exec command - ${JSON.stringify(execCommand)}`);
if (!commandExists.sync(execCommand)) {
logger.debug(`validateKubeConfig: exec command ${String(execCommand)} in kubeconfig ${contextName} not found`);
throw new ExecValidationNotFoundError(execCommand, isAbsolute);