rails matchers bot ruby-on-rails ruby ruby-on-rails-4 rspec rspec-rails

ruby-on-rails - matchers - rspec ruby



Acceso al objeto de solicitud en las especificaciones de solicitud (2)

¿Cómo puedo configurar los encabezados de solicitud antes de hacer la solicitud en una especificación de solicitud?

Moveré las especificaciones del controlador para solicitar especificaciones en mi API usando Rails. Una cosa en la que estoy estancado es que no tengo acceso a un objeto de request para permitir las solicitudes.

En las especificaciones de mi controlador, tengo acceso a un método que he creado que firma un usuario específico:

def sign_in(user) token = user.api_keys.first.token # note the request object being used in the next line request.env["HTTP_AUTHORIZATION"] = ActionController::HttpAuthentication::Token.encode_credentials(token) end

Esto funciona bien en las especificaciones del controlador, puedo hacerlo de forma segura:

before { sign_in(user) } it { post :endpoint, params }

Pero en una especificación de solicitud, el objeto de request no está disponible. Si trato de:

before { sign_in(user) } it { post "/api/endpoint", params }

Recibo una request en mi método de ayuda como nil .

Sé que podría hacer:

it { post "/api/endpoint", {"HTTP_AUTHORIZATION" => ... } }

Pero esto parece mucho desorden en la especificación, especialmente en comparación con una especificación de controlador.

Intenté usar ActionDispatch::TestRequest::DEFAULT_ENV como lo sugiere esta respuesta , pero tampoco funcionó (obtengo un 401 ).


Si aún no está utilizando Rack::Test para esto, entonces debería hacerlo. Rack::Test es más adecuado que Capybara para probar las solicitudes API. Se puede configurar en su rspec/spec_helper.rb

RSpec.configure do |config| # ... config.include Rack::Test::Methods end

Cuando está configurado para usar Rack :: Test, puede establecer los encabezados antes de la solicitud, así:

it ''POST /api/enpoint authenticates successfully'' do header ''Authorization'', ''...'' post "/api/endpoint", params expect(last_response).to be_ok end

Esto estará accesible en su controlador como request.headers[''HTTP_AUTHORIZATION''] .

El código fuente de este método se puede encontrar aquí - https://github.com/brynary/rack-test/blob/master/lib/rack/test.rb#L127-L141


Si usa capybara para las especificaciones de solicitud, supongo que puede establecer encabezados como se sugiere aquí , sin embargo, es mejor realizar el inicio de sesión real a través del formulario HTML o la forma de autenticarse en su aplicación, porque las especificaciones de solicitud son de un nivel más alto que los controladores, y es por eso que normalmente no le permiten configurar manualmente los encabezados, cookies y otras cosas de bajo nivel.