[bitnami/jupyterhub] Add tests and publishing using VIB (#13432)

* [bitnami/jupyterhub] Add tests and publishing using VIB

Signed-off-by: FraPazGal <fdepaz@vmware.com>

* Remove unused params

Signed-off-by: FraPazGal <fdepaz@vmware.com>

* Update runtime_params

Signed-off-by: FraPazGal <fdepaz@vmware.com>

* Update runtime_params and add missing goss tests

Signed-off-by: FraPazGal <fdepaz@vmware.com>

* Remove unused runtime_param

Signed-off-by: FraPazGal <fdepaz@vmware.com>

* Update runtime_params per suggestion

Signed-off-by: FraPazGal <fdepaz@vmware.com>

Signed-off-by: FraPazGal <fdepaz@vmware.com>
This commit is contained in:
Francisco de Paz Galan
2022-11-16 09:49:52 +01:00
committed by GitHub
parent 1bf577d013
commit 0b9b51a5ef
11 changed files with 330 additions and 0 deletions

View File

@@ -35,6 +35,7 @@ on: # rebuild any PRs and main branch changes
- 'bitnami/jasperreports/**'
- 'bitnami/jenkins/**'
- 'bitnami/joomla/**'
- 'bitnami/jupyterhub/**'
- 'bitnami/kafka/**'
- 'bitnami/keycloak/**'
- 'bitnami/kibana/**'

View File

@@ -0,0 +1,8 @@
{
"baseUrl": "http://localhost/",
"defaultCommandTimeout": 30000,
"env": {
"username": "test_user",
"password": "ComplicatedPassword123!4"
}
}

View File

@@ -0,0 +1,51 @@
{
"cells": [
{
"cell_type": "code",
"execution_count": 1,
"id": "908534a5",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Hello World!"
]
}
],
"source": [
"print(\"Hello\" + \" World!\")"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "215c7ef4",
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.7.9"
}
},
"nbformat": 4,
"nbformat_minor": 5
}

View File

@@ -0,0 +1,44 @@
/// <reference types="cypress" />
import { random } from '../support/utils';
it('allows to upload and execute a python notebook', () => {
const notebookName = `notebook_template_${random}.ipynb`;
const userName = Cypress.env('username');
cy.login();
cy.visit(`/user/${userName}/tree/tmp`);
cy.contains('Upload').should('be.visible');
cy.get('[type=file]').selectFile('cypress/fixtures/notebook_template.ipynb', {
force: true,
});
cy.get('.filename_input').clear().type(notebookName);
cy.contains('button', 'Upload').click();
cy.contains('a', notebookName);
cy.visit(`/user/${userName}/notebooks/tmp/${notebookName}`);
cy.contains('button', 'Run').click();
cy.contains('Hello World!');
});
it('allows generating an API token', () => {
cy.login();
cy.visit('/hub/token');
// We need to wait until the background API request is finished
cy.contains(/\d+Z/).should('not.exist');
cy.contains('button', 'API token').click();
cy.get('#token-result')
.should('be.visible')
.invoke('text')
.then((apiToken) => {
cy.request({
url: '/hub/api/users',
method: 'GET',
headers: {
Authorization: `token ${apiToken}`,
},
}).then((response) => {
expect(response.status).to.eq(200);
expect(response.body[0].name).to.eq(Cypress.env('username'));
});
});
});

View File

@@ -0,0 +1,35 @@
const COMMAND_DELAY = 2000;
for (const command of ['click']) {
Cypress.Commands.overwrite(command, (originalFn, ...args) => {
const origVal = originalFn(...args);
return new Promise((resolve) => {
setTimeout(() => {
resolve(origVal);
}, COMMAND_DELAY);
});
});
}
Cypress.Commands.add(
'login',
(username = Cypress.env('username'), password = Cypress.env('password')) => {
cy.visit('/hub/login');
cy.get('#username_input').type(username);
cy.get('#password_input').type(password);
cy.get('#login_submit').click();
// The authentication is not completed until the page is rendered
cy.contains('Launcher');
}
);
Cypress.on('uncaught:exception', (err, runnable) => {
// we expect a 3rd party library error with message 'list not defined'
// and don't want to fail the test so we return false
if (err.message.includes('Cannot read properties of null')) {
return false;
}
// we still want to ensure there are no other unexpected
// errors, so we let them fail the test
});

View File

@@ -0,0 +1,20 @@
// ***********************************************************
// This example support/index.js is processed and
// loaded automatically before your test files.
//
// This is a great place to put global configuration and
// behavior that modifies Cypress.
//
// You can change the location of this file or turn off
// automatically serving support files with the
// 'supportFile' configuration option.
//
// You can read more here:
// https://on.cypress.io/configuration
// ***********************************************************
// Import commands.js using ES2015 syntax:
import './commands';
// Alternatively you can use CommonJS syntax:
// require('./commands')

View File

@@ -0,0 +1,3 @@
/// <reference types="cypress" />
export let random = (Math.random() + 1).toString(36).substring(7);

View File

@@ -0,0 +1,39 @@
http:
http://jupyterhub-hub:{{ .Vars.hub.service.ports.http }}/hub/health:
status: 200
http://jupyterhub-proxy-api:{{ .Vars.proxy.service.api.ports.http }}:
status: 404
file:
/etc/jupyterhub:
exists: true
filetype: directory
mode: "0755"
owner: root
/etc/jupyterhub/jupyterhub_config.py:
exists: true
filetype: file
mode: "0644"
owner: root
contains:
- /hub_container_port.*{{ .Vars.hub.containerPorts.http }}/
/usr/local/etc/jupyterhub/secret/values.yaml:
exists: true
filetype: symlink
mode: "0777"
owner: root
contains:
- postgresql://{{ .Vars.postgresql.auth.username }}@jupyterhub-postgresql:{{ .Vars.postgresql.service.ports.postgresql }}/{{ .Vars.postgresql.auth.database }}
- /uid.*{{ .Vars.singleuser.containerSecurityContext.runAsUser }}/
- /fsGid.*{{ .Vars.singleuser.podSecurityContext.fsGroup }}/
- /type.*dynamic/
/var/run/secrets/kubernetes.io/serviceaccount:
exists: {{ .Vars.hub.serviceAccount.automountServiceAccountToken }}
filetype: directory
mode: "3777"
command:
check-user-info:
exec: id
exit-status: 0
stdout:
- uid={{ .Vars.hub.containerSecurityContext.runAsUser }}
- /groups=.*{{ .Vars.hub.podSecurityContext.fsGroup }}/

View File

@@ -0,0 +1,29 @@
hub:
containerPorts:
http: 8082
containerSecurityContext:
runAsUser: 1002
podSecurityContext:
fsGroup: 1002
serviceAccount:
automountServiceAccountToken: true
service:
ports:
http: 8082
proxy:
service:
api:
ports:
http: 8000
singleuser:
containerSecurityContext:
runAsUser: 1002
podSecurityContext:
fsGroup: 1002
postgresql:
auth:
username: bn_vib_jupyterhub
database: bitnami_vib_jupyterhub
service:
ports:
postgresql: 5432

View File

@@ -16,6 +16,56 @@
}
]
},
"verify": {
"context": {
"resources": {
"url": "{SHA_ARCHIVE}",
"path": "/bitnami/jupyterhub"
},
"runtime_parameters": "aHViOgogIGJhc2VVcmw6IC8KICBhZG1pblVzZXI6IHRlc3RfdXNlcgogIHBhc3N3b3JkOiBDb21wbGljYXRlZFBhc3N3b3JkMTIzITQKICBjb250YWluZXJQb3J0czoKICAgIGh0dHA6IDgwODIKICBjb250YWluZXJTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBydW5Bc1VzZXI6IDEwMDIKICBwb2RTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBmc0dyb3VwOiAxMDAyCiAgc2VydmljZUFjY291bnQ6CiAgICBjcmVhdGU6IHRydWUKICAgIGF1dG9tb3VudFNlcnZpY2VBY2NvdW50VG9rZW46IHRydWUKICByYmFjOgogICAgY3JlYXRlOiB0cnVlCiAgc2VydmljZToKICAgIHBvcnRzOgogICAgICBodHRwOiA4MDgyCnByb3h5OgogIHNlcnZpY2U6CiAgICBhcGk6CiAgICAgIHBvcnRzOgogICAgICAgIGh0dHA6IDgwMDAKICAgIHB1YmxpYzoKICAgICAgdHlwZTogTG9hZEJhbGFuY2VyCiAgICAgIHBvcnRzOgogICAgICAgIGh0dHA6IDgwCmltYWdlUHVsbGVyOgogIGVuYWJsZWQ6IHRydWUKc2luZ2xldXNlcjoKICBjb250YWluZXJTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBydW5Bc1VzZXI6IDEwMDIKICBwb2RTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBmc0dyb3VwOiAxMDAyCiAgcGVyc2lzdGVuY2U6CiAgICBlbmFibGVkOiB0cnVlCnBvc3RncmVzcWw6CiAgZW5hYmxlZDogdHJ1ZQogIGF1dGg6CiAgICB1c2VybmFtZTogYm5fdmliX2p1cHl0ZXJodWIKICAgIGRhdGFiYXNlOiBiaXRuYW1pX3ZpYl9qdXB5dGVyaHViCiAgc2VydmljZToKICAgIHBvcnRzOgogICAgICBwb3N0Z3Jlc3FsOiA1NDMy",
"target_platform": {
"target_platform_id": "{VIB_ENV_TARGET_PLATFORM}",
"size": {
"name": "S4"
}
}
},
"actions": [
{
"action_id": "health-check",
"params": {
"endpoint": "lb-jupyterhub-proxy-public-http",
"app_protocol": "HTTP"
}
},
{
"action_id": "goss",
"params": {
"resources": {
"path": "/.vib/jupyterhub/goss"
},
"remote": {
"workload": "deploy-jupyterhub-hub"
},
"vars_file": "vars.yaml"
}
},
{
"action_id": "cypress",
"params": {
"resources": {
"path": "/.vib/jupyterhub/cypress"
},
"endpoint": "lb-jupyterhub-proxy-public-http",
"app_protocol": "HTTP",
"env": {
"username": "test_user",
"password": "ComplicatedPassword123!4"
}
}
}
]
},
"publish": {
"actions": [
{

View File

@@ -15,6 +15,56 @@
"action_id": "helm-lint"
}
]
},
"verify": {
"context": {
"resources": {
"url": "{SHA_ARCHIVE}",
"path": "/bitnami/jupyterhub"
},
"runtime_parameters": "aHViOgogIGJhc2VVcmw6IC8KICBhZG1pblVzZXI6IHRlc3RfdXNlcgogIHBhc3N3b3JkOiBDb21wbGljYXRlZFBhc3N3b3JkMTIzITQKICBjb250YWluZXJQb3J0czoKICAgIGh0dHA6IDgwODIKICBjb250YWluZXJTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBydW5Bc1VzZXI6IDEwMDIKICBwb2RTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBmc0dyb3VwOiAxMDAyCiAgc2VydmljZUFjY291bnQ6CiAgICBjcmVhdGU6IHRydWUKICAgIGF1dG9tb3VudFNlcnZpY2VBY2NvdW50VG9rZW46IHRydWUKICByYmFjOgogICAgY3JlYXRlOiB0cnVlCiAgc2VydmljZToKICAgIHBvcnRzOgogICAgICBodHRwOiA4MDgyCnByb3h5OgogIHNlcnZpY2U6CiAgICBhcGk6CiAgICAgIHBvcnRzOgogICAgICAgIGh0dHA6IDgwMDAKICAgIHB1YmxpYzoKICAgICAgdHlwZTogTG9hZEJhbGFuY2VyCiAgICAgIHBvcnRzOgogICAgICAgIGh0dHA6IDgwCmltYWdlUHVsbGVyOgogIGVuYWJsZWQ6IHRydWUKc2luZ2xldXNlcjoKICBjb250YWluZXJTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBydW5Bc1VzZXI6IDEwMDIKICBwb2RTZWN1cml0eUNvbnRleHQ6CiAgICBlbmFibGVkOiB0cnVlCiAgICBmc0dyb3VwOiAxMDAyCiAgcGVyc2lzdGVuY2U6CiAgICBlbmFibGVkOiB0cnVlCnBvc3RncmVzcWw6CiAgZW5hYmxlZDogdHJ1ZQogIGF1dGg6CiAgICB1c2VybmFtZTogYm5fdmliX2p1cHl0ZXJodWIKICAgIGRhdGFiYXNlOiBiaXRuYW1pX3ZpYl9qdXB5dGVyaHViCiAgc2VydmljZToKICAgIHBvcnRzOgogICAgICBwb3N0Z3Jlc3FsOiA1NDMy",
"target_platform": {
"target_platform_id": "{VIB_ENV_TARGET_PLATFORM}",
"size": {
"name": "S4"
}
}
},
"actions": [
{
"action_id": "health-check",
"params": {
"endpoint": "lb-jupyterhub-proxy-public-http",
"app_protocol": "HTTP"
}
},
{
"action_id": "goss",
"params": {
"resources": {
"path": "/.vib/jupyterhub/goss"
},
"remote": {
"workload": "deploy-jupyterhub-hub"
},
"vars_file": "vars.yaml"
}
},
{
"action_id": "cypress",
"params": {
"resources": {
"path": "/.vib/jupyterhub/cypress"
},
"endpoint": "lb-jupyterhub-proxy-public-http",
"app_protocol": "HTTP",
"env": {
"username": "test_user",
"password": "ComplicatedPassword123!4"
}
}
}
]
}
}
}