Если задача уже готова, await ничего не ждёт. Код идёт дальше на том же потоке. ConfigureAwait тут ни при чём, хотя за него голосовали 24%.
Как с посылкой.
Посылка уже лежит у двери — забрал и пошёл дальше. Это готовая задача.
Посылку ещё не привезли. Ты не ждёшь в прихожей, оставляешь записку "позвоните, как приедете" и уходишь по делам. Курьер позвонит, и дверь откроет тот, кто будет дома. Это задача, которая ещё не готова.
ConfigureAwait(false) дописывает в записку "открыть может кто угодно". Но если посылка уже у двери, записку никто не читает.
Теперь без посылок. Я запустил await Task.Delay(100) в консоли, WinForms и ASP.NET Core и посмотрел номер потока до и после:
Консоль до 2, после 5 WinForms до 2, после 2 ASP.NET Core тот же поток примерно в 9 запросах из 10
WinForms возвращает код в UI-поток через SynchronizationContext. В консоли и ASP.NET Core его нет, продолжает любой свободный поток. При 50 запросах разом в ASP.NET Core тот же поток совпал только в 10–16 из 50 🔥
Поэтому компилятор и не даёт написать await внутри lock. Лок привязан к потоку, а после await ты можешь оказаться на другом.
Нужны ещё такие квизы с простым разбором на следующий же день? Если наберётся куча 🌟, сделаю постоянной рубрикой

Дискуссия