More screenshots link (#289)

* More screenshots link

* bugfix: wip

* cicd: Test flakey tests

* cicd: more tests

* cicd: more tests

* cicd: Try a 10s timeout

* cicd: Better debugging of process start / stop

* cicd: Better debugging of process start / stop

* cicd: Possibly unflaky tests
This commit is contained in:
James Read 2024-04-23 21:54:54 +01:00 committed by GitHub
parent 7c6f36c600
commit a3aee3603f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
8 changed files with 78 additions and 29 deletions

View File

@ -12,6 +12,7 @@ OliveTin gives **safe** and **simple** access to predefined shell commands from
[![Build Snapshot](https://github.com/OliveTin/OliveTin/actions/workflows/build-snapshot.yml/badge.svg)](https://github.com/OliveTin/OliveTin/actions/workflows/build-snapshot.yml) [![Build Snapshot](https://github.com/OliveTin/OliveTin/actions/workflows/build-snapshot.yml/badge.svg)](https://github.com/OliveTin/OliveTin/actions/workflows/build-snapshot.yml)
<img alt = "screenshot" src = "https://github.com/OliveTin/OliveTin/blob/main/var/marketing/screenshotDesktop.png" /> <img alt = "screenshot" src = "https://github.com/OliveTin/OliveTin/blob/main/var/marketing/screenshotDesktop.png" />
<a href = "#screenshots">More screenshots below</a>
## Use cases ## Use cases

View File

@ -1,6 +1,10 @@
default: default: test-install test-run
test-install:
npm install --no-fund npm install --no-fund
./node_modules/.bin/mocha -t 5000
test-run:
./node_modules/.bin/mocha -t 10000
nginx: nginx:
podman-compose up -d nginx podman-compose up -d nginx

View File

@ -1,5 +1,6 @@
import { By } from 'selenium-webdriver' import { By } from 'selenium-webdriver'
import fs from 'fs' import fs from 'fs'
import { Condition } from 'selenium-webdriver'
export async function getActionButtons (webdriver) { export async function getActionButtons (webdriver) {
return await webdriver.findElement(By.id('contentActions')).findElements(By.tagName('button')) return await webdriver.findElement(By.id('contentActions')).findElements(By.tagName('button'))
@ -10,3 +11,17 @@ export function takeScreenshot (webdriver) {
fs.writeFileSync('out.png', img, 'base64') fs.writeFileSync('out.png', img, 'base64')
}) })
} }
export async function getRootAndWait() {
await webdriver.get(runner.baseUrl())
await webdriver.wait(new Condition('wait for initial-marshal-complete', async function() {
const body = await webdriver.findElement(By.tagName('body'))
const attr = await body.getAttribute('initial-marshal-complete')
if (attr == 'true') {
return true
} else {
return false
}
}))
}

View File

@ -29,40 +29,57 @@ class OliveTinTestRunner {
class OliveTinTestRunnerStartLocalProcess extends OliveTinTestRunner { class OliveTinTestRunnerStartLocalProcess extends OliveTinTestRunner {
async start (cfg) { async start (cfg) {
let stdout = ""
let stderr = ""
this.ot = spawn('./../OliveTin', ['-configdir', 'configs/' + cfg + '/']) this.ot = spawn('./../OliveTin', ['-configdir', 'configs/' + cfg + '/'])
const logStdout = process.env.OLIVETIN_TEST_RUNNER_LOG_STDOUT === '1' const logStdout = process.env.OLIVETIN_TEST_RUNNER_LOG_STDOUT === '1'
if (logStdout) { this.ot.stdout.on('data', (data) => {
this.ot.stdout.on('data', (data) => { stdout += data
if (logStdout) {
console.log(`stdout: ${data}`) console.log(`stdout: ${data}`)
})
this.ot.stderr.on('data', (data) => {
console.error(`stderr: ${data}`)
})
}
this.ot.on('close', (code) => {
if (code != null) {
console.log(`child process exited with code ${code}`)
} }
}) })
/* this.ot.stderr.on('data', (data) => {
this.server = await startSomeServer({port: process.env.TEST_PORT}); stderr += data
console.log(`server running on port ${this.server.port}`);
*/
this.BASE_URL = 'http://localhost:1337/' if (logStdout) {
console.log(`stderr: ${data}`)
await waitOn({ }
resources: [this.BASE_URL]
}) })
this.ot.on('close', (code) => {
if (code != null) {
console.log(`OliveTin local process exited with code ${code}`)
console.log(stdout)
console.log(stderr)
console.log(this.ot.exitCode)
}
})
if (this.ot.exitCode == null) {
this.BASE_URL = 'http://localhost:1337/'
await waitOn({
resources: [this.BASE_URL]
})
console.log(" OliveTin local process started and webUI accessible")
} else {
console.log(" OliveTin local process start FAILED!")
console.log(stdout)
console.log(stderr)
console.log(this.ot.exitCode)
}
} }
async stop () { async stop () {
await this.ot.kill() await this.ot.kill()
console.log(" OliveTin local process killed")
} }
} }

View File

@ -1,7 +1,7 @@
import { describe, it, before, after } from 'mocha' import { describe, it, before, after } from 'mocha'
import { expect } from 'chai' import { expect } from 'chai'
import { By, until } from 'selenium-webdriver' import { By, until } from 'selenium-webdriver'
import { takeScreenshot } from '../lib/elements.js' import { getRootAndWait, takeScreenshot } from '../lib/elements.js'
describe('config: entities', function () { describe('config: entities', function () {
before(async function () { before(async function () {
@ -13,7 +13,7 @@ describe('config: entities', function () {
}) })
it('Entity buttons are rendered', async function() { it('Entity buttons are rendered', async function() {
webdriver.get(runner.baseUrl()) await getRootAndWait()
const buttons = await webdriver.findElement(By.id('root-group')).findElements(By.tagName('button')) const buttons = await webdriver.findElement(By.id('root-group')).findElements(By.tagName('button'))
expect(buttons).to.not.be.null expect(buttons).to.not.be.null

View File

@ -1,7 +1,8 @@
import { describe, it, before, after } from 'mocha' import { describe, it, before, after } from 'mocha'
import { expect } from 'chai' import { expect } from 'chai'
import { By } from 'selenium-webdriver' import { By, until, Condition } from 'selenium-webdriver'
//import * as waitOn from 'wait-on' //import * as waitOn from 'wait-on'
import { getRootAndWait } from '../lib/elements.js'
describe('config: general', function () { describe('config: general', function () {
before(async function () { before(async function () {
@ -19,6 +20,16 @@ describe('config: general', function () {
expect(title).to.be.equal("OliveTin") expect(title).to.be.equal("OliveTin")
}) })
it('Page title2', async function () {
/*
await webdriver.get(runner.baseUrl())
const title = await webdriver.getTitle()
expect(title).to.be.equal("OliveTin")
*/
})
it('Footer contains promo', async function () { it('Footer contains promo', async function () {
const ftr = await webdriver.findElement(By.tagName('footer')).getText() const ftr = await webdriver.findElement(By.tagName('footer')).getText()
@ -26,7 +37,7 @@ describe('config: general', function () {
}) })
it('Default buttons are rendered', async function() { it('Default buttons are rendered', async function() {
await webdriver.get(runner.baseUrl()) await getRootAndWait()
const buttons = await webdriver.findElement(By.id('root-group')).findElements(By.tagName('button')) const buttons = await webdriver.findElement(By.id('root-group')).findElements(By.tagName('button'))
@ -34,7 +45,7 @@ describe('config: general', function () {
}) })
it('Start date action (popup)', async function() { it('Start date action (popup)', async function() {
await webdriver.get(runner.baseUrl()) await getRootAndWait()
const buttons = await webdriver.findElements(By.css('[title="date-popup"]')) const buttons = await webdriver.findElements(By.css('[title="date-popup"]'))

View File

@ -1,7 +1,7 @@
import { describe, it, before, after } from 'mocha' import { describe, it, before, after } from 'mocha'
import { expect } from 'chai' import { expect } from 'chai'
import { By, until } from 'selenium-webdriver' import { By, until } from 'selenium-webdriver'
import { getActionButtons } from '../lib/elements.js' import { getActionButtons, getRootAndWait } from '../lib/elements.js'
describe('config: multipleDropdowns', function () { describe('config: multipleDropdowns', function () {
before(async function () { before(async function () {
@ -13,7 +13,7 @@ describe('config: multipleDropdowns', function () {
}) })
it('Multiple dropdowns are possible', async function() { it('Multiple dropdowns are possible', async function() {
await webdriver.get(runner.baseUrl()) await getRootAndWait()
const buttons = await getActionButtons(webdriver) const buttons = await getActionButtons(webdriver)

View File

@ -20,6 +20,7 @@ export function marshalDashboardComponentsJsonToHtml (json) {
marshalDashboardStructureToHtml(json) marshalDashboardStructureToHtml(json)
document.getElementById('username').innerText = json.authenticatedUser document.getElementById('username').innerText = json.authenticatedUser
document.body.setAttribute('initial-marshal-complete', 'true')
changeDirectory(null) changeDirectory(null)
} }