import csv import json import math import os import pprint import re import sys from collections import defaultdict from datetime import timedelta from pathlib import Path from openpyxl import load_workbook from tabulate import tabulate from tqdm import tqdm from config import * from lib import read_recipes, markdown_link, recipe_url, markdown_alert def read_plan(): wb = load_workbook("data/Planung + Einkauf Brotaufstriche.xlsx") sheet = wb.active plan = {} for row in sheet.iter_rows(values_only=True): r_name = row[0] # Ansprechpartner*in = row[1] r_total_net_weight = row[2] # gpn23 = row[3] r_serving_net_weight = row[4] # (Formula) = row[5] r_recipe_url = row[6] # We simply skip over any rows that do not have the recipe url if not r_recipe_url: continue if m := re.match(r"https://.*/(\d+)$", r_recipe_url): r_recipe_id = int(m.group(1)) else: continue # skip r_wanted_servings = r_total_net_weight / r_serving_net_weight plan[r_name] = { "total_net_weight": r_total_net_weight, "serving_net_weight": r_serving_net_weight, "recipe_id": r_recipe_id, "wanted_servings": r_wanted_servings, } return plan plan = read_plan() # XXX move to lib def grams(ingredient): conversion = None warnings = [] if not ingredient["unit"] and ingredient["food"]["name"] not in FOOD_NO_UNIT_OK: warnings.append(f"🟡 No unit for {ingredient["food"]["name"]}") for c in ingredient["conversions"]: if c["unit"] in ["g / Gramm", "g"]: conversion = c if conversion: return conversion.get("amount"), warnings else: if ingredient["unit"]: warnings.append(f"🟡 No conversion to grams for unit {ingredient["unit"]["name"]}") return None, warnings def main(): recipes = read_recipes(keyword="Frühstück") inventory = {} for recipe in recipes: scale_factor = plan[recipe["name"]]["wanted_servings"] / recipe["servings"] r_name = recipe["name"] for step in recipe["steps"]: for ingredient in step["ingredients"]: i_name = ingredient["food"]["name"] if not ingredient.get("food"): raise ValueError("No food in ingredient") continue g, warnings = grams(ingredient) if warnings: print(r_name, "-", i_name) for w in warnings: print(f"- {w}") i_grams = scale_factor * (g or 0) i_description = ingredient["food"][ "description" ] # XXX probably not what i wanted inventory.setdefault(i_name, []).append((i_grams, r_name)) # gross ingredient weight per serving r_gross_weight = 0.0 for step in recipe["steps"]: for ingredient in step["ingredients"]: if not ingredient.get("food"): raise ValueError("No food in ingredient") continue r_gross_weight += (grams(ingredient)[0] or 0) r_gross_weight /= recipe["servings"] recipe["total_net_weight"] = plan[r_name]["total_net_weight"] recipe["wanted_servings"] = plan[r_name]["wanted_servings"] recipe["total_gross_weight"] = r_gross_weight * plan[r_name]["wanted_servings"] print("---") print("tags: GPN24, Fruehstueck") print("---") print("# GPN24 Frühstück Aufstriche Inventar + Bestellung") print(markdown_alert("automatisch erstellt, nicht editieren...")) print() print("## Rezepte und Portionen") data = [] for recipe in recipes: row = [markdown_link(recipe["name"], recipe_url(recipe["id"])), int(recipe["wanted_servings"]), int(recipe["total_net_weight"]), int(recipe["total_gross_weight"])] data.append(row) headers = ["Rezept", "Portionen", "Gewicht Netto (Soll)", "Gewicht Brutto Zutaten"] print(tabulate(data, headers=headers, tablefmt="github")) print() print() print("## Zutaten") for ingredient, entries in inventory.items(): total = sum(amount for amount, _ in entries) print(f"### {ingredient}") print(f"- **{total:.1f}g** **Total**") for i_grams, r_name in entries: print(f"- {i_grams:.1f}g {r_name}") print() print() print("## Für die Bestellung nochmal als Tabelle") table_data = [] for ingredient, entries in inventory.items(): total = sum(amount for amount, _ in entries) table_data.append((math.ceil(total), ingredient)) table_headers = ("Gewicht (g)", "Zutat") print(tabulate(table_data, headers=table_headers, tablefmt="github")) print() print() print("## Notes") with open("fruehstueck_bestellung+inventar-notes.md") as notes_fd: print(notes_fd.read()) if __name__ == "__main__": main()