require-atomic-updates
Disallow assignments that use a value read before an await or a yield
total += await fetchPrice(id) reads total first, then waits. If two calls run at the same time, both start from the same total, and one of the additions is lost.
The rule checks async functions and generators. It reports an assignment to a variable or a property that was read before an await or a yield and not read again after it. A local variable that no other function uses isn't reported, because nothing else can change it during the wait.
Configure#
Off by default. To turn it on:
[lint.rules]
"require-atomic-updates" = "error" # or "warn"Every option, set to its default:
[lint.rules]
"require-atomic-updates" = ["error", {
allowProperties = false,
}]Examples#
let total = 0;
async function addPrice(id) {
total += await fetchPrice(id)Possible race condition: total might be reassigned based on an outdated value of total.;
}let total = 0;
async function addPrice(id) {
const price = await fetchPrice(id);
total += price;
}
async function sumPrices(ids) {
let sum = 0;
for (const id of ids) {
sum += await fetchPrice(id);
}
return sum;
}A property of a parameter is checked too, because the caller still holds the object:
async function loadUser(session) {
if (!session.user) {
session.user = await fetchUser(session.id)Possible race condition: session.user might be assigned based on an outdated state of session.;
}
}Check again after the wait:
async function loadUser(session) {
const user = await fetchUser(session.id);
if (!session.user) {
session.user = user;
}
}Options#
| Option | Default | What it does |
|---|---|---|
allowProperties | false | Don't report assignments to properties. Variables are still checked. |
{ "allowProperties": true }No problemsasync function loadUser(session) {
if (!session.user) {
session.user = await fetchUser(session.id);
}
}When not to use it#
The rule can't tell whether two calls ever overlap, so it also reports code where nothing else touches the value. If most reports are about properties of request or context objects, set allowProperties to true.