From 91efa5ab51904667eaf3353008753ea99bf5b17d Mon Sep 17 00:00:00 2001 From: Kevin J Hoerr Date: Thu, 12 Dec 2019 14:30:58 -0500 Subject: [PATCH] Simplify and generalize template processing "For the unit tests. For the unit tests!" --- example_reports/blank.template | 0 example_reports/ex.template | 1 + src/index.ts | 23 ++++++++++++++++- src/templates.test.ts | 47 ++++++++++++++++++++++++++++++++++ src/templates.ts | 46 +++++++++++++++------------------ 5 files changed, 91 insertions(+), 26 deletions(-) create mode 100644 example_reports/blank.template create mode 100644 example_reports/ex.template create mode 100644 src/templates.test.ts diff --git a/example_reports/blank.template b/example_reports/blank.template new file mode 100644 index 0000000..e69de29 diff --git a/example_reports/ex.template b/example_reports/ex.template new file mode 100644 index 0000000..b55937a --- /dev/null +++ b/example_reports/ex.template @@ -0,0 +1 @@ +But what is {{that}} other than {{potential}}? \ No newline at end of file diff --git a/src/index.ts b/src/index.ts index 4165d2e..12bbd76 100644 --- a/src/index.ts +++ b/src/index.ts @@ -9,6 +9,7 @@ import expressWinston from "express-winston"; dotenv.config(); +import processTemplate, { Template } from "./templates"; import routes from "./routes"; import Metadata from "./metadata"; import loggerConfig from "./util/logger"; @@ -17,6 +18,7 @@ import { configOrError, handleShutdown } from "./util/config"; // Start-up configuration const BIND_ADDRESS = process.env.BIND_ADDRESS || "localhost"; const PORT = Number(process.env.PORT || 3000); +const TARGET_URL = process.env.TARGET_URL || "http://localhost:3000"; const logger = winston.createLogger(loggerConfig("ROOT")); @@ -31,7 +33,26 @@ if (!path.isAbsolute(HOST_DIR)) { } // prepare template files -require("./templates"); +const bashTemplate = { + inputFile: path.join(__dirname, "..", "public", "bash.template"), + outputFile: path.join(HOST_DIR, "bash"), + context: { TARGET_URL } +} as Template; +processTemplate(bashTemplate) + .then(template => { + logger.debug("Generated '%s' from template file", template.outputFile); + }) + .catch(err => { + logger.error("Unable to process template file: %s", err); + + // if the output file exists, then we are fine with continuing without + return fs.promises.access(bashTemplate.outputFile, fs.constants.R_OK); + }) + .catch(err => { + logger.error("Cannot proceed: %s", err); + + process.exit(1); + }); new MongoClient(MONGO_URI, { useUnifiedTopology: true }).connect( (err, mongo) => { diff --git a/src/templates.test.ts b/src/templates.test.ts new file mode 100644 index 0000000..1fb88b7 --- /dev/null +++ b/src/templates.test.ts @@ -0,0 +1,47 @@ +import processTemplate, { Template } from "./templates"; +import path from "path"; +import fs from "fs"; + +const genTemplate = (filename: string): Template => + ({ + inputFile: path.join(__dirname, "..", "example_reports", filename), + outputFile: path.join( + __dirname, + "..", + "build", + filename.replace(/template/, "txt") + ), + context: { that: "this", potential: "resolved" } + } as Template); + +describe("processTemplate", () => { + beforeAll(() => + fs.promises.mkdir(path.join(__dirname, "..", "build")).catch(() => null) + ); + + it("should process the template file with the given context", async () => { + // Arrange + const template = genTemplate("ex.template"); + + // Act + const result = await processTemplate(template); + + // Assert + expect(result.data).not.toBeNull(); + expect(result.data).toEqual("But what is this other than resolved?"); + expect(fs.existsSync(result.outputFile)).toEqual(true); + }); + + it("should process the blank file", async () => { + // Arrange + const template = genTemplate("blank.template"); + + // Act + const result = await processTemplate(template); + + // Assert + expect(result.data).not.toBeNull(); + expect(result.data).toEqual(""); + expect(fs.existsSync(result.outputFile)).toEqual(true); + }); +}); diff --git a/src/templates.ts b/src/templates.ts index 2ffd0dd..5458a36 100644 --- a/src/templates.ts +++ b/src/templates.ts @@ -1,30 +1,26 @@ -import winston from "winston"; import handlebars from "handlebars"; -import path from "path"; import fs from "fs"; -import loggerConfig from "./util/logger"; -import { configOrError } from "./util/config"; +export interface Template { + inputFile: string; + outputFile: string; + context: object; + data: string | undefined; +} -const logger = winston.createLogger(loggerConfig("TEMPLATE")); +export default (_template: Template): Promise