# no-magic-numbers

> Require numbers to be given a name instead of being used directly

A bare number in the middle of an expression doesn't tell you what it stands for. If the same number is used in several places, you have to find and change each one. A named constant explains the number and keeps it in one place.

The rule doesn't report the number a variable is declared with, the values in an object literal, a number assigned to a property, the second argument of `parseInt()`, or numbers in JSX. It reports everything else, including `0` and `1`.

{/* Generated by src/codegen/lint-rule-docs.ts. Do not edit this section. */}

## Configure

Off by default. To turn it on:

```toml bunfig.toml
[lint.rules]
"no-magic-numbers" = "error" # or "warn"
```

Every option, set to its default:

```toml bunfig.toml
[lint.rules]
"no-magic-numbers" = ["error", {
  ignore = [], # list of numbers or strings
  ignoreArrayIndexes = false,
  ignoreDefaultValues = false,
  ignoreClassFieldInitialValues = false,
  enforceConst = false,
  detectObjects = false,
  ignoreEnums = false,
  ignoreNumericLiteralTypes = false,
  ignoreReadonlyClassProperties = false,
  ignoreTypeIndexes = false,
}]
```

{/* End of the generated section. */}

## Examples

Reported:

{/* bad {"count": 2} */}
```js
function priceWithTax(price) {
  return price * 1.2;
}

setInterval(refresh, 60000);
```

Not reported:

{/* good */}
```js
const TAX_RATE = 1.2;
const ONE_MINUTE = 60000;

function priceWithTax(price) {
  return price * TAX_RATE;
}

setInterval(refresh, ONE_MINUTE);
```

{/* good */}
```jsx
const server = { port: 8080 };
server.timeout = 5000;
const quantity = parseInt(input.value, 10);
const grid = <Grid columns={3} />;
```

## Options

| Option | Default | What it does |
| --- | --- | --- |
| `ignore` | `[]` | Numbers that are never reported. Write a `bigint` as a string: `"100n"`. |
| `ignoreArrayIndexes` | `false` | Allow a number as an index: `items[0]`. |
| `ignoreDefaultValues` | `false` | Allow a number as a default value for a parameter or in destructuring. |
| `ignoreClassFieldInitialValues` | `false` | Allow a number as the initial value of a class field. |
| `enforceConst` | `false` | Report a variable that's declared with a number and isn't a `const`. |
| `detectObjects` | `false` | Also report numbers in object literals and numbers assigned to a property. |
| `ignoreEnums` | `false` | TypeScript: allow numbers in `enum` members. |
| `ignoreNumericLiteralTypes` | `false` | TypeScript: allow numbers in a type alias such as `type Dice = 1 \| 2`. |
| `ignoreReadonlyClassProperties` | `false` | TypeScript: allow numbers in `readonly` class properties. |
| `ignoreTypeIndexes` | `false` | TypeScript: allow a number as the index of a type: `Row[0]`. |

{/* good {"options": [{"ignore": [0, 1]}]} */}
```js
const isLast = index === items.length - 1;
const isEmpty = items.length === 0;
```

Each of these lines is reported by default:

{/* bad {"count": 3} */}
```js
const first = items[0];
function retry(times = 3) {}
class Pool { size = 10; }
```

{/* good {"options": [{"ignoreArrayIndexes": true, "ignoreDefaultValues": true, "ignoreClassFieldInitialValues": true}]} */}
```js
const first = items[0];
function retry(times = 3) {}
class Pool { size = 10; }
```

{/* bad {"options": [{"enforceConst": true}]} */}
```js
let timeout = 5000;
```

{/* bad {"options": [{"detectObjects": true}], "count": 2} */}
```js
const server = { port: 8080 };
server.timeout = 5000;
```

The same goes for TypeScript. Each of these lines is reported by default:

{/* bad {"count": 5} */}
```ts
enum Level { Debug = 10 }
type Dice = 1 | 2;
class Pool { readonly size = 10; }
type First = Row[0];
```

{/* good {"options": [{"ignoreEnums": true, "ignoreNumericLiteralTypes": true, "ignoreReadonlyClassProperties": true, "ignoreTypeIndexes": true}]} */}
```ts
enum Level { Debug = 10 }
type Dice = 1 | 2;
class Pool { readonly size = 10; }
type First = Row[0];
```

## When not to use it

Code that's full of numbers with an obvious meaning, such as math, geometry or test data, gets a report on nearly every line.
