This project is archived and is in readonly mode.
ActiveResource::Base.prefix isn't reset correctly when ActiveResource::Base.site is reset.
Reported by Matthew Moore | January 11th, 2009 @ 02:53 AM
If you need to set the values for ActiveResource.site with a URI that includes a path, ActiveResource::Base.prefix will be wrong.
Consider this example. If you have an active resource called MyActiveResource (e.g.: )
class MyActiveResource < ActiveResource::Base
end
Setting a site value, and then another site value will produce the wrong ActiveResource::Base.prefix value, if the site url has a path.
See this example:
MyActiveResource.site = "http://www.example.com/app1"
# => "http://www.example.com/app1"
MyActiveResource.prefix
# => "/app1/"
MyActiveResource.site = "http://www.example.com/app2"
# "http://www.example.com/app2"
MyActiveResource.prefix
# "/app1/" <---- BUG ----
MyActiveResource.site.path
# => "/app2" <-- Prefix above is wrong despite new, correct value of MyActiveResource.site.path
As you can see, even though you set a new site with a different
path, the prefix method is not updated with the new site.path
value, whereas it should be.
At first glance, this looks like it's because the first ActiveRecord::Base#prefix= call overrides the original prefix method with a new method, that retains the old value. Why does the prefix= override the prefix method with a new method??
# Sets the \prefix for a resource's nested URL (e.g., <tt>prefix/collectionname/1.xml</tt>).
# Default value is <tt>site.path</tt>.
def prefix=(value = '/')
# Replace :placeholders with '#{embedded options[:lookups]}'
prefix_call = value.gsub(/:\w+/) { |key| "\#{options[#{key}]}" }
# Clear prefix parameters in case they have been cached
@prefix_parameters = nil
# Redefine the new methods.
code = <<-end_code
def prefix_source() "#{value}" end
def prefix(options={}) "#{prefix_call}" end # <--- ????
end_code
silence_warnings { instance_eval code, __FILE__, __LINE__ }
rescue
logger.error "Couldn't set prefix: #{$!}\n #{code}"
raise
end
Comments and changes to this ticket
-
Matthew Moore January 11th, 2009 @ 03:36 AM
It seems odd to me that the prefix is stored in a method (by redefining a method when it's set), rather than a variable.
Was there any method to this madness? Why it shouldn't just be stored in a class variable?
-
Michael Koziarski January 12th, 2009 @ 05:25 AM
- Milestone cleared.
Short version is that class variables don't play nice with inheritance. So if you set it on ChildClass it overrides ParentClass
-
Michael Koziarski February 1st, 2009 @ 02:11 AM
- Assigned user changed from Michael Koziarski to Rick
Assigning to rick as he uses ares, feel free to remove the 2.3 blocker if it's not immediately obvious how to fix it.
-
Rick February 1st, 2009 @ 06:08 PM
Because #prefix has to take an options parameter. If you set it to something like "/projects/:project_id", the prefix method will look something like this:
def prefix(options = {}) "/projects/#{options[:project_id]}" end Message.prefix(:project_id => 1) # => "/projects/1"
-
Rick February 1st, 2009 @ 06:37 PM
- State changed from new to committed
I committed a fix to my rails fork, let me know if it works out.
Create your profile
Help contribute to this project by taking a few moments to create your personal profile. Create your profile »
<h2 style="font-size: 14px">Tickets have moved to Github</h2>
The new ticket tracker is available at <a href="https://github.com/rails/rails/issues">https://github.com/rails/rails/issues</a>