How IBU is calculated
homebre.ws calculates International Bitterness Units (IBU) using the Tinseth formula, with corrections for kettle geometry and an optional system-specific utilization factor.
The formula
For each hop addition:
IBU_addition = (decimal_alpha × mass_g × 1000 / volume_L) × utilization
utilization = bigness_factor × boil_time_factor
Where:
bigness_factor = 1.65 × 0.000125^(wort_gravity − 1)— penalises high-gravity worts.boil_time_factor = (1 − e^(−0.04 × time_min)) / 4.15— rises asymptotically with boil time.
The recipe’s IBU is the sum across all additions, optionally scaled by the equipment profile’s hop utilization factor (default 100%).
Contact time per hop use
time_min is not always the addition’s own time field. Each use supplies its own contact time:
- Boil uses the addition’s own time.
- First wort uses the recipe’s boil time. First wort hops go into the kettle during the lauter, before the burner is lit, so they isomerise for the whole boil. Changing the recipe’s boil time changes their bitterness; their own time field is ignored, which is why the editor hides it.
- Whirlpool uses the addition’s own time, modulated by how hot the wort is. A whirlpool with a set temperature is scaled by the isomerisation rate at that temperature; a flameout whirlpool is integrated over the kettle’s cooling curve (this is the mIBU part of the model).
- Mash and dry hop contribute no calculated bitterness.
Worked example
Below, homebre.ws calculates the IBU for a sample recipe. The numbers come from running calculateRecipeStats (the same function the app uses) at build time — so they match what you’d see in the recipe page.
Why we trust these numbers
The card above is rendered by the same calculateRecipeStats function that powers the recipe page in the app. If the formula ever changes, this page changes too — there’s no copy of the math in prose to drift out of sync.