Esta página foi traduzida por máquina e ainda não foi revisada por uma pessoa. O inglês é a referência; correções são bem-vindas no GitHub. GitHub

Cookwala / SDK e cenários / 020

Check a simmer trace against its envelope: inside, left it, missed the target

An envelope is the safe band for the medium. The check tolerates the warm-up, then requires every reading to stay in the band and, once the recipe target is reached, near it.

Público: developer · Objetivo: Robôs para pessoas · Nível: beginner

Leia primeiro: /docs/CORE/ /docs/QUICKSTART/

Passos

  1. Warm-up to 88, then 92 and 94 degC with a target of 94 plus or minus 3: inside the band, target held. checkEnvelope

  2. The same pot reaches 99 degC: that is a boil, not a simmer. checkEnvelope

  3. Inside the band but it drifted away from the target after reaching it. checkEnvelope

  4. The band itself, from the vocabulary. getOps

Resultado

You can tell an envelope violation from a missed target, and you know the warm-up is not a violation. Next: scenario 021 moves the boiling band with altitude.

Linha de comando

printf '[{"t": 0, "tempC": 60}, {"t": 30, "tempC": 88}, {"t": 60, "tempC": 92}, {"t": 90, "tempC": 94}]' > trace.json && cookwala envelope cw.op.simmer trace.json --target 94 --tolerance 3
printf '[{"t": 0, "tempC": 60}, {"t": 30, "tempC": 90}, {"t": 60, "tempC": 94}, {"t": 90, "tempC": 99}]' > trace.json && cookwala envelope cw.op.simmer trace.json --target 94 --tolerance 3

Saída gravada

Status: ok

[1] checkEnvelope: {"envelopeOk": true, "targetOk": true, "reason": "ok"}
[2] checkEnvelope: {"envelopeOk": false, "targetOk": false, "reason": "left_envelope"}
[3] checkEnvelope: {"envelopeOk": true, "targetOk": false, "reason": "missed_target"}
[4] getOps: {"name": "ops", "version": "0.2.0", "entries": [{"id": "cw.op.dispense", "label": {"en": "Dispense / measure", "ar": "قياس وإضافة"}, "definition": "Measure an ingredient by mass, volume or count and add it to a target.", "classes": ["cw.opfamily.handle"], "paramsSchema": {"type": "object", "properties": {"precision": {"type": "number"}}}, "sensors": ["cw.sense.mass"], "links": {"ieee1872": "IEEE 1872.1-2024 Task (to be mapped)"}}, {"id": "cw.op.transfer", "label": {"en": "Transfer", "ar": "نقل"}, "definition": "Move food or a vessel's contents from one place to another.", "classes": ["cw.opfam…

Código

Executar: python scenarios/out/020-simmer-trace-inside-and-outside/python.py

# Scenario 020: Check a simmer trace against its envelope: inside, left it, missed the target
# An envelope is the safe band for the medium. The check tolerates the warm-up, then requires every reading to stay in the band and, once the recipe target is reached, near it.
# Run a hub first: python hub/cookwala_hub.py --recipes examples
import json, os
from cookwala.client import CookwalaClient, CookwalaProblem

def load(path):
    with open(path, encoding="utf-8") as f:
        return json.load(f)

def pick(obj, path):
    for part in path.replace("]", "").replace("[", ".").split("."):
        obj = obj[int(part)] if part.isdigit() else (len(obj) if part == "length" else obj.get(part))
    return obj

c = CookwalaClient(os.environ.get("COOKWALA_HUB", "http://localhost:7878"))


# Step 1: Warm-up to 88, then 92 and 94 degC with a target of 94 plus or minus 3: inside the band, target held.
ok = c.check_envelope("cw.op.simmer", [{"t": 0, "tempC": 60}, {"t": 30, "tempC": 88}, {"t": 60, "tempC": 92}, {"t": 90, "tempC": 94}], {"value": 94, "tolerance": 3})
assert pick(ok, "envelopeOk") == True, pick(ok, "envelopeOk")
print("ok", "envelopeOk", "=", True)
assert pick(ok, "targetOk") == True, pick(ok, "targetOk")
print("ok", "targetOk", "=", True)
assert pick(ok, "reason") == "ok", pick(ok, "reason")
print("ok", "reason", "=", "ok")

# Step 2: The same pot reaches 99 degC: that is a boil, not a simmer.
left = c.check_envelope("cw.op.simmer", [{"t": 0, "tempC": 60}, {"t": 30, "tempC": 90}, {"t": 60, "tempC": 94}, {"t": 90, "tempC": 99}], {"value": 94, "tolerance": 3})
assert pick(left, "envelopeOk") == False, pick(left, "envelopeOk")
print("ok", "envelopeOk", "=", False)
assert pick(left, "targetOk") == False, pick(left, "targetOk")
print("ok", "targetOk", "=", False)
assert pick(left, "reason") == "left_envelope", pick(left, "reason")
print("ok", "reason", "=", "left_envelope")

# Step 3: Inside the band but it drifted away from the target after reaching it.
missed = c.check_envelope("cw.op.simmer", [{"t": 0, "tempC": 86}, {"t": 30, "tempC": 94}, {"t": 60, "tempC": 88}], {"value": 94, "tolerance": 3})
assert pick(missed, "envelopeOk") == True, pick(missed, "envelopeOk")
print("ok", "envelopeOk", "=", True)
assert pick(missed, "targetOk") == False, pick(missed, "targetOk")
print("ok", "targetOk", "=", False)
assert pick(missed, "reason") == "missed_target", pick(missed, "reason")
print("ok", "reason", "=", "missed_target")

# Step 4: The band itself, from the vocabulary.
ops = c.get_ops()
assert pick(ops, "entries[32].id") == "cw.op.simmer", pick(ops, "entries[32].id")
print("ok", "entries[32].id", "=", "cw.op.simmer")
assert pick(ops, "entries[32].envelope.medium") == "water", pick(ops, "entries[32].envelope.medium")
print("ok", "entries[32].envelope.medium", "=", "water")
assert pick(ops, "entries[32].envelope.tempC.min") == 85, pick(ops, "entries[32].envelope.tempC.min")
print("ok", "entries[32].envelope.tempC.min", "=", 85)
assert pick(ops, "entries[32].envelope.tempC.max") == 96, pick(ops, "entries[32].envelope.tempC.max")
print("ok", "entries[32].envelope.tempC.max", "=", 96)

print("scenario complete")

scenarios/020-simmer-trace-inside-and-outside.json

Anterior: 019 Próximo: 021