{"id":"05f18d2fc83bdc3e","repo":"stretchr/testify","slug":"expected-value-must-have-a-value-other-than-zero-t","errorCode":null,"errorMessage":"expected value must have a value other than zero to calculate the relative error","messagePattern":"expected value must have a value other than zero to calculate the relative error","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"assert/assertions.go","lineNumber":1567,"sourceCode":"\t}\n\n\treturn true\n}\n\nfunc calcRelativeError(expected, actual interface{}) (float64, error) {\n\taf, aok := toFloat(expected)\n\tbf, bok := toFloat(actual)\n\tif !aok || !bok {\n\t\treturn 0, fmt.Errorf(\"Parameters must be numerical\")\n\t}\n\tif math.IsNaN(af) && math.IsNaN(bf) {\n\t\treturn 0, nil\n\t}\n\tif math.IsNaN(af) {\n\t\treturn 0, errors.New(\"expected value must not be NaN\")\n\t}\n\tif af == 0 {\n\t\treturn 0, fmt.Errorf(\"expected value must have a value other than zero to calculate the relative error\")\n\t}\n\tif math.IsNaN(bf) {\n\t\treturn 0, errors.New(\"actual value must not be NaN\")\n\t}\n\n\treturn math.Abs(af-bf) / math.Abs(af), nil\n}\n\n// InEpsilon asserts that expected and actual have a relative error less than epsilon\nfunc InEpsilon(t TestingT, expected, actual interface{}, epsilon float64, msgAndArgs ...interface{}) bool {\n\tif h, ok := t.(tHelper); ok {\n\t\th.Helper()\n\t}\n\tif math.IsNaN(epsilon) {\n\t\treturn Fail(t, \"epsilon must not be NaN\", msgAndArgs...)\n\t}\n\tactualEpsilon, err := calcRelativeError(expected, actual)\n\tif err != nil {","sourceCodeStart":1549,"sourceCodeEnd":1585,"githubUrl":"https://github.com/stretchr/testify/blob/001eb7946baf451879253643e4ce4b38eaa0d4a7/assert/assertions.go#L1549-L1585","documentation":"Returned by calcRelativeError (assert/assertions.go:1566) when the expected value converts to 0.0. Relative error is computed as |expected-actual|/|expected| (assert/assertions.go:1573), so a zero denominator is undefined; testify refuses to compute it. Surfaced through assert.InEpsilon.","triggerScenarios":"Calling assert.InEpsilon(t, 0.0, actual, eps) or assert.InEpsilon(t, int(0), actual, eps). Also when expected is a numeric type whose value happens to be zero.","commonSituations":"Asserting tolerance against a baseline/expected of zero (e.g. measuring drift from a zero starting point), or testing near-zero sensor readings where absolute tolerance, not relative, is appropriate.","solutions":["Use assert.InDelta(t, 0.0, actual, absTol) for absolute tolerance instead of relative when the expected baseline is zero.","If zero is genuinely the expected value, use assert.Equal(t, 0.0, actual) or assert.InDelta with a small absolute bound.","Shift the baseline so expected is non-zero before computing relative error."],"exampleFix":"// before\nassert.InEpsilon(t, 0.0, reading, 0.05)\n// after\nassert.InDelta(t, 0.0, reading, 0.05)","handlingStrategy":"validation","validationCode":"ef, ok := asFloat(expected)\nif ok && ef == 0 {\n    t.Log(\"expected is zero; using InDelta instead\")\n    assert.InDelta(t, expected, actual, absTol)\n    return\n}\nassert.InEpsilon(t, expected, actual, eps)","typeGuard":"func isNonZeroNumeric(v interface{}) bool {\n    f, ok := asFloat(v)\n    return ok && f != 0 && !math.IsNaN(f)\n}","tryCatchPattern":"// Choose assertion based on expected magnitude:\nif f, ok := asFloat(expected); ok && f == 0 {\n    assert.InDelta(t, expected, actual, absTol)\n} else {\n    assert.InEpsilon(t, expected, actual, eps)\n}","preventionTips":["Default to InDelta for absolute tolerance when baselines can be zero.","Parameterize tolerance helpers to pick InDelta vs InEpsilon by magnitude.","Document that InEpsilon is undefined for zero expected values."],"tags":["assertion","numeric","division-by-zero","in-epsilon"],"analyzedSha":"001eb7946baf451879253643e4ce4b38eaa0d4a7","analyzedAt":"2026-08-04T21:49:58.715Z","schemaVersion":2}