```json
{
  "sym_variables": [
    ("x0", "knishes"),
    ("x1", "chicken drumsticks"),
    ("x2", "steaks")
  ],
  "objective_function": "9.54 * x0 + 1.56 * x1 + 4.96 * x2",
  "constraints": [
    "23 * x0 + 7 * x2 >= 20",
    "2 * x1 + 7 * x2 >= 37",
    "23 * x0 + 2 * x1 + 7 * x2 >= 34",
    "15 * x0 + 3 * x1 >= 20",
    "15 * x0 + 3 * x1 + 23 * x2 >= 20",
    "13 * x0 + 5 * x1 >= 26",
    "13 * x0 + 24 * x2 >= 67",
    "5 * x1 + 24 * x2 >= 36",
    "13 * x0 + 5 * x1 + 24 * x2 >= 36",
    "15 * x0 + 20 * x1 >= 25",
    "15 * x0 + 15 * x2 >= 34",
    "15 * x0 + 20 * x1 + 15 * x2 >= 34",
    "7 * x0 - 7 * x2 >= 0",
    "15 * x0 + 23 * x2 <= 102",
    "15 * x0 + 3 * x1 + 23 * x2 <= 139",
    "13 * x0 + 5 * x1 + 24 * x2 <= 194",
    "15 * x0 + 20 * x1 <= 143",
    "20 * x1 + 15 * x2 <= 88",
    "23 * x0 + 2 * x1 + 7 * x2 <= 133",
    "15 * x0 + 3 * x1 + 23 * x2 <= 145",
    "13 * x0 + 5 * x1 + 24 * x2 <= 240",
    "15 * x0 + 20 * x1 + 15 * x2 <= 168"

  ]
}
```

```python
import gurobipy as gp

# Create a new model
m = gp.Model("food_optimization")

# Create variables
knishes = m.addVar(lb=0, vtype=gp.GRB.CONTINUOUS, name="knishes")
chicken_drumsticks = m.addVar(lb=0, vtype=gp.GRB.INTEGER, name="chicken_drumsticks")
steaks = m.addVar(lb=0, vtype=gp.GRB.INTEGER, name="steaks")

# Set objective function
m.setObjective(9.54 * knishes + 1.56 * chicken_drumsticks + 4.96 * steaks, gp.GRB.MINIMIZE)

# Add constraints
m.addConstr(23 * knishes + 7 * steaks >= 20, "iron_constr1")
m.addConstr(2 * chicken_drumsticks + 7 * steaks >= 37, "iron_constr2")
m.addConstr(23 * knishes + 2 * chicken_drumsticks + 7 * steaks >= 34, "iron_constr3")
m.addConstr(15 * knishes + 3 * chicken_drumsticks >= 20, "fiber_constr1")
m.addConstr(15 * knishes + 3 * chicken_drumsticks + 23 * steaks >= 20, "fiber_constr2")
m.addConstr(13 * knishes + 5 * chicken_drumsticks >= 26, "fat_constr1")
m.addConstr(13 * knishes + 24 * steaks >= 67, "fat_constr2")
m.addConstr(5 * chicken_drumsticks + 24 * steaks >= 36, "fat_constr3")
m.addConstr(13 * knishes + 5 * chicken_drumsticks + 24 * steaks >= 36, "fat_constr4")
m.addConstr(15 * knishes + 20 * chicken_drumsticks >= 25, "protein_constr1")
m.addConstr(15 * knishes + 15 * steaks >= 34, "protein_constr2")
m.addConstr(15 * knishes + 20 * chicken_drumsticks + 15 * steaks >= 34, "protein_constr3")
m.addConstr(7 * knishes - 7 * steaks >= 0, "misc_constr1")
m.addConstr(15 * knishes + 23 * steaks <= 102, "fiber_constr3")
m.addConstr(15 * knishes + 3 * chicken_drumsticks + 23 * steaks <= 139, "fiber_constr4")
m.addConstr(13 * knishes + 5 * chicken_drumsticks + 24 * steaks <= 194, "fat_constr5")
m.addConstr(15 * knishes + 20 * chicken_drumsticks <= 143, "protein_constr4")
m.addConstr(20 * chicken_drumsticks + 15 * steaks <= 88, "protein_constr5")

# Resource Constraints
m.addConstr(23 * knishes + 2 * chicken_drumsticks + 7 * steaks <= 133, "iron_limit")
m.addConstr(15 * knishes + 3 * chicken_drumsticks + 23 * steaks <= 145, "fiber_limit")
m.addConstr(13 * knishes + 5 * chicken_drumsticks + 24 * steaks <= 240, "fat_limit")
m.addConstr(15 * knishes + 20 * chicken_drumsticks + 15 * steaks <= 168, "protein_limit")


# Optimize model
m.optimize()

# Print solution
if m.status == gp.GRB.OPTIMAL:
    print('Obj: %g' % m.objVal)
    print('knishes:', knishes.x)
    print('chicken_drumsticks:', chicken_drumsticks.x)
    print('steaks:', steaks.x)
elif m.status == gp.GRB.INFEASIBLE:
    print("The model is infeasible.")
else:
    print("Optimization ended with status:", m.status)

```
