Выбор ответа Senior Потоки и синхронизация обновлено

AsyncLocal и ThreadStatic

Вопрос

Почему для хранения контекста запроса (например, correlation id) в async-коде используют AsyncLocal<T>, а не [ThreadStatic]?

Попробуйте сами

Выберите вариант, и откроется разбор.

Показать ответ и разбор

Коротко

Правильный ответ: AsyncLocal течёт через await, а поток после него может смениться. Значение [ThreadStatic] привязано к потоку ОС, а продолжение await может выполниться на любом потоке пула и увидит чужое или пустое значение.

Варианты ответа

  1. ThreadStatic не работает в .NET Core и помечен устаревшим
  2. AsyncLocal быстрее, потому что хранится в регистрах процессора
  3. AsyncLocal виден всем потокам приложения одновременно и сразу
  4. AsyncLocal течёт через await, а поток после него может сменитьсяправильный ответ

Разбор

Значение [ThreadStatic] привязано к потоку ОС, а продолжение await может выполниться на любом потоке пула и увидит чужое или пустое значение. AsyncLocal<T> хранится в ExecutionContext, который захватывается и восстанавливается в продолжениях, поэтому значение следует за логическим потоком выполнения. Изменения в дочерней асинхронной операции не видны родителю. На нём построены Activity.Current и IHttpContextAccessor. ThreadStatic в .NET Core работает, просто не подходит для async.

Ответьте сами, а не прочитайте

В тренажёре вопрос попадёт в повторения и вернётся, когда начнёт забываться. Плюс билеты с зачётом: 20 вопросов, не больше 2 ошибок.

Термины по теме