diff --git a/src/parser/parser.test.ts b/src/parser/parser.test.ts index 2adf239..5a71658 100644 --- a/src/parser/parser.test.ts +++ b/src/parser/parser.test.ts @@ -35,7 +35,7 @@ describe("Parser", () => { `); }); - it("parses workout header with all fields", () => { + it("parses workout header with name, author, description", () => { expect( parse(` Name: My Workout @@ -60,6 +60,46 @@ Description: `); }); + it("parses workout header with comma-separated tags", () => { + expect( + parse(` +Name: My Workout +Tags: Recovery, Intervals , FTP +`), + ).toMatchInlineSnapshot(` + Object { + "author": "", + "description": "", + "intervals": Array [], + "name": "My Workout", + "tags": Array [ + "Recovery", + "Intervals", + "FTP", + ], + } + `); + }); + + it("treats with space-separated tags as single tag", () => { + expect( + parse(` +Name: My Workout +Tags: Recovery Intervals FTP +`), + ).toMatchInlineSnapshot(` + Object { + "author": "", + "description": "", + "intervals": Array [], + "name": "My Workout", + "tags": Array [ + "Recovery Intervals FTP", + ], + } + `); + }); + it("throws error for unknown labels", () => { expect(() => parse(` diff --git a/src/parser/parser.ts b/src/parser/parser.ts index a6aee0d..64ee767 100644 --- a/src/parser/parser.ts +++ b/src/parser/parser.ts @@ -43,6 +43,11 @@ const parseHeader = (tokens: Token[]): [Header, Token[]] => { const [description, rest] = extractText(tokens); header.description = description; tokens = rest; + } else if (token.type === "header" && token.value === "Tags") { + tokens.shift(); + const [tags, rest] = extractText(tokens); + header.tags = tags.split(/\s*,\s*/); + tokens = rest; } else { // End of header break; @@ -138,7 +143,7 @@ export const parseTokens = (tokens: Token[]): Workout => { name: header.name || "Untitled", author: header.author || "", description: header.description || "", - tags: [], + tags: header.tags || [], intervals: parseIntervals(intervalTokens), }; }; diff --git a/src/parser/tokenizer.ts b/src/parser/tokenizer.ts index 229dace..8efb7e3 100644 --- a/src/parser/tokenizer.ts +++ b/src/parser/tokenizer.ts @@ -1,10 +1,10 @@ import { ParseError } from "./ParseError"; -export type HeaderType = "Name" | "Author" | "Description"; +export type HeaderType = "Name" | "Author" | "Description" | "Tags"; export type IntervalType = "Warmup" | "Rest" | "Interval" | "Cooldown" | "FreeRide"; const isHeaderType = (value: string): value is HeaderType => { - return ["Name", "Author", "Description"].includes(value); + return ["Name", "Author", "Description", "Tags"].includes(value); }; const isIntervalType = (value: string): value is IntervalType => { return ["Warmup", "Rest", "Interval", "Cooldown", "FreeRide"].includes(value);