{"record":{"id":"581487fe4c851d4e","repo":"mislav/will_paginate","slug":"the-collection-name-variable-appears-to-be-empt","errorCode":null,"errorMessage":"The #{collection_name} variable appears to be empty. Did you forget to pass the collection object for will_paginate?","messagePattern":"The #(.+?) variable appears to be empty\\. Did you forget to pass the collection object for will_paginate\\?","errorType":"exception","errorClass":"ArgumentError","httpStatus":null,"severity":"error","filePath":"lib/will_paginate/view_helpers/action_view.rb","lineNumber":94,"sourceCode":"        if Array === keys\n          defaults = keys.dup\n          key = defaults.shift\n        else\n          defaults = nil\n          key = keys\n        end\n        translate(key, **options.merge(:default => defaults, :scope => :will_paginate))\n      else\n        super\n      end\n    end\n\n    protected\n\n    def infer_collection_from_controller\n      collection_name = \"@#{controller.controller_name}\"\n      collection = instance_variable_get(collection_name)\n      raise ArgumentError, \"The #{collection_name} variable appears to be empty. Did you \" +\n        \"forget to pass the collection object for will_paginate?\" if collection.nil?\n      collection\n    end\n\n    class LinkRenderer < ViewHelpers::LinkRenderer\n      protected\n\n      GET_PARAMS_BLACKLIST = [:script_name, :original_script_name]\n\n      def default_url_params\n        {}\n      end\n\n      def url(page)\n        @base_url_params ||= begin\n          url_params = merge_get_params(default_url_params)\n          url_params[:only_path] = true\n          merge_optional_params(url_params)","sourceCodeStart":76,"sourceCodeEnd":112,"githubUrl":"https://github.com/mislav/will_paginate/blob/50017c3eb0712e7b3a53268a81e81a184b7a49f6/lib/will_paginate/view_helpers/action_view.rb#L76-L112","documentation":"The ActionView wrapper for will_paginate lets you call <%= will_paginate %> with no argument; it then infers the collection from the instance variable named after the controller (\"@#{controller.controller_name}\"). If that ivar is nil it raises ArgumentError telling you the variable 'appears to be empty' — meaning it was never assigned, not that the list has zero rows.","triggerScenarios":"PostsController#index that never runs @posts = Post.paginate(...), or assigns a differently named ivar (@list, @results) while the view relies on argument-less will_paginate; partials shared across controllers where controller_name doesn't match the ivar; copy-pasting a view into another controller without copying the ivar assignment.","commonSituations":"Renaming the ivar in the controller but not the view (or vice versa); refactoring index actions to local variables for render partial: locals; Typhpos like @post instead of @posts; a before_action that conditionally skips the assignment on some code path.","solutions":["Pass the collection explicitly: <%= will_paginate(@posts) %> — this removes the naming coupling entirely","Or make the controller assign the conventional ivar: @posts = Post.paginate(page: params[:page] || 1) in PostsController","In shared partials, always pass the collection as a local and render will_paginate posts or will_paginate(local_assigns[:posts])"],"exampleFix":"// before\n# controllers/posts_controller.rb\ndef index\n  @list = Post.paginate(page: params[:page] || 1)\nend\n# views/posts/index.html.erb\n<%= will_paginate %>\n\n// after\n# controllers/posts_controller.rb\ndef index\n  @posts = Post.paginate(page: params[:page] || 1)\nend\n# views/posts/index.html.erb\n<%= will_paginate(@posts) %>","handlingStrategy":"validation","validationCode":null,"typeGuard":null,"tryCatchPattern":"begin\n  will_paginate\nrescue ArgumentError => e\n  raise unless e.message.include?('appears to be empty')\n  nil # render nothing rather than 500 when the ivar was legitimately not set\nend","preventionTips":["Standardize: index actions assign the ivar named after the resource (@posts in PostsController) as Rails convention expects","Lint views for argument-less will_paginate calls in shared partials — require an explicit collection there","Cover each list action with a request spec asserting the ivar is assigned; this fails before the view ever infers"],"tags":["will-paginate","actionview","naming-convention","rails"],"backgroundTag":"nil-instance-variable","analyzedSha":"50017c3eb0712e7b3a53268a81e81a184b7a49f6","analyzedAt":"2026-08-21T19:50:58.546Z","schemaVersion":2},"datasetVersion":"2026-08-21T23:17:16.201Z"}