Почему Rails допускает двойной рендеринг? - PullRequest
0 голосов
/ 26 апреля 2018
class SomeController < ApplicationController
  before_action :api_limit

  def new
    if user.can_access_foo?
      render 'foo'
    end

    if user.can_access_bar?
      render 'bar'
    end

    if user.can_access_hello?
      render 'hello'
    end
  end

  def api_limit
    render 'exceed_limit_error'
    # code in action will not be executed.
  end
end

Если в before_filter существует render или redirect_to, действие не будет выполнено.Короче говоря, нет риска двойного рендеринга.

См. Руководство по Rails для контроллеров :

Если фильтр «до» отрисовывает или перенаправляет,действие не будет работать.Если после этого фильтра планируется запустить дополнительные фильтры, они также будут отменены.

Однако, почему Rails допускает двойной рендеринг в действии?

Возьмем следующий код в качестве примера.Исключение двойного рендеринга будет вызываться Rails, когда пользователь может получить доступ к foo, bar или hello.

class SomeController < ApplicationController
  before_action :callback

  def new
    if user.can_access_foo?
      render 'foo' 
      # From my understanding, following render should 
      # be ignored if this step is successfully performed.
    end

    if user.can_access_bar?
      render 'bar'
    end

    if user.can_access_hello?
      render 'hello'
    end
  end
end

Почему бы не ответить немедленно и остановить цикл запроса после завершения render 'foo'?Это звучит более разумно.

1 Ответ

0 голосов
/ 26 апреля 2018

Причина, по которой оператор render в действии не возвращает выполнение кода, состоит в том, что разумным вариантом использования является то, что после рендеринга в действии существует дополнительный (не отображающий) код.

Причина, по которой рендеринг в обратном вызове before_action не позволяет выполнению кода войти в действие, состоит в том, что это предполагает, что у вас есть действия, которые имеют пути к коду, которые не рендерится и не перенаправляются (в противном случае вы получитедвойная ошибка рендеринга).Этот путь кода в действии является гораздо менее разумным вариантом использования, потому что он будет полагаться на фильтр «до», который уже запустил и выполнил рендеринг.

Намерение структуры действий и фильтров Rails вКонтроллеры в том, что они не так тесно связаны.Обычно фильтр не знает о том, какое действие будет выполнено после него, а действие не знает о том, какие фильтры сработали до его запуска.Таким образом, чтобы заставить их координировать то, что делает рендеринг, это сломало бы эту слабую связь.Каждое действие должно предполагать, что рендеринг является неотъемлемой частью его роли, поэтому не имеет смысла запускать действие, если фильтр уже отрендерен.

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