memorium/lib/parseIngredient.ts

98 lines
2.2 KiB
TypeScript
Raw Permalink Normal View History

import {
parseIngredient,
unitsOfMeasure as _unitsOfMeasure,
} from "https://esm.sh/parse-ingredient@1.2.1";
import { Ingredient, IngredientGroup } from "@lib/recipeSchema.ts";
import { removeMarkdownFormatting } from "@lib/string.ts";
const customUnits = {
tableSpoon: {
short: "EL",
plural: "Table Spoons",
alternates: ["el", "EL", "Tbsp", "tbsp"],
},
dose: {
short: "Dose",
plural: "Dosen",
alternates: ["Dose", "dose", "Dose(n)"],
},
pound: {
short: "lb",
plural: "pounds",
alternates: ["lb", "lbs", "pound", "pounds"],
},
teaSpoon: {
short: "TL",
plural: "Tea Spoon",
alternates: ["tl", "TL", "Tsp", "tsp", "teaspoon"],
},
litre: {
short: "L",
plural: "liters",
alternates: ["L", "l"],
},
paket: {
short: "Paket",
plural: "Pakets",
alternates: ["Paket", "paket"],
},
};
export const unitsOfMeasure = {
..._unitsOfMeasure,
...customUnits,
} as const;
export function parseIngredients(
text: string,
): (Ingredient | IngredientGroup)[] {
2025-01-19 21:11:38 +01:00
const cleanText = removeMarkdownFormatting(text)
.split("\n")
.map((line) => line.trim().replace(/^-/, ""))
.join("\n");
const ingredients = parseIngredient(cleanText, {
normalizeUOM: true,
additionalUOMs: customUnits,
2025-01-18 00:46:05 +01:00
});
const results: (Ingredient | IngredientGroup)[] = [];
let currentGroup: IngredientGroup | undefined;
for (const ing of ingredients) {
if (ing.isGroupHeader) {
if (currentGroup) {
results.push(currentGroup);
}
currentGroup = {
name: ing.description.replace(/:$/, ""),
items: [],
};
} else {
const ingredient = {
name: ing.description.replace(/^\s?-/, "").trim(),
unit: ing.unitOfMeasure || "",
quantity: ing.quantity?.toString() || ing.quantity2?.toString() || "",
note: "",
};
const unit = ingredient.unit.toLowerCase() as keyof typeof unitsOfMeasure;
if (unit in unitsOfMeasure && unit !== "cup") {
ingredient.unit = unitsOfMeasure[unit].short;
}
if (!currentGroup) {
results.push(ingredient);
} else {
currentGroup.items.push(ingredient);
}
}
}
if (currentGroup) {
results.push(currentGroup);
}
return results;
2025-01-18 00:46:05 +01:00
}