mirror of
https://github.com/elastic/kibana.git
synced 2025-04-23 17:28:26 -04:00
[8.12] Updates test file wrapper to deterministically detect file write completion (#176115) (#176161)
# Backport This will backport the following commits from `main` to `8.12`: - [Updates test file wrapper to deterministically detect file write completion (#176115)](https://github.com/elastic/kibana/pull/176115) <!--- Backport version: 9.4.3 --> ### Questions ? Please refer to the [Backport tool documentation](https://github.com/sqren/backport) <!--BACKPORT [{"author":{"name":"Jeramy Soucy","email":"jeramy.soucy@elastic.co"},"sourceCommit":{"committedDate":"2024-02-02T14:57:37Z","message":"Updates test file wrapper to deterministically detect file write completion (#176115)\n\nCloses #119267\r\n\r\n## Summary\r\n\r\nAttempts to deterministically detect when a file is written in entirety\r\nin order to resolve flaky test issues where parsed JSON is incomplete.\r\n\r\nFlaky Test Runner:\r\nhttps://buildkite.com/elastic/kibana-flaky-test-suite-runner/builds/5015","sha":"f9125ba079aeaa31fcd07e442cf6789c344452ec","branchLabelMapping":{"^v8.13.0$":"main","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["Team:Security","release_note:skip","backport:all-open","v8.13.0"],"title":"Updates test file wrapper to deterministically detect file write completion","number":176115,"url":"https://github.com/elastic/kibana/pull/176115","mergeCommit":{"message":"Updates test file wrapper to deterministically detect file write completion (#176115)\n\nCloses #119267\r\n\r\n## Summary\r\n\r\nAttempts to deterministically detect when a file is written in entirety\r\nin order to resolve flaky test issues where parsed JSON is incomplete.\r\n\r\nFlaky Test Runner:\r\nhttps://buildkite.com/elastic/kibana-flaky-test-suite-runner/builds/5015","sha":"f9125ba079aeaa31fcd07e442cf6789c344452ec"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v8.13.0","branchLabelMappingKey":"^v8.13.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/176115","number":176115,"mergeCommit":{"message":"Updates test file wrapper to deterministically detect file write completion (#176115)\n\nCloses #119267\r\n\r\n## Summary\r\n\r\nAttempts to deterministically detect when a file is written in entirety\r\nin order to resolve flaky test issues where parsed JSON is incomplete.\r\n\r\nFlaky Test Runner:\r\nhttps://buildkite.com/elastic/kibana-flaky-test-suite-runner/builds/5015","sha":"f9125ba079aeaa31fcd07e442cf6789c344452ec"}}]}] BACKPORT--> Co-authored-by: Jeramy Soucy <jeramy.soucy@elastic.co>
This commit is contained in:
parent
8bff5996f2
commit
0e7f0277d8
8 changed files with 26 additions and 18 deletions
|
@ -245,7 +245,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.set('Cookie', sessionCookie.cookieString())
|
||||
.expect(302);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(2);
|
||||
|
|
|
@ -25,7 +25,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
|
||||
it('logs audit events when reading and writing saved objects', async () => {
|
||||
await supertest.get('/audit_log?query=param').set('kbn-xsrf', 'foo').expect(204);
|
||||
await retry.waitFor('logs event in the dest file', async () => await logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const content = await logFile.readJSON();
|
||||
|
||||
const httpEvent = content.find((c) => c.event.action === 'http_request');
|
||||
|
@ -68,7 +68,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
params: { username, password },
|
||||
})
|
||||
.expect(200);
|
||||
await retry.waitFor('logs event in the dest file', async () => await logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const content = await logFile.readJSON();
|
||||
|
||||
const loginEvent = content.find((c) => c.event.action === 'user_login');
|
||||
|
@ -92,7 +92,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
params: { username, password: 'invalid_password' },
|
||||
})
|
||||
.expect(401);
|
||||
await retry.waitFor('logs event in the dest file', async () => await logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const content = await logFile.readJSON();
|
||||
|
||||
const loginEvent = content.find((c) => c.event.action === 'user_login');
|
||||
|
|
|
@ -9,6 +9,8 @@ import Fs from 'fs';
|
|||
import type { RetryService } from '@kbn/ftr-common-functional-services';
|
||||
|
||||
export class FileWrapper {
|
||||
delay = (ms: number) => new Promise((resolve) => setTimeout(resolve, ms));
|
||||
|
||||
constructor(private readonly path: string, private readonly retry: RetryService) {}
|
||||
async reset() {
|
||||
// "touch" each file to ensure it exists and is empty before each test
|
||||
|
@ -32,9 +34,15 @@ export class FileWrapper {
|
|||
});
|
||||
}
|
||||
// writing in a file is an async operation. we use this method to make sure logs have been written.
|
||||
async isNotEmpty() {
|
||||
const content = await this.read();
|
||||
const line = content[0];
|
||||
return line.length > 0;
|
||||
async isWritten() {
|
||||
// attempt at determinism - wait for the size of the file to stop changing.
|
||||
await this.retry.waitForWithTimeout(`file '${this.path}' to be written`, 5000, async () => {
|
||||
const sizeBefore = Fs.statSync(this.path).size;
|
||||
await this.delay(500);
|
||||
const sizeAfter = Fs.statSync(this.path).size;
|
||||
return sizeAfter === sizeBefore;
|
||||
});
|
||||
|
||||
return Fs.statSync(this.path).size > 0;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -519,7 +519,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.set('Cookie', sessionCookie.cookieString())
|
||||
.expect(302);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(2);
|
||||
|
@ -545,7 +545,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.set('Authorization', `Negotiate ${Buffer.from('Hello').toString('base64')}`)
|
||||
.expect(401);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(1);
|
||||
|
|
|
@ -714,7 +714,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.set('Cookie', sessionCookie.cookieString())
|
||||
.expect(302);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(2);
|
||||
|
@ -739,7 +739,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.get(`/api/security/oidc/callback?code=thisisthecode&state=someothervalue`)
|
||||
.expect(401);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(1);
|
||||
|
|
|
@ -505,7 +505,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.set('Cookie', sessionCookie.cookieString())
|
||||
.expect(302);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(2);
|
||||
|
@ -528,7 +528,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
it('should log authentication failure correctly', async () => {
|
||||
await supertest.get('/security/account').ca(CA_CERT).pfx(UNTRUSTED_CLIENT_CERT).expect(401);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(1);
|
||||
|
|
|
@ -843,7 +843,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.set('Cookie', sessionCookie.cookieString())
|
||||
.expect(302);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(2);
|
||||
|
@ -881,7 +881,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
})
|
||||
.expect(401);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(1);
|
||||
|
|
|
@ -53,7 +53,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
.set('Cookie', sessionCookie.cookieString())
|
||||
.expect(302);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(2);
|
||||
|
@ -85,7 +85,7 @@ export default function ({ getService }: FtrProviderContext) {
|
|||
})
|
||||
.expect(401);
|
||||
|
||||
await retry.waitFor('audit events in dest file', () => logFile.isNotEmpty());
|
||||
await logFile.isWritten();
|
||||
const auditEvents = await logFile.readJSON();
|
||||
|
||||
expect(auditEvents).to.have.length(1);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue