From 1d39e4d918c78eaf618cc06c67a2d1b5abee2405 Mon Sep 17 00:00:00 2001 From: Tsu-ba-me Date: Wed, 22 Jun 2022 16:47:05 -0400 Subject: [PATCH] fix(striker-ui-api): use separate fifo for each server screenshot request and read all data chunks --- striker-ui-api/src/lib/consts/SERVER_PATHS.ts | 1 + .../server/getServerDetail.ts | 58 +++++++++++++------ 2 files changed, 42 insertions(+), 17 deletions(-) diff --git a/striker-ui-api/src/lib/consts/SERVER_PATHS.ts b/striker-ui-api/src/lib/consts/SERVER_PATHS.ts index dea1f4d1..882fdf0f 100644 --- a/striker-ui-api/src/lib/consts/SERVER_PATHS.ts +++ b/striker-ui-api/src/lib/consts/SERVER_PATHS.ts @@ -10,6 +10,7 @@ const EMPTY_SERVER_PATHS: ServerPath = { usr: { bin: { mkfifo: {}, + rm: {}, sed: {}, }, sbin: { diff --git a/striker-ui-api/src/lib/request_handlers/server/getServerDetail.ts b/striker-ui-api/src/lib/request_handlers/server/getServerDetail.ts index f98973ac..bda5981b 100644 --- a/striker-ui-api/src/lib/request_handlers/server/getServerDetail.ts +++ b/striker-ui-api/src/lib/request_handlers/server/getServerDetail.ts @@ -1,24 +1,27 @@ import assert from 'assert'; import { RequestHandler } from 'express'; -import { createReadStream, existsSync, rmSync, statSync } from 'fs'; +import { createReadStream } from 'fs'; import path from 'path'; import { REP_UUID } from '../../consts/REG_EXP_PATTERNS'; import SERVER_PATHS from '../../consts/SERVER_PATHS'; import { dbQuery, sub } from '../../accessModule'; -import { mkfifo } from '../../mkfifo'; import { sanitizeQS } from '../../sanitizeQS'; +import { mkfifo, rm } from '../../shell'; export const getServerDetail: RequestHandler = (request, response) => { const { serverUUID } = request.params; const { ss, resize } = request.query; + const epoch = Date.now(); const isScreenshot = sanitizeQS(ss, { returnType: 'boolean', }); - console.log(`serverUUID=[${serverUUID}],isScreenshot=[${isScreenshot}]`); + console.log( + `serverUUID=[${serverUUID}],epoch=[${epoch}],isScreenshot=[${isScreenshot}]`, + ); try { assert( @@ -67,27 +70,47 @@ export const getServerDetail: RequestHandler = (request, response) => { console.log(`serverHostUUID=[${serverHostUUID}]`); - const imageFileName = `${serverUUID}_screenshot`; + const imageFileName = `${serverUUID}_screenshot_${epoch}`; const imageFilePath = path.join(SERVER_PATHS.tmp.self, imageFileName); try { - if (existsSync(imageFilePath)) { - if (!statSync(imageFilePath).isFIFO()) { - rmSync(imageFilePath); - mkfifo(imageFilePath); - } - } else { - mkfifo(imageFilePath); - } + mkfifo(imageFilePath); const namedPipeReadStream = createReadStream(imageFilePath, { + autoClose: true, encoding: 'utf-8', }); - namedPipeReadStream.once('data', (data) => { - response.status(200).send({ screenshot: data.toString().trim() }); + let imageData = ''; + + namedPipeReadStream.once('close', () => { + console.log(`On close; removing named pipe at ${imageFilePath}.`); + + try { + rm(imageFilePath); + } catch (cleanPipeError) { + console.log( + `Failed to clean up named pipe; CAUSE: ${cleanPipeError}`, + ); + } + }); + + namedPipeReadStream.once('end', () => { + response.status(200).send({ screenshot: imageData }); + }); + + namedPipeReadStream.on('data', (data) => { + const imageChunk = data.toString().trim(); + const chunkLogLength = 10; + + console.log( + `${serverUUID} image chunk: ${imageChunk.substring( + 0, + chunkLogLength, + )}...${imageChunk.substring(imageChunk.length - chunkLogLength - 1)}`, + ); - namedPipeReadStream.close(); + imageData += imageChunk; }); } catch (prepPipeError) { console.log(`Failed to prepare named pipe; CAUSE: ${prepPipeError}`); @@ -114,8 +137,9 @@ export const getServerDetail: RequestHandler = (request, response) => { SERVER_PATHS.usr.sbin['anvil-get-server-screenshot'].self, job_data: `server-uuid=${serverUUID} request-host-uuid=${requestHostUUID} -resize=${resizeArgs}`, - job_name: `get_server_screenshot::${serverUUID}`, +resize=${resizeArgs} +out-file-id=${epoch}`, + job_name: `get_server_screenshot::${serverUUID}::${epoch}`, job_title: 'job_0356', job_description: 'job_0357', job_progress: 0,