2011-02-26 11 views
7

He una acción provocada por una petición AJAX generada por Ajax.InPlaceEditor o InPlaceCollectionEditor así:+ Rails 3.0.4 finaliza la sesión después de la petición AJAX

new Ajax.InPlaceCollectionEditor('agent_email', 'inspections/<%= @inspection.id %>/update_field', 
{ 
collection: [<% @agents.each do |agent| %> 
     '<%= agent.email %>',   
     <% end %>], 
    okText: 'Update', 
    cancelText: 'Never mind', 
    savingText: 'Updating...' 

}); 

En el otro extremo, la acción contiene esto:

def update_field 
    --some code here-- 
    if success 
    puts "stored change" 
    render :text => result 
    else 
    puts "did note change store" 
    render :text => inspection.errors.to_json, :status => 500 
    end 
end 

Una vez que se llega a alguno de los métodos de renderizado, la sesión expira y la próxima vez que el usuario envíe una solicitud, Devise los envía al inicio de sesión en la página.

Aunque estoy eximiendo update_field de la autenticación (before_filter :authenticate_user!, :except => :update_field), la sesión todavía se está restableciendo.

He mirado la respuesta a una pregunta muy similar en Devise session immediately expiring on .js call [AJAX], pero no resuelve mi problema en particular.

¿Alguna idea?

Respuesta

11

Tengo esto para trabajar por conseguir el código de http://weblog.rubyonrails.org/2011/2/8/csrf-protection-bypass-in-ruby-on-rails (prototipo): snippet.js

/* 
* Registers a callback which copies the csrf token into the 
* X-CSRF-Token header with each ajax request. Necessary to 
* work with rails applications which have fixed 
* CVE-2011-0447 
*/ 

Ajax.Responders.register({ 
onCreate: function(request) { 
    var csrf_meta_tag = $$('meta[name=csrf-token]')[0]; 

    if (csrf_meta_tag) { 
    var header = 'X-CSRF-Token', 
     token = csrf_meta_tag.readAttribute('content'); 

    if (!request.options.requestHeaders) { 
     request.options.requestHeaders = {}; 
    } 
    request.options.requestHeaders[header] = token; 
    } 
} 
}); 

... dentro de un bloque Javascript en mi application.html.erb:

<script type="text/javascript"> 
    (... the code from above) 
</script> 

Tampoco se olvide de añadir:

<%= csrf_meta_tag %> 

en el mismo archivo en la parte superior (si no está ya allí).

El documento "CSRF Protection Bypass in Ruby on Rails" explica por qué funciona esto.

Cuestiones relacionadas