-
Notifications
You must be signed in to change notification settings - Fork 8.3k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[Reporting/Test] move functional tests to apps (#64368)
* Squashed commit of the following: commit 5953089c03bea6b2d091f7723fea25bb1c210ee8 Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 18:29:55 2020 -0700 move tests to apps commit 39adeaae6d3502d2c6da4e6111c2a396f2a7aedb Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 17:49:20 2020 -0700 update archive with better dashboard commit 55b600748356c1adc5e75669b0c5588a812e401d Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 17:16:53 2020 -0700 fix the refactoring bugs commit 11aff10cd8009aeb9bb78aa5ce0b37a72d47776e Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 17:16:28 2020 -0700 remove unused fixtuers commit 05c33817c8eb67c461ac012cf2f71a9c01f1a91e Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 16:37:36 2020 -0700 Start of refactoring commit b63c182b5f32b19dc3ca715efdbc5f18fcc02f67 Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 16:32:50 2020 -0700 Todo comments commit 1e0105e Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 14:31:58 2020 -0700 revert unrelated change commit 206fd14 Merge: 0d4c2ad 8343064 Author: Timothy Sullivan <tsullivan@elastic.co> Date: Thu Apr 9 14:28:45 2020 -0700 Merge branch 'master' into reporting/test-better commit 0d4c2ad Author: Timothy Sullivan <tsullivan@elastic.co> Date: Wed Apr 8 10:41:19 2020 -0700 fix ts commit 890128c Merge: d9ce402 3598b8c Author: Timothy Sullivan <tsullivan@elastic.co> Date: Wed Apr 8 10:31:09 2020 -0700 Merge branch 'master' into reporting/test-better commit d9ce402 Author: Timothy Sullivan <tsullivan@elastic.co> Date: Tue Apr 7 08:31:58 2020 -0700 [Reporting] convert all server unit tests to TypeScript * fix imports and readmes * remove not-needed readme * remove extra info from readme * correct some comments * log the error that was caught * fix config path in readme * fix readme instructions to point to updated paths Co-authored-by: Elastic Machine <elasticmachine@users.noreply.github.com>
- Loading branch information
1 parent
4e714c2
commit 4c460b8
Showing
16 changed files
with
298 additions
and
466 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
## The Dashboard Reporting Tests | ||
|
||
### Baseline snapshots | ||
|
||
The reporting tests create a few PNG reports and do a snapshot comparison against stored baselines. The baseline images are stored in `./reports/baseline`. | ||
|
||
### Updating the baselines | ||
|
||
Every now and then visual changes will be made that will require the snapshots to be updated. This is how you go about updating it. | ||
|
||
1. **Load the ES Archive containing the dashboard and data.** | ||
This will load the test data into an Elasticsearch instance running via the functional test server: | ||
``` | ||
node scripts/es_archiver load reporting/ecommerce --config=x-pack/test/functional/config.js | ||
node scripts/es_archiver load reporting/ecommerce_kibana --config=x-pack/test/functional/config.js | ||
``` | ||
2. **Generate the reports of the E-commerce dashboard in the Kibana UI.** | ||
Navigate to `http://localhost:5620`, find the archived dashboard, and generate all the types of reports for which there are stored baseline images. | ||
3. **Download the reports, and save them into the `reports/baseline` folder.** | ||
Change the names of the PNG/PDF files to overwrite the stored baselines. | ||
|
||
The next time functional tests run, the generated reports will be compared to the latest image that you have saved :bowtie: |
126 changes: 126 additions & 0 deletions
126
x-pack/test/functional/apps/dashboard/reporting/index.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,126 @@ | ||
/* | ||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one | ||
* or more contributor license agreements. Licensed under the Elastic License; | ||
* you may not use this file except in compliance with the Elastic License. | ||
*/ | ||
|
||
import expect from '@kbn/expect'; | ||
import path from 'path'; | ||
import fs from 'fs'; | ||
import { promisify } from 'util'; | ||
import { checkIfPngsMatch } from './lib/compare_pngs'; | ||
|
||
const writeFileAsync = promisify(fs.writeFile); | ||
const mkdirAsync = promisify(fs.mkdir); | ||
|
||
const REPORTS_FOLDER = path.resolve(__dirname, 'reports'); | ||
|
||
export default function({ getService, getPageObjects }) { | ||
const esArchiver = getService('esArchiver'); | ||
const browser = getService('browser'); | ||
const log = getService('log'); | ||
const config = getService('config'); | ||
const PageObjects = getPageObjects(['reporting', 'common', 'dashboard']); | ||
|
||
describe('Reporting', () => { | ||
before('initialize tests', async () => { | ||
log.debug('ReportingPage:initTests'); | ||
await esArchiver.loadIfNeeded('reporting/ecommerce'); | ||
await esArchiver.loadIfNeeded('reporting/ecommerce_kibana'); | ||
await browser.setWindowSize(1600, 850); | ||
}); | ||
after('clean up archives', async () => { | ||
await esArchiver.unload('reporting/ecommerce'); | ||
await esArchiver.unload('reporting/ecommerce_kibana'); | ||
}); | ||
|
||
describe('Print PDF button', () => { | ||
it('is not available if new', async () => { | ||
await PageObjects.common.navigateToApp('dashboard'); | ||
await PageObjects.dashboard.clickNewDashboard(); | ||
await PageObjects.reporting.openPdfReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be('true'); | ||
}); | ||
|
||
it('becomes available when saved', async () => { | ||
await PageObjects.dashboard.saveDashboard('My PDF Dashboard'); | ||
await PageObjects.reporting.openPdfReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be(null); | ||
}); | ||
}); | ||
|
||
describe('Print Layout', () => { | ||
it('downloads a PDF file', async function() { | ||
// Generating and then comparing reports can take longer than the default 60s timeout because the comparePngs | ||
// function is taking about 15 seconds per comparison in jenkins. | ||
this.timeout(300000); | ||
await PageObjects.common.navigateToApp('dashboard'); | ||
await PageObjects.dashboard.loadSavedDashboard('Ecom Dashboard'); | ||
await PageObjects.reporting.openPdfReportingPanel(); | ||
await PageObjects.reporting.checkUsePrintLayout(); | ||
await PageObjects.reporting.clickGenerateReportButton(); | ||
|
||
const url = await PageObjects.reporting.getReportURL(60000); | ||
const res = await PageObjects.reporting.getResponse(url); | ||
|
||
expect(res.statusCode).to.equal(200); | ||
expect(res.headers['content-type']).to.equal('application/pdf'); | ||
}); | ||
}); | ||
|
||
describe('Print PNG button', () => { | ||
it('is not available if new', async () => { | ||
await PageObjects.common.navigateToApp('dashboard'); | ||
await PageObjects.dashboard.clickNewDashboard(); | ||
await PageObjects.reporting.openPngReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be('true'); | ||
}); | ||
|
||
it('becomes available when saved', async () => { | ||
await PageObjects.dashboard.saveDashboard('My PNG Dash'); | ||
await PageObjects.reporting.openPngReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be(null); | ||
}); | ||
}); | ||
|
||
describe('Preserve Layout', () => { | ||
it('matches baseline report', async function() { | ||
const writeSessionReport = async (name, rawPdf, reportExt) => { | ||
const sessionDirectory = path.resolve(REPORTS_FOLDER, 'session'); | ||
await mkdirAsync(sessionDirectory, { recursive: true }); | ||
const sessionReportPath = path.resolve(sessionDirectory, `${name}.${reportExt}`); | ||
await writeFileAsync(sessionReportPath, rawPdf); | ||
return sessionReportPath; | ||
}; | ||
const getBaselineReportPath = (fileName, reportExt) => { | ||
const baselineFolder = path.resolve(REPORTS_FOLDER, 'baseline'); | ||
const fullPath = path.resolve(baselineFolder, `${fileName}.${reportExt}`); | ||
log.debug(`getBaselineReportPath (${fullPath})`); | ||
return fullPath; | ||
}; | ||
|
||
this.timeout(300000); | ||
|
||
await PageObjects.common.navigateToApp('dashboard'); | ||
await PageObjects.dashboard.loadSavedDashboard('Ecom Dashboard'); | ||
await PageObjects.reporting.openPngReportingPanel(); | ||
await PageObjects.reporting.forceSharedItemsContainerSize({ width: 1405 }); | ||
await PageObjects.reporting.clickGenerateReportButton(); | ||
await PageObjects.reporting.removeForceSharedItemsContainerSize(); | ||
|
||
const url = await PageObjects.reporting.getReportURL(60000); | ||
const reportData = await PageObjects.reporting.getRawPdfReportData(url); | ||
const reportFileName = 'dashboard_preserve_layout'; | ||
const sessionReportPath = await writeSessionReport(reportFileName, reportData, 'png'); | ||
const percentSimilar = await checkIfPngsMatch( | ||
sessionReportPath, | ||
getBaselineReportPath(reportFileName, 'png'), | ||
config.get('screenshots.directory'), | ||
log | ||
); | ||
|
||
expect(percentSimilar).to.be.lessThan(0.1); | ||
}); | ||
}); | ||
}); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
File renamed without changes
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,75 @@ | ||
/* | ||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one | ||
* or more contributor license agreements. Licensed under the Elastic License; | ||
* you may not use this file except in compliance with the Elastic License. | ||
*/ | ||
|
||
import expect from '@kbn/expect'; | ||
|
||
export default function({ getService, getPageObjects }) { | ||
const log = getService('log'); | ||
const esArchiver = getService('esArchiver'); | ||
const browser = getService('browser'); | ||
const PageObjects = getPageObjects(['reporting', 'common', 'discover']); | ||
const filterBar = getService('filterBar'); | ||
|
||
describe('Discover', () => { | ||
before('initialize tests', async () => { | ||
log.debug('ReportingPage:initTests'); | ||
await esArchiver.loadIfNeeded('reporting/ecommerce'); | ||
await browser.setWindowSize(1600, 850); | ||
}); | ||
after('clean up archives', async () => { | ||
await esArchiver.unload('reporting/ecommerce'); | ||
}); | ||
|
||
describe('Generate CSV button', () => { | ||
beforeEach(() => PageObjects.common.navigateToApp('discover')); | ||
|
||
it('is not available if new', async () => { | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be('true'); | ||
}); | ||
|
||
it('becomes available when saved', async () => { | ||
await PageObjects.discover.saveSearch('my search - expectEnabledGenerateReportButton'); | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be(null); | ||
}); | ||
|
||
it('becomes available/not available when a saved search is created, changed and saved again', async () => { | ||
// create new search, csv export is not available | ||
await PageObjects.discover.clickNewSearchButton(); | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be('true'); | ||
// save search, csv export is available | ||
await PageObjects.discover.saveSearch('my search - expectEnabledGenerateReportButton 2'); | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be(null); | ||
// add filter, csv export is not available | ||
await filterBar.addFilter('currency', 'is', 'EUR'); | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be('true'); | ||
// save search again, csv export is available | ||
await PageObjects.discover.saveSearch('my search - expectEnabledGenerateReportButton 2'); | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be(null); | ||
}); | ||
|
||
it('generates a report with data', async () => { | ||
await PageObjects.discover.clickNewSearchButton(); | ||
await PageObjects.reporting.setTimepickerInDataRange(); | ||
await PageObjects.discover.saveSearch('my search - with data - expectReportCanBeCreated'); | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.canReportBeCreated()).to.be(true); | ||
}); | ||
|
||
it('generates a report with no data', async () => { | ||
await PageObjects.reporting.setTimepickerInNoDataRange(); | ||
await PageObjects.discover.saveSearch('my search - no data - expectReportCanBeCreated'); | ||
await PageObjects.reporting.openCsvReportingPanel(); | ||
expect(await PageObjects.reporting.canReportBeCreated()).to.be(true); | ||
}); | ||
}); | ||
}); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,69 @@ | ||
/* | ||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one | ||
* or more contributor license agreements. Licensed under the Elastic License; | ||
* you may not use this file except in compliance with the Elastic License. | ||
*/ | ||
|
||
import expect from '@kbn/expect'; | ||
|
||
export default function({ getService, getPageObjects }) { | ||
const esArchiver = getService('esArchiver'); | ||
const browser = getService('browser'); | ||
const log = getService('log'); | ||
const PageObjects = getPageObjects([ | ||
'reporting', | ||
'common', | ||
'dashboard', | ||
'visualize', | ||
'visEditor', | ||
]); | ||
|
||
describe('Visualize', () => { | ||
before('initialize tests', async () => { | ||
log.debug('ReportingPage:initTests'); | ||
await esArchiver.loadIfNeeded('reporting/ecommerce'); | ||
await esArchiver.loadIfNeeded('reporting/ecommerce_kibana'); | ||
await browser.setWindowSize(1600, 850); | ||
}); | ||
after('clean up archives', async () => { | ||
await esArchiver.unload('reporting/ecommerce'); | ||
await esArchiver.unload('reporting/ecommerce_kibana'); | ||
}); | ||
|
||
describe('Print PDF button', () => { | ||
it('is not available if new', async () => { | ||
await PageObjects.common.navigateToUrl('visualize', 'new'); | ||
await PageObjects.visualize.clickAreaChart(); | ||
await PageObjects.visualize.clickNewSearch('ecommerce'); | ||
await PageObjects.reporting.openPdfReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be('true'); | ||
}); | ||
|
||
it('becomes available when saved', async () => { | ||
await PageObjects.reporting.setTimepickerInDataRange(); | ||
await PageObjects.visEditor.clickBucket('X-axis'); | ||
await PageObjects.visEditor.selectAggregation('Date Histogram'); | ||
await PageObjects.visEditor.clickGo(); | ||
await PageObjects.visualize.saveVisualization('my viz'); | ||
await PageObjects.reporting.openPdfReportingPanel(); | ||
expect(await PageObjects.reporting.isGenerateReportButtonDisabled()).to.be(null); | ||
}); | ||
|
||
it('downloaded PDF has OK status', async function() { | ||
// Generating and then comparing reports can take longer than the default 60s timeout | ||
this.timeout(180000); | ||
|
||
await PageObjects.common.navigateToApp('dashboard'); | ||
await PageObjects.dashboard.loadSavedDashboard('Ecom Dashboard'); | ||
await PageObjects.reporting.openPdfReportingPanel(); | ||
await PageObjects.reporting.clickGenerateReportButton(); | ||
|
||
const url = await PageObjects.reporting.getReportURL(60000); | ||
const res = await PageObjects.reporting.getResponse(url); | ||
|
||
expect(res.statusCode).to.equal(200); | ||
expect(res.headers['content-type']).to.equal('application/pdf'); | ||
}); | ||
}); | ||
}); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.