Блокировка ввода-вывода / Ruby on Rails - PullRequest
11 голосов
/ 21 января 2012

Я собираюсь написать веб-приложение на Rails. Каждый сделанный пользователем запрос будет зависеть от вызываемого внешнего API. Этот внешний API может быть очень медленным (2-3 секунды), поэтому очевидно, что это повлияет на отдельный запрос.

В течение этого времени, когда код ожидает возврата внешнего API, будут ли заблокированы дальнейшие запросы пользователей?

Просто для дальнейшего разъяснения, поскольку, похоже, есть некоторая путаница, вот модель, которую я ожидаю:

  1. Алиса делает запрос в мое веб-приложение. Для этого производится вызов API-сервера A. API-сервер A работает медленно и занимает 3 секунды.
  2. В течение этого времени ожидания, когда приложение Rails вызывает API-сервер A, Боб делает запрос, который должен отправить запрос на API-сервер B.

Не собирается ли интерпретатор Ruby (1.9.3) (или что-то в среде Rails 3.x) заблокировать запрос Боба, требуя, чтобы он дождался выполнения запроса Алисы?

Ответы [ 3 ]

7 голосов
/ 21 января 2012

Если вы используете только один однопоточный, не-четный сервер (или не используете чётный ввод-вывод с чётным сервером), да. Среди других решений, использующих Thin и EM-Synchrony , этого избежать.

Разработка, на основе вашего обновления:

Нет, ни Ruby, ни Rails не приведут к блокировке вашего приложения. Вы пропустили ту часть, которая будет, тем не менее: веб-сервер. Вам нужно либо несколько процессов, несколько потоков, либо сервер с четными данными в сочетании с выполнением запросов веб-службы с библиотекой с вечерними операциями ввода-вывода.

@ alexd описано с использованием нескольких процессов. Лично я предпочитаю четный сервер, потому что мне не нужно заранее знать / угадывать, сколько параллельных запросов у меня может быть (или использовать что-то, что ускоряет процессы в зависимости от нагрузки). thin процесс может обслуживать тонны параллельных запросов.

3 голосов
/ 21 января 2012

Ответ на ваш вопрос зависит от сервера, на котором работает приложение Rails.Что вы используете прямо сейчас?Тонкий?Unicorn?Apache + Passenger?

Я искренне рекомендую Unicorn для вашей ситуации - он позволяет очень легко запускать несколько серверных процессов параллельно, и вы можете настроить количество параллельных процессов, просто изменив число в файле конфигурации,Пока один работник Unicorn обрабатывает запрос Алисы с высокой задержкой, другой работник Unicorn может использовать ваши свободные циклы ЦП для обработки запроса Боба.

0 голосов
/ 21 января 2012

Скорее всего, да. Очевидно, что есть способы обойти это, но ни один из них не является легким.

Лучший вопрос: зачем вам нужно использовать внешний API при каждом запросе? Почему бы не реализовать слой кэша между вашим Rails-приложением и внешним API и использовать его для большинства запросов?

Таким образом, с некоторой настраиваемой логикой для истечения срока действия кэша у вас будет быстрое приложение Rails, и вы все равно сможете использовать службу внешнего API.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...