| Module | Ardes::ResourcesController::InstanceMethods |
| In: |
lib/ardes/resources_controller.rb
|
# File lib/ardes/resources_controller.rb, line 564
564: def self.included(base)
565: base.class_eval do
566: protected
567: # we define the find|new_resource(s) methods only if they're not already defined
568: # this allows abstract controllers to define the resource service methods
569: unless instance_methods.include?('find_resources')
570: # finds the collection of resources
571: def find_resources
572: resource_service.find :all
573: end
574: end
575:
576: unless instance_methods.include?('find_resource')
577: # finds the resource, using the passed id
578: def find_resource(id = params[:id])
579: resource_service.find id
580: end
581: end
582:
583: unless instance_methods.include?('new_resource')
584: # makes a new resource, optionally using the passed hash
585: def new_resource(attributes = (params[resource_name] || {}))
586: resource_service.new attributes
587: end
588: end
589: end
590: base.send :hide_action, *instance_methods
591: end
# File lib/ardes/resources_controller.rb, line 597
597: def name_prefix
598: @name_prefix ||= ''
599: end
Has the resource been saved successfully? If the record has not had validation attempted, it is saved. Returns true if the record is not new, and there are no errors
# File lib/ardes/resources_controller.rb, line 671
671: def resource_saved?
672: resource.save unless resource.validation_attempted?
673: resource.saved?
674: end
returns the resource service for the controller - this will be lazilly created to a ResourceService, or a SingletonResourceService (if :singleton => true)
# File lib/ardes/resources_controller.rb, line 649
649: def resource_service
650: @resource_service ||= resource_specification.singleton? ? SingletonResourceService.new(self) : ResourceService.new(self)
651: end
# File lib/ardes/resources_controller.rb, line 593
593: def resource_service=(service)
594: @resource_service = service
595: end
returns the instance resource_specification
# File lib/ardes/resources_controller.rb, line 654
654: def resource_specification
655: self.class.resource_specification
656: end
DEPRECATED: just use resource.save
# File lib/ardes/resources_controller.rb, line 677
677: def save_resource
678: resource.save
679: end
returns the all route segments except for the ones corresponding to the current resource and action. Also remove any route segments from the front which correspond to modules (namespaces)
# File lib/ardes/resources_controller.rb, line 701
701: def enclosing_segments
702: segments = remove_namespaces_from_segments(recognized_route.segments.dup)
703: while segments.size > 0
704: segment = segments.pop
705: return segments if segment.is_a?(::ActionController::Routing::StaticSegment) && segment.value == resource_specification.segment
706: end
707: ResourcesController.raise_missing_segment(self)
708: end
# File lib/ardes/resources_controller.rb, line 785
785: def load_enclosing_resource_from_specification(spec)
786: spec.segment == route_enclosing_names[enclosing_resources.size].first or ResourcesController.raise_resource_mismatch(self)
787: returning spec.find_from(self) do |resource|
788: update_name_prefix(spec.name_prefix)
789: enclosing_resources << resource
790: enclosing_collection_resources << resource unless spec.singleton?
791: instance_variable_set("@#{spec.name}", resource)
792: instance_variable_set("@#{spec.as}", resource) if spec.as
793: end
794: end
this is the before_filter that loads all specified and wildcard resources
# File lib/ardes/resources_controller.rb, line 740
740: def load_enclosing_resources
741: specifications.each_with_index do |spec, idx|
742: case spec
743: when '*' then load_wildcards_from(idx)
744: when /^\?(.*)/ then load_wildcard($1)
745: else load_enclosing_resource_from_specification(spec)
746: end
747: end
748: end
load a wildcard resource by either
Optionally takes a variable name to set the instance variable as (for polymorphic use)
# File lib/ardes/resources_controller.rb, line 754
754: def load_wildcard(as = nil)
755: route_enclosing_names[enclosing_resources.size] or ResourcesController.raise_resource_mismatch(self)
756: segment, singleton = *route_enclosing_names[enclosing_resources.size]
757: if resource_specification_map[segment]
758: spec = resource_specification_map[segment]
759: spec = returning(spec.dup) {|s| s.as = as} if as
760: else
761: spec = Specification.new(singleton ? segment : segment.singularize, :singleton => singleton, :as => as)
762: end
763: load_enclosing_resource_from_specification(spec)
764: end
loads a series of wildcard resources, from the specified specification idx
To do this, we need to figure out where the next specified resource is and how many single wildcards are prior to that. What is left over from the current route enclosing names will be the number of wildcards we need to load
# File lib/ardes/resources_controller.rb, line 771
771: def load_wildcards_from(start)
772: specs = specifications.slice(start..-1)
773: encls = route_enclosing_names.slice(enclosing_resources.size..-1)
774:
775: if spec = specs.find {|s| s.is_a?(Specification)}
776: spec_seg = encls.index([spec.segment, spec.singleton?]) or ResourcesController.raise_resource_mismatch(self)
777: number_of_wildcards = spec_seg - (specs.index(spec) -1)
778: else
779: number_of_wildcards = encls.length - (specs.length - 1)
780: end
781:
782: number_of_wildcards.times { load_wildcard }
783: end
returns the route that was used to invoke this controller and current action. The path is found first from params[:resource_path] if it exists, and then from the request.path. Likewise the method is found from params[:resource_method]
params[:erp] == params[:resource_path] for BC
# File lib/ardes/resources_controller.rb, line 687
687: def recognized_route
688: unless @recognized_route
689: path = params[:resource_path] || params[:erp] || request.path
690: environment = ::ActionController::Routing::Routes.extract_request_environment(request)
691: environment.merge!(:method => params[:resource_method]) if params[:resource_method]
692: @recognized_route ||= ::ActionController::Routing::Routes.routes_for_controller_and_action(controller_path, action_name).find do |route|
693: route.recognize(path, environment)
694: end or ResourcesController.raise_no_recognized_route(self)
695: end
696: @recognized_route
697: end
shift namespaces from segments, update the name_prefix accordingly for outgoing routes.
# File lib/ardes/resources_controller.rb, line 711
711: def remove_namespaces_from_segments(segments)
712: namespaces = controller_path.sub(controller_name,'').sub(/\/$/,'').split('/')
713: while namespaces.size > 0
714: if segments[0].is_a?(ActionController::Routing::DividerSegment) && segments[1].is_a?(ActionController::Routing::StaticSegment) && segments[1].value == namespaces.first
715: segments.shift; segments.shift # shift the '/' & 'namespace' segments
716: update_name_prefix("#{namespaces.shift}_")
717: else
718: break
719: end
720: end
721: segments
722: end
Returns an array of pairs [<name>, <singleton?>] e.g. [[users, false], [blog, true], [posts, false]] corresponding to the enclosing resource route segments
This is used to map resources and automatically load resources.
# File lib/ardes/resources_controller.rb, line 728
728: def route_enclosing_names
729: @route_enclosing_names ||= returning(Array.new) do |req|
730: enclosing_segments.each do |segment|
731: unless segment.is_optional or segment.is_a?(::ActionController::Routing::DividerSegment)
732: req << [segment.value, true] if segment.is_a?(::ActionController::Routing::StaticSegment)
733: req.last[1] = false if segment.is_a?(::ActionController::Routing::DynamicSegment)
734: end
735: end
736: end
737: end
The name prefix is used for forwarding urls and will be different depending on which route the controller was invoked by. The resource specifications build up the name prefix as the resources are loaded.
# File lib/ardes/resources_controller.rb, line 799
799: def update_name_prefix(name_prefix)
800: @name_prefix = "#{@name_prefix}#{name_prefix}"
801: end