mirror of
https://github.com/mealie-recipes/mealie.git
synced 2025-06-03 05:35:02 -04:00
* docs: fix typos * typos: fix typos found by `codespell` across the codebase * docs: fix `macOS` spelling * docs: fix `authentification` terminology "Authentification" is not a thing. * docs: fix `localhost` typo in example link * typos: fix in-code typos These are potentially higher risk, but no other mentions of these typos show up in the codebase.
80 lines
3.0 KiB
Python
80 lines
3.0 KiB
Python
import shutil
|
||
from dataclasses import dataclass
|
||
from fractions import Fraction
|
||
|
||
import pytest
|
||
|
||
from mealie.services.parser_services import RegisteredParser, get_parser
|
||
from mealie.services.parser_services.crfpp.processor import CRFIngredient, convert_list_to_crf_model
|
||
|
||
|
||
@dataclass
|
||
class TestIngredient:
|
||
input: str
|
||
quantity: float
|
||
unit: str
|
||
food: str
|
||
comments: str
|
||
|
||
|
||
def crf_exists() -> bool:
|
||
|
||
return shutil.which("crf_test") is not None
|
||
|
||
|
||
# TODO - add more robust test cases
|
||
test_ingredients = [
|
||
TestIngredient("½ cup all-purpose flour", 0.5, "cup", "all-purpose flour", ""),
|
||
TestIngredient("1 ½ teaspoons ground black pepper", 1.5, "teaspoon", "black pepper", "ground"),
|
||
TestIngredient("⅔ cup unsweetened flaked coconut", 0.667, "cup", "coconut", "unsweetened flaked"),
|
||
TestIngredient("⅓ cup panko bread crumbs", 0.333, "cup", "panko bread crumbs", ""),
|
||
# Small Fraction Tests - PR #1369
|
||
# Reported error is was for 1/8 - new lowest expected threshold is 1/32
|
||
TestIngredient("1/8 cup all-purpose flour", 0.125, "cup", "all-purpose flour", ""),
|
||
TestIngredient("1/32 cup all-purpose flour", 0.031, "cup", "all-purpose flour", ""),
|
||
]
|
||
|
||
|
||
@pytest.mark.skipif(not crf_exists(), reason="CRF++ not installed")
|
||
def test_nlp_parser():
|
||
models: list[CRFIngredient] = convert_list_to_crf_model([x.input for x in test_ingredients])
|
||
|
||
# Iterate over models and test_ingredients to gather
|
||
for model, test_ingredient in zip(models, test_ingredients):
|
||
assert round(float(sum(Fraction(s) for s in model.qty.split())), 3) == pytest.approx(test_ingredient.quantity)
|
||
|
||
assert model.comment == test_ingredient.comments
|
||
assert model.name == test_ingredient.food
|
||
assert model.unit == test_ingredient.unit
|
||
|
||
|
||
def test_brute_parser():
|
||
# input: (quantity, unit, food, comments)
|
||
expectations = {
|
||
# Dutch
|
||
"1 theelepel koffie": (1, "theelepel", "koffie", ""),
|
||
"3 theelepels koffie": (3, "theelepels", "koffie", ""),
|
||
"1 eetlepel tarwe": (1, "eetlepel", "tarwe", ""),
|
||
"20 eetlepels bloem": (20, "eetlepels", "bloem", ""),
|
||
"1 mespunt kaneel": (1, "mespunt", "kaneel", ""),
|
||
"1 snuf(je) zout": (1, "snuf(je)", "zout", ""),
|
||
"2 tbsp minced cilantro, leaves and stems": (2, "tbsp", "minced cilantro", "leaves and stems"),
|
||
"1 large yellow onion, coarsely chopped": (1, "large", "yellow onion", "coarsely chopped"),
|
||
"1 1/2 tsp garam masala": (1.5, "tsp", "garam masala", ""),
|
||
"2 cups mango chunks, (2 large mangoes) (fresh or frozen)": (
|
||
2,
|
||
"cups",
|
||
"mango chunks, (2 large mangoes)",
|
||
"fresh or frozen",
|
||
),
|
||
}
|
||
parser = get_parser(RegisteredParser.brute)
|
||
|
||
for key, val in expectations.items():
|
||
parsed = parser.parse_one(key)
|
||
|
||
assert parsed.ingredient.quantity == val[0]
|
||
assert parsed.ingredient.unit.name == val[1]
|
||
assert parsed.ingredient.food.name == val[2]
|
||
assert parsed.ingredient.note in {val[3], None}
|