add request header on backbone
Solution 1
Models in Backbone retrieve, update, and destroy data using the methods fetch
, save
, and destroy
. These methods delegate the actual request portion to Backbone.sync. Under the hood, all Backbone.sync
is doing is creating an ajax request using jQuery. In order to incorporate your Basic HTTP authentication you have a couple of options.
fetch
, save
, and destroy
all accept an additional parameter [options]
. These [options]
are simply a dictionary of jQuery request options that get included into jQuery ajax call that is made. This means you can easily define a simple method which appends the authentication:
sendAuthentication = function (xhr) {
var user = "myusername";// your actual username
var pass = "mypassword";// your actual password
var token = user.concat(":", pass);
xhr.setRequestHeader('Authorization', ("Basic ".concat(btoa(token))));
}
And include it in each fetch
, save
, and destroy
call you make. Like so:
fetch({
beforeSend: sendAuthentication
});
This can create quite a bit of repetition. Another option could be to override the Backbone.sync
method, copy the original code and just include the beforeSend
option into each jQuery ajax request that is made.
Hope this helps!
Solution 2
The easiest way to add request header in Backbone.js is to just pass them over to the fetch method as parameters, e.g.
MyCollection.fetch( { headers: {'Authorization' :'Basic USERNAME:PASSWORD'} } );
Solution 3
One option might be to use the jQuery ajaxSetup, All Backbone requests will eventually use the underlying jQuery ajax. The benefit of this approach is that you only have to add it one place.
$.ajaxSetup({
headers: { 'Authorization' :'Basic USERNAME:PASSWORD' }
});
Edit 2nd Jan 2018 For complex web applications this may not be the best approach, see comments below. Leaving the answer here for references sake.
Solution 4
You could override Backbone sync method.
#coffeescript
_sync = Backbone.sync
Backbone.sync = (method, model, options) ->
options.beforeSend = (xhr) ->
xhr.setRequestHeader('X-Auth-Token_or_other_header' , your_hash_key)
#make sure your server accepts X-Auth-Token_or_other_header!!
#calling the original sync function so we only overriding what we need
_sync.call( this, method, model, options )
Solution 5
Backbone.$.ajaxSetup({
headers: {'Authorization' :'Basic USERNAME:PASSWORD'}
});
This code set headers to Backbone ajax, so they will be sent with every Backbone.sync. You will be able to send headers without using xhr.setRequestHeader
with every sync call.
So you don't need to do the following every time:
MyCollection.fetch({ headers: {'Authorization' :'Basic USERNAME:PASSWORD'} } );
You can just do
MyCollection.fetch();
Maybe it's kind of hack but it works perfectly for my system.
n0minal
Updated on July 09, 2022Comments
-
n0minal almost 2 years
My server has a manual authorization. I need to put the username/password of my server to my backbone request inorder for it to go through. How may i do this? Any ideas? Thank you
-
n0minal about 12 yearstried your code. but there's no response. it doesn't call the service.
-
shanewwarren about 12 yearsNo response at all? Or are you receiving a 401 response code?
-
n0minal about 12 yearsnope. anyways. can you give me a sample code on how to override the backbone.sync to headers?
-
MusikPolice about 11 yearsCan you provide an example of the backbone.js code that you wrote for this implementation? I'm having a problem getting it to work. You can see my progress in this question
-
albertpeiro almost 11 yearsThis worked for me, surprisingly! And it's not in the docs by the time I'm typing just if anyone wondered. Extremely simple way to handle it ;) amazing. >thanks!
-
dstarh over 10 yearsthat works unless username has a : in it, you really should base64 encode username:password
-
chug2k over 10 yearsI wouldn't copy the original Backbone.sync method. You can do something like what's suggested in japhr.blogspot.com/2011/10/…, but basically just override
options
, and callBackbone.Model.prototype.fetch.call(this, options)
. -
Wally Altman almost 9 yearsPerhaps you could give an explanation as to how this answers the question?
-
Cristian C. about 8 yearsI like your solution! But in the return line I would call
Backbone.Model.prototype.sync.apply(this, arguments)
instead. -
sebastian-greco about 8 years@cristian-conedera You are right, that would be a more elegant and correct way. Changed the code as you suggested
-
Emile Bergeron almost 8 yearsI would just add a call to the original
beforeSend
option (if passed) inside the new beforeSend callback. See the annotated source for reference: backbonejs.org/docs/backbone.html#section-179 -
Emile Bergeron over 6 yearsWhile it looks like it could work, don't use this for the reasons I described in another answer.
-
Emile Bergeron over 6 yearsIt is a hack that shouldn't be used for reasons explained in another answer of mine. It's also the same answer as the
$.ajaxSetup
one above. -
Emile Bergeron over 6 yearsThat's a good way, but instead of overwriting the
sync
function, you should override it and call the parent one which is not guaranteed to beBackbone.sync
. -
Emile Bergeron over 6 yearsThat's the same answer as the
fetch
example above, but without any explanation. -
Andy Polhill over 6 yearsI'd be inclined to agree, my answer is pretty old now. The only thing I would say is if you are working on a simple experiment with one data source this would be a quick way of getting going. So I might leave it here for reference.
-
Ziko over 4 yearsIs there a way to define the response interceptor? Something like ajaxError?