Active Resource can make use of HTTP authentication set at the class level. For instance:
class Resource < ActiveResource::Base
end
Resource.user = 'user'
Resource.password = 'password'
or
Resource.site = "http://user:password@site.com/"
But what if I use different HTTP authentication based on which user is logged in? If I change Resource.user and Resource.password, is that going to cause a race condition where requests from one thread suddenly start using the authentication of a user whose requests are running simultaneously in a different thread? Or is this a non-issue (as long as I reset the authentication between requests) because rails servers are not multithreaded?
Even if there's no thread safety problem, it still seems risky that if I fail to reset them, the previous user's credentials will be used automatically by future requests.
Update: After being frustrated with ActiveResource, I wrote my own REST library:
https://github.com/DeepWebTechnologies/well_rested
Monkey patch the host
, user
and password
methods of ActiveResource::Base
class:
class ActiveResource::Base
# store the attribute value in a thread local variable
class << self
%w(host user password).each do |attr|
define_method(attr) do
Thread.current["active_resource.#{attr}"]
end
define_method("#{attr}=") do |val|
Thread.current["active_resource.#{attr}"] = val
end
end
end
end
Now set the credentials in every request
class ApplicationController < ActionController::Base
around_filter :set_api_credentials
private
# set the credentials in every request
def set_api_credentials
ActiveResource::Base.host,
ActiveResource::Base.user,
ActiveResource::Base.password = current_user_credentials
yield
ensure
ActiveResource::Base.host =
ActiveResource::Base.user =
ActiveResource::Base.password = nil
end
DEFAULT_HOST, DEFAULT_USER, DEFAULT_PASSWORD= [
"http://www.foo.com", "user1", "user78102" ]
def current_user_credentials
current_user.present? ?
[ current_user.host, current_user.login, current_user.password] :
[ DEFAULT_HOST, DEFAULT_USER, DEFAULT_PASSWORD]
end
end
As of Active Resource 4.1.0, those settings are thread local, so this example would not cause a race condition anymore.
This is the relevant commit if anyone is interested: https://github.com/rails/activeresource/commit/538588ddba9ffc9bf356790e9186dc7e6adad12f