protect_from_forgery authenticity ruby-on-rails ruby ruby-on-rails-4 authenticity-token

ruby on rails - authenticity - Rails 4 Autenticidad Token



can''t verify csrf token authenticity (13)

Estaba trabajando en una nueva aplicación de Rails 4 (en Ruby 2.0.0-p0) cuando tuve algunos problemas de token de autenticidad.

Mientras escribía un controlador que responde a json (usando el método respond_to class), llegué a la acción de create Comencé a obtener excepciones de ActionController::InvalidAuthenticityToken cuando intenté crear un registro usando curl .

Me aseguré de establecer -H "Content-Type: application/json" y configuré los datos con -d "<my data here>" pero aún así no -d "<my data here>" suerte.

Intenté escribir el mismo controlador utilizando Rails 3.2 (en Ruby 1.9.3) y no tuve ningún problema de token de autenticidad. Busqué por todas partes y vi que había algunos cambios con tokens de autenticidad en Rails 4. Por lo que entiendo, ¿ya no se insertan automáticamente en los formularios? Supongo que esto está afectando de alguna manera a los tipos de contenido no HTML.

¿Hay alguna forma de evitar esto sin tener que solicitar un formulario HTML, arrebatando el token de autenticidad y luego haciendo otra solicitud con ese token? ¿O me estoy perdiendo algo que es completamente obvio?

Edición: Acabo de intentar crear un nuevo registro en una nueva aplicación de Rails 4 usando un andamio sin cambiar nada y me estoy topando con el mismo problema, así que supongo que no es algo que hice.


¿Has probado?

protect_from_forgery with: :null_session, if: Proc.new {|c| c.request.format.json? }


Agregando la siguiente línea en el formulario trabajado para mí:

<%= hidden_field_tag :authenticity_token, form_authenticity_token %>


Agregue authenticity_token: true a la etiqueta de formulario


Creo que lo acabo de descubrir. He cambiado el (nuevo) por defecto

protect_from_forgery with: :exception

a

protect_from_forgery with: :null_session

según el comentario en ApplicationController .

# Prevent CSRF attacks by raising an exception. # For APIs, you may want to use :null_session instead.

Puede ver la diferencia mirando la fuente de request_forgery_protecton.rb o, más específicamente, las siguientes líneas:

En Rieles 3.2 :

# This is the method that defines the application behavior when a request is found to be unverified. # By default, /Rails resets the session when it finds an unverified request. def handle_unverified_request reset_session end

En los carriles 4 :

def handle_unverified_request forgery_protection_strategy.new(self).handle_unverified_request end

Que llamará a lo siguiente :

def handle_unverified_request raise ActionController::InvalidAuthenticityToken end


Cuando define su propio formulario html, debe incluir la cadena de token de autenticación, que debe enviarse al controlador por razones de seguridad. Si utiliza el asistente de formulario Rails para generar el token de autenticidad, se agregará al formulario de la siguiente manera.

<form accept-charset="UTF-8" action="/login/signin" method="post"> <div style="display:none"> <input name="utf8" type="hidden" value="&#x2713;" /> <input name="authenticity_token" type="hidden" value="x37DrAAwyIIb7s+w2+AdoCR8cAJIpQhIetKRrPgG5VA="> </div> ... </form>

Por lo tanto, la solución al problema es agregar el campo authenticity_token o usar guías de formularios en lugar de comprometer la seguridad, etc.


En lugar de desactivar la protección csrf, es mejor agregar la siguiente línea de código en el formulario

<%= tag(:input, :type => "hidden", :name => request_forgery_protection_token.to_s, :value => form_authenticity_token) %>

y si está usando form_for o form_tag para generar el formulario, entonces agregará automáticamente la línea de código anterior en el formulario


Encontré el mismo problema. Se corrigió agregando a mi controlador:

skip_before_filter :verify_authenticity_token, if: :json_request?



Estas características se agregaron para fines de seguridad y protección contra falsificaciones.
Sin embargo, para responder a su pregunta, aquí hay algunas entradas. Puede agregar estas líneas después de su nombre del controlador.

Al igual que,

class NameController < ApplicationController skip_before_action :verify_authenticity_token

Aquí hay algunas líneas para diferentes versiones de rieles.

Rieles 3

skip_before_filter: verify_authenticity_token

Rieles 4 :

skip_before_action: verify_authenticity_token


Si pretende deshabilitar esta función de seguridad para todas las rutinas de controlador, puede cambiar el valor de protect_from_forgery a : null_session en su archivo application_controller.rb.

Al igual que,

class ApplicationController < ActionController::Base protect_from_forgery with: :null_session end



No creo que sea bueno desactivar la protección CSRF siempre y cuando no implementes una API exclusivamente.

Al consultar la documentación de la API de Rails 4 para api.rubyonrails.org/classes/ActionController/… , descubrí que puede desactivar la protección falsificada por controlador o por método.

Por ejemplo, para desactivar la protección CSRF para los métodos que puede utilizar

class FooController < ApplicationController protect_from_forgery except: :index


Si está utilizando jQuery con rieles, tenga cuidado de no permitir la entrada a métodos sin verificar el token de autenticidad.

jquery-ujs puede gestionar los tokens por ti

Ya deberías tenerlo como parte de la gema jquery-rails, pero es posible que tengas que incluirlo en application.js con

//= require jquery_ujs

Eso es todo lo que necesita: su llamada ajax ahora debería funcionar

Para obtener más información, consulte: https://github.com/rails/jquery-ujs


Todas mis pruebas funcionaron bien. Pero por alguna razón había configurado mi variable de entorno como no-test:

export RAILS_ENV=something_non_test

Olvidé desactivar esta variable debido a que comencé a obtener la excepción ActionController::InvalidAuthenticityToken .

Después de desactivar $RAILS_ENV , mis pruebas comenzaron a funcionar nuevamente.