mealie/tests/unit_tests/test_ingredient_parser.py
Hayden 3b920babe3
feat: Add brute strategy to ingredient processor (#744)
* fix UI column width

* words

* update parser to support diff strats

* add new model url

* make button more visible

* fix nutrition error

* feat(backend):  add 'brute' strategy for parsing ingredients

* satisfy linter

* update UI for creation page

* feat(backend):  log 422 errors in detail when not in PRODUCTION

* add strategy selector

Co-authored-by: Hayden <hay-kot@pm.me>
2021-10-16 16:06:13 -08:00

76 lines
2.7 KiB
Python
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

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:
import shutil
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.7, "cup", "coconut", "unsweetened flaked"),
TestIngredient("⅓ cup panko bread crumbs", 0.3, "cup", "panko bread crumbs", ""),
]
@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])
# Itterate over mdoels and test_ingreidnets to gether
for model, test_ingredient in zip(models, test_ingredients):
assert float(sum(Fraction(s) for s in model.qty.split())) == 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}