Чтение документации о Play Framework и ReactiveMongo заставляет меня думать, что ReactiveMongo работает таким образом, что использует несколько потоков и никогда не блокирует.
Однако, похоже, что связь приложения Play с сервером Mongo должна произойти где-то в каком-то потоке. Как это реализовано? Ссылки на исходный код для Play, ReactiveMongo, Akka и т.д. Также были бы очень оценены.
Платформа Play содержит некоторую документацию об этом на этой странице о пулах потоков. Он начинается:
Структура воспроизведения - снизу вверх - асинхронная веб-фреймворк. Потоки обрабатываются асинхронно, используя итерации. Пулы потоков в Play настроены на использование меньше потоков, чем в традиционных веб-фреймворках, поскольку IO в play-core никогда не блокируется.
Затем он немного рассказывает об ReactiveMongo:
Наиболее распространенное место, которое типичное приложение Play будет блокировать, - это когда он разговаривает с базой данных. К сожалению, ни одна из основных баз данных не предоставляет асинхронные драйверы базы данных для JVM, поэтому для большинства баз данных единственным вариантом является использование блокировки ввода-вывода. A примечательным исключением является ReactiveMongo, драйвер для MongoDB, который использует библиотеку Plays Iteratee для общения с MongoDB.
Ниже приведена заметка об использовании Futures:
Обратите внимание, что у вас может возникнуть соблазн, поэтому вы можете заблокировать свой блокирующий код в Futures. Это не делает его не блокирующим, это просто означает, что блокировка произойдет в другом потоке. Вам все равно нужно убедиться, что пул потоков, который вы используете там, имеет достаточно потоков для обработки блокировки.
В документации Play есть аналогичная заметка на странице Обработка асинхронных результатов:
Вы не можете магически превратить синхронный IO в асинхронный, обернув его в Будущее. Если вы не можете изменить архитектуру приложений, чтобы избежать блокировки операций, в какой-то момент, что операция должна быть выполнена, и этот поток будет блокировать. Таким образом, помимо включения операции в будущее, необходимо настроить ее для запуска в отдельном контексте выполнения, который был настроен с достаточным количеством потоков для работы с ожидаемым concurrency.
В документации, по-видимому, говорится, что ReactiveMongo не блокирует, поэтому вам не нужно беспокоиться о том, что он поглощает много потоков в вашем пуле потоков. Но ReactiveMongo должен где-то общаться с сервером Mongo.
Как это сообщение реализовано так, что Mongo не использует потоки из пула потоков Play по умолчанию?
Еще раз ссылки на конкретные файлы в Play, ReactiveMongo, Akka и т.д., будет очень признателен.