# CSRF # #= require ./beforesend #= require ./prepare # # Adds CSRF tokens to AJAX requests and forms missing them. # # CSRF tokens must be set in the document head as meta tags. # # # # # The AJAX prefilter filter will run before all jQuery XHR requests and # allows the request to be modified. $(document).on 'ajaxBeforeSend', (event, xhr, settings) -> # Skip for cross domain requests. Other sites can't do much # with our token. return if settings.crossDomain # Skip for GET requests return if settings.type is 'GET' # Get token from meta element on the page. # # On Rails 3, `<%= csrf_meta_tags %>` will spit this out. if token = $('meta[name="csrf-token"]').attr 'content' # Send the token along in a header. xhr.setRequestHeader 'X-CSRF-Token', token # Listen for form submissions and inject hidden `authenticity_token` # input into forms missing them. $(document).on 'submit:prepare', 'form', -> form = $(this) # Don't handle remote requests. They'll have a header set instead. return if form.is 'form[data-remote]' # Skip for GET requests return if !this.method or this.method.toUpperCase() is 'GET' # Skip for cross domain requests. Other sites can't do much # with our token. return unless isSameOrigin form.attr 'action' # Get param token from meta elements on the page. # # On Rails 3, `<%= csrf_meta_tags %>` will spit these out. param = $('meta[name="csrf-param"]').attr 'content' token = $('meta[name="csrf-token"]').attr 'content' if param? and token? # Check if theres already a `authenticity_token` input field unless form.find("input[name=#{param}]")[0] input = document.createElement 'input' input.setAttribute 'type', 'hidden' input.setAttribute 'name', param input.setAttribute 'value', token form.prepend input return # Check if url is within the same origin policy. isSameOrigin = (url) -> a = document.createElement 'a' a.href = url origin = a.href.split('/', 3).join "/" location.href.indexOf(origin) is 0