prettier lint

This commit is contained in:
Ava Gaiety W 2023-03-16 00:34:58 -05:00
parent fdfcd74fe4
commit fa32427fe1
7 changed files with 231 additions and 165 deletions

View file

@ -22,32 +22,32 @@ cache:
paths: paths:
- node_modules/ - node_modules/
stages: # List of stages for jobs, and their order of execution stages: # List of stages for jobs, and their order of execution
- build - build
- test - test
- deploy - deploy
build-job: # This job runs in the build stage, which runs first. build-job: # This job runs in the build stage, which runs first.
stage: build stage: build
script: script:
- npm i - npm i
- npm run build:svg - npm run build:svg
- npm run build:css - npm run build:css
unit-test-job: # This job runs in the test stage. unit-test-job: # This job runs in the test stage.
stage: test # It only starts when the job in the build stage completes successfully. stage: test # It only starts when the job in the build stage completes successfully.
script: script:
- echo "Running unit tests..." - echo "Running unit tests..."
- npm i - npm i
- npm test - npm test
lint-test-job: # This job also runs in the test stage. lint-test-job: # This job also runs in the test stage.
stage: test # It can run at the same time as unit-test-job (in parallel). stage: test # It can run at the same time as unit-test-job (in parallel).
script: script:
- echo "Linting code... TBD" - echo "Linting code... TBD"
deploy-job: # This job runs in the deploy stage. deploy-job: # This job runs in the deploy stage.
stage: deploy # It only runs when *both* jobs in the test stage complete successfully. stage: deploy # It only runs when *both* jobs in the test stage complete successfully.
environment: production environment: production
script: script:
- echo "Deploying application... TBD lol" - echo "Deploying application... TBD lol"

View file

@ -2,7 +2,7 @@
## Getting Started ## Getting Started
* [NodeJS](https://nodejs.org/en/) - [NodeJS](https://nodejs.org/en/)
```bash ```bash
npm i # Installs Dependencies npm i # Installs Dependencies

146
app.js
View file

@ -1,69 +1,113 @@
import express from 'express' import express from "express";
import { engine } from 'express-handlebars' import { engine } from "express-handlebars";
import fetchData from './data.js' import fetchData from "./data.js";
const app = express() const app = express();
const data = fetchData() const data = fetchData();
app.engine('handlebars', engine()) app.engine("handlebars", engine());
app.set('view engine', 'handlebars') app.set("view engine", "handlebars");
app.set('views', './src/views') app.set("views", "./src/views");
app.use(express.static('dist')) app.use(express.static("dist"));
app.use(express.static('public')) app.use(express.static("public"));
const siteName = "Pronoun Monster" const siteName = "Pronoun Monster";
const pronounsToDisplayOnHome = 6 const pronounsToDisplayOnHome = 6;
function constructLexicon(nominative, accusative, pronominalPossessive, predicativePossessive, reflexive) { function constructLexicon(
nominative,
accusative,
pronominalPossessive,
predicativePossessive,
reflexive
) {
return { return {
nominative: { name: "Nominative", value: nominative}, nominative: { name: "Nominative", value: nominative },
accusative: { name: "Accusative", value: accusative}, accusative: { name: "Accusative", value: accusative },
pronominalPossessive: { name: "Pronominal Possessive", value: pronominalPossessive}, pronominalPossessive: {
predicativePossessive: { name: "Predicative Possessive", value: predicativePossessive}, name: "Pronominal Possessive",
reflexive: { name: "Reflexive", value: reflexive} value: pronominalPossessive,
} },
predicativePossessive: {
name: "Predicative Possessive",
value: predicativePossessive,
},
reflexive: { name: "Reflexive", value: reflexive },
};
} }
app.get('/', (req, res) => { app.get("/", (req, res) => {
const pageTitle = siteName; const pageTitle = siteName;
const pronounListLimited = data.map(pronounObject => Object.values(pronounObject).join('/')).slice(0, pronounsToDisplayOnHome) const pronounListLimited = data
res.render('home', { siteName, pageTitle, pronounList: pronounListLimited } ) .map((pronounObject) => Object.values(pronounObject).join("/"))
}) .slice(0, pronounsToDisplayOnHome);
res.render("home", { siteName, pageTitle, pronounList: pronounListLimited });
});
app.get('/list', (req, res) => { app.get("/list", (req, res) => {
const pageTitle = "List"; const pageTitle = "List";
const pronounList = data.map(pronounObject => Object.values(pronounObject).join('/')) const pronounList = data.map((pronounObject) =>
res.render('list', { siteName, pageTitle, pronounList } ) Object.values(pronounObject).join("/")
}) );
res.render("list", { siteName, pageTitle, pronounList });
});
app.get('/:nominative/:accusative/:predicative_possessive/:reflexive', (req, res) => { app.get(
const { "/:nominative/:accusative/:predicative_possessive/:reflexive",
nominative, (req, res) => {
accusative, const {
predicative_possessive: predicativePossessive, nominative,
reflexive, accusative,
} = req.params predicative_possessive: predicativePossessive,
reflexive,
} = req.params;
const lexicon = constructLexicon(nominative, accusative, accusative, predicativePossessive, reflexive); const lexicon = constructLexicon(
const pageTitle = Object.values(lexicon).map(entry => entry.value).join("/") + " - " + siteName; nominative,
accusative,
accusative,
predicativePossessive,
reflexive
);
const pageTitle =
Object.values(lexicon)
.map((entry) => entry.value)
.join("/") +
" - " +
siteName;
res.render('individual', { siteName, pageTitle, lexicon }) res.render("individual", { siteName, pageTitle, lexicon });
}) }
);
app.get('/:nominative/:accusative/:pronominal_possessive/:predicative_possessive/:reflexive', (req, res) => { app.get(
const { "/:nominative/:accusative/:pronominal_possessive/:predicative_possessive/:reflexive",
nominative, (req, res) => {
accusative, const {
pronominal_possessive: pronominalPossessive, nominative,
predicative_possessive: predicativePossessive, accusative,
reflexive, pronominal_possessive: pronominalPossessive,
} = req.params predicative_possessive: predicativePossessive,
reflexive,
} = req.params;
const lexicon = constructLexicon(nominative, accusative, pronominalPossessive, predicativePossessive, reflexive); const lexicon = constructLexicon(
const pageTitle = Object.values(lexicon).map(entry => entry.value).join("/") + " - " + siteName; nominative,
accusative,
pronominalPossessive,
predicativePossessive,
reflexive
);
const pageTitle =
Object.values(lexicon)
.map((entry) => entry.value)
.join("/") +
" - " +
siteName;
res.render('individual', { siteName, pageTitle, lexicon }) res.render("individual", { siteName, pageTitle, lexicon });
}) }
);
app.listen(3000) app.listen(3000);

39
data.js
View file

@ -1,20 +1,21 @@
import fs from 'fs' import fs from "fs";
const databaseCSV = fs.readFileSync('database.csv', {encoding:'utf8', flag:'r'}) const databaseCSV = fs.readFileSync("database.csv", {
encoding: "utf8",
flag: "r",
});
export function splitNewLines(string) { export function splitNewLines(string) {
return string.split(/\n/) return string.split(/\n/);
} }
export function cleanupArrayOfStrings(arrayOfStrings) { export function cleanupArrayOfStrings(arrayOfStrings) {
return arrayOfStrings return arrayOfStrings.map((line) => line.trim()).filter((line) => line != "");
.map(line => line.trim())
.filter(line => line != '')
} }
export function stringCsvToDataObject(string) { export function stringCsvToDataObject(string) {
let splitString = string.split(',') let splitString = string.split(",");
if (splitString[2].trim() == '') splitString[2] = splitString[1] if (splitString[2].trim() == "") splitString[2] = splitString[1];
const [ const [
nominative, nominative,
@ -22,15 +23,23 @@ export function stringCsvToDataObject(string) {
pronominalPossessive, pronominalPossessive,
predicativePossessive, predicativePossessive,
reflexive, reflexive,
] = cleanupArrayOfStrings(splitString) ] = cleanupArrayOfStrings(splitString);
return { return {
nominative, accusative, pronominalPossessive, predicativePossessive, reflexive nominative,
} accusative,
pronominalPossessive,
predicativePossessive,
reflexive,
};
} }
export default function() { export default function () {
const databaseCSV = fs.readFileSync('database.csv', {encoding:'utf8', flag:'r'}) const databaseCSV = fs.readFileSync("database.csv", {
return cleanupArrayOfStrings(splitNewLines(databaseCSV)).map(line => stringCsvToDataObject(line)) encoding: "utf8",
flag: "r",
});
return cleanupArrayOfStrings(splitNewLines(databaseCSV)).map((line) =>
stringCsvToDataObject(line)
);
} }

View file

@ -3,105 +3,111 @@
@tailwind utilities; @tailwind utilities;
:root { :root {
/* light */ /* light */
--background: #F8FAF9; /* Sage/Light/2 */ --background: #f8faf9; /* Sage/Light/2 */
--callout: #ECEFED; /* Sage/Light/4 */ --callout: #ecefed; /* Sage/Light/4 */
--stroke: #D7DCDA; /* Sage/Light/7 */ --stroke: #d7dcda; /* Sage/Light/7 */
--text-shout: #236E4A; /* Green/Dark/8 */ --text-shout: #236e4a; /* Green/Dark/8 */
--text-murmur: #113123; /* Green/Dark/4 */ --text-murmur: #113123; /* Green/Dark/4 */
} }
@media (prefers-color-scheme: dark) { @media (prefers-color-scheme: dark) {
:root { :root {
/* dark */ /* dark */
--background: #141716; /* Sage/Dark/1 */ --background: #141716; /* Sage/Dark/1 */
--callout: #252A27; /* Sage/Dark/4 */ --callout: #252a27; /* Sage/Dark/4 */
--stroke: #393F3C; /* Sage/Dark/7 */ --stroke: #393f3c; /* Sage/Dark/7 */
--text-shout: #92CEAC; /* Green/Light/7 */ --text-shout: #92ceac; /* Green/Light/7 */
--text-murmur: #99A29E; /* Green/Dark/11 */ --text-murmur: #99a29e; /* Green/Dark/11 */
} }
} }
body { body {
background-color: var(--background); background-color: var(--background);
color: var(--text-murmur); color: var(--text-murmur);
font-family: Manrope, 'Lucida Sans', 'Lucida Sans Regular', 'Lucida Grande', 'Lucida Sans Unicode', Geneva, Verdana, sans-serif; font-family: Manrope, "Lucida Sans", "Lucida Sans Regular", "Lucida Grande",
font-weight: 500; "Lucida Sans Unicode", Geneva, Verdana, sans-serif;
font-weight: 500;
} }
h1, h2, h3, h4 { h1,
font-weight: 700; h2,
h3,
h4 {
font-weight: 700;
} }
h2, h3, h4 { h2,
color: var(--text-shout); h3,
h4 {
color: var(--text-shout);
} }
h1 { h1 {
font-family: "Redaction", Georgia, 'Times New Roman', Times, serif; font-family: "Redaction", Georgia, "Times New Roman", Times, serif;
} }
h2 { h2 {
font-family: "Redaction 10", Georgia, 'Times New Roman', Times, serif; font-family: "Redaction 10", Georgia, "Times New Roman", Times, serif;
} }
footer { footer {
border-color: var(--stroke); border-color: var(--stroke);
} }
.pronoun-list-title span:not(:last-child):after { .pronoun-list-title span:not(:last-child):after {
content: "/"; content: "/";
} }
.pronoun-list-link { .pronoun-list-link {
color: var(--text-shout); color: var(--text-shout);
text-decoration: underline; text-decoration: underline;
} }
.pronoun-list-icon { .pronoun-list-icon {
color: var(--text-murmur); color: var(--text-murmur);
} }
.pronoun-example-table { .pronoun-example-table {
border-color: var(--stroke); border-color: var(--stroke);
} }
.t-row:not(:last-child) { .t-row:not(:last-child) {
@apply border-b; @apply border-b;
border-color: var(--stroke); border-color: var(--stroke);
} }
.t-header { .t-header {
background-color: var(--callout); background-color: var(--callout);
} }
.button-cta { .button-cta {
background-color: var(--callout); background-color: var(--callout);
color: var(--text-shout); color: var(--text-shout);
border-bottom: 2px solid var(--text-shout); border-bottom: 2px solid var(--text-shout);
border-left: 1px solid var(--text-shout); border-left: 1px solid var(--text-shout);
border-radius: 1rem 0.5rem 1rem 0.5rem; border-radius: 1rem 0.5rem 1rem 0.5rem;
padding: 0.5rem 1rem; padding: 0.5rem 1rem;
display: inline-block; display: inline-block;
} }
.button-cta:not(:active) { .button-cta:not(:active) {
margin-bottom: 1px; margin-bottom: 1px;
margin-left: 1px; margin-left: 1px;
} }
.button-cta:active { .button-cta:active {
border-top: 1px solid var(--text-shout); border-top: 1px solid var(--text-shout);
border-right: 1px solid var(--text-shout); border-right: 1px solid var(--text-shout);
transform: translate(-1px, 2px) transform: translate(-1px, 2px);
} }
@media (min-width: 1024px) { @media (min-width: 1024px) {
.t-row:not(:last-child) { .t-row:not(:last-child) {
@apply border-b-0; @apply border-b-0;
} }
.t-row:not(:last-child) .t-cell { .t-row:not(:last-child) .t-cell {
@apply border-r; @apply border-r;
border-color: var(--stroke); border-color: var(--stroke);
} }
} }

View file

@ -1,7 +1,7 @@
module.exports = { module.exports = {
content: ['./src/views/**/*.{handlebars,hbs,html,htm,js}'], content: ["./src/views/**/*.{handlebars,hbs,html,htm,js}"],
theme: { theme: {
extend: {}, extend: {},
}, },
plugins: [], plugins: [],
} };

View file

@ -1,55 +1,62 @@
import fs from 'fs' import fs from "fs";
import test from 'ava' import test from "ava";
import fetchData, { splitNewLines, cleanupArrayOfStrings, stringCsvToDataObject } from '../data.js' import fetchData, {
splitNewLines,
cleanupArrayOfStrings,
stringCsvToDataObject,
} from "../data.js";
test('splitNewLines', t => { test("splitNewLines", (t) => {
const result = splitNewLines(`foo\nbar`) const result = splitNewLines(`foo\nbar`);
t.deepEqual(result, ['foo', 'bar']) t.deepEqual(result, ["foo", "bar"]);
}) });
test('cleanupArrayOfStrings', t => { test("cleanupArrayOfStrings", (t) => {
const result = cleanupArrayOfStrings([ const result = cleanupArrayOfStrings(["", " foo", "bar ", ""]);
'',
' foo',
'bar ',
''
])
t.deepEqual(result, ['foo', 'bar']) t.deepEqual(result, ["foo", "bar"]);
}) });
test('clean an array made from a string of new lines', t => { test("clean an array made from a string of new lines", (t) => {
const result = cleanupArrayOfStrings( const result = cleanupArrayOfStrings(
splitNewLines(` splitNewLines(`
foo foo
bar bar
`) `)
) );
t.deepEqual(result, ['foo', 'bar']) t.deepEqual(result, ["foo", "bar"]);
}) });
test('stringCsvToDataObject', t => { test("stringCsvToDataObject", (t) => {
const result = stringCsvToDataObject('they,them,them, their,themself') const result = stringCsvToDataObject("they,them,them, their,themself");
t.deepEqual(result, { t.deepEqual(result, {
nominative: 'they', accusative: 'them', pronominalPossessive: 'them', predicativePossessive: 'their', reflexive: 'themself' nominative: "they",
}) accusative: "them",
}) pronominalPossessive: "them",
predicativePossessive: "their",
reflexive: "themself",
});
});
test('stringCsvToDataObject with missing pronominalPossessive', t => { test("stringCsvToDataObject with missing pronominalPossessive", (t) => {
const result = stringCsvToDataObject('they,them,,their,themself') const result = stringCsvToDataObject("they,them,,their,themself");
t.deepEqual(result, { t.deepEqual(result, {
nominative: 'they', accusative: 'them', pronominalPossessive: 'them', predicativePossessive: 'their', reflexive: 'themself' nominative: "they",
}) accusative: "them",
}) pronominalPossessive: "them",
predicativePossessive: "their",
reflexive: "themself",
});
});
test('database.csv loads into array of valid data', t => { test("database.csv loads into array of valid data", (t) => {
const data = fetchData() const data = fetchData();
t.truthy(Array.isArray(data)) t.truthy(Array.isArray(data));
t.is(typeof data[0], 'object') t.is(typeof data[0], "object");
t.is(typeof data[0].nominative, 'string') t.is(typeof data[0].nominative, "string");
}) });