From f1cd9e7298ce0c11debd48d5812df010bab8b5c9 Mon Sep 17 00:00:00 2001 From: Anton Khorev Date: Fri, 8 Aug 2025 20:59:32 +0300 Subject: [PATCH] Remove classic pagination --- app/helpers/browse_helper.rb | 23 -- config/application.rb | 2 +- config/initializers/classic_pagination.rb | 33 -- lib/classic_pagination/pagination.rb | 422 -------------------- lib/classic_pagination/pagination_helper.rb | 169 -------- 5 files changed, 1 insertion(+), 648 deletions(-) delete mode 100644 config/initializers/classic_pagination.rb delete mode 100644 lib/classic_pagination/pagination.rb delete mode 100644 lib/classic_pagination/pagination_helper.rb diff --git a/app/helpers/browse_helper.rb b/app/helpers/browse_helper.rb index e462eb61b..c93d16293 100644 --- a/app/helpers/browse_helper.rb +++ b/app/helpers/browse_helper.rb @@ -70,29 +70,6 @@ module BrowseHelper "nofollow" if object.tags.empty? end - def sidebar_classic_pagination(pages, page_param) - max_width_for_default_padding = 35 - - width = 0 - pagination_items(pages, {}).each do |(body)| - width += 2 # padding width - width += body.length - end - link_classes = ["page-link", { "px-1" => width > max_width_for_default_padding }] - - tag.ul :class => "pagination pagination-sm mb-2" do - pagination_items(pages, {}).each do |body, page_or_class| - linked = !(page_or_class.is_a? String) - link = if linked - link_to body, url_for(page_param => page_or_class.number), :class => link_classes, **yield(page_or_class) - else - tag.span body, :class => link_classes - end - concat tag.li link, :class => ["page-item", { page_or_class => !linked }] - end - end - end - private def feature_name(tags) diff --git a/config/application.rb b/config/application.rb index 463561eef..d60ad4c1b 100644 --- a/config/application.rb +++ b/config/application.rb @@ -14,7 +14,7 @@ module OpenStreetMap # Please, add to the `ignore` list any other `lib` subdirectories that do # not contain `.rb` files, or that should not be reloaded or eager loaded. # Common ones are `templates`, `generators`, or `middleware`, for example. - config.autoload_lib(:ignore => %w[assets classic_pagination tasks]) + config.autoload_lib(:ignore => %w[assets tasks]) # Configuration for the application, engines, and railties goes here. # diff --git a/config/initializers/classic_pagination.rb b/config/initializers/classic_pagination.rb deleted file mode 100644 index d87993a2b..000000000 --- a/config/initializers/classic_pagination.rb +++ /dev/null @@ -1,33 +0,0 @@ -#-- -# Copyright (c) 2004-2006 David Heinemeier Hansson -# -# Permission is hereby granted, free of charge, to any person obtaining -# a copy of this software and associated documentation files (the -# "Software"), to deal in the Software without restriction, including -# without limitation the rights to use, copy, modify, merge, publish, -# distribute, sublicense, and/or sell copies of the Software, and to -# permit persons to whom the Software is furnished to do so, subject to -# the following conditions: -# -# The above copyright notice and this permission notice shall be -# included in all copies or substantial portions of the Software. -# -# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND -# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE -# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION -# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION -# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -#++ - -require "classic_pagination/pagination" -require "classic_pagination/pagination_helper" - -ActionController::Base.class_eval do - include ActionController::Pagination -end - -ActionView::Base.class_eval do - include ActionView::Helpers::PaginationHelper -end diff --git a/lib/classic_pagination/pagination.rb b/lib/classic_pagination/pagination.rb deleted file mode 100644 index 97f0530a8..000000000 --- a/lib/classic_pagination/pagination.rb +++ /dev/null @@ -1,422 +0,0 @@ -module ActionController - # === Action Pack pagination for Active Record collections - # - # The Pagination module aids in the process of paging large collections of - # Active Record objects. It offers macro-style automatic fetching of your - # model for multiple views, or explicit fetching for single actions. And if - # the magic isn't flexible enough for your needs, you can create your own - # paginators with a minimal amount of code. - # - # The Pagination module can handle as much or as little as you wish. In the - # controller, have it automatically query your model for pagination; or, - # if you prefer, create Paginator objects yourself. - # - # Pagination is included automatically for all controllers. - # - # For help rendering pagination links, see - # ActionView::Helpers::PaginationHelper. - # - # ==== Automatic pagination for every action in a controller - # - # class PersonController < ApplicationController - # model :person - # - # paginate :people, :order => 'last_name, first_name', - # :per_page => 20 - # - # # ... - # end - # - # Each action in this controller now has access to a @people - # instance variable, which is an ordered collection of model objects for the - # current page (at most 20, sorted by last name and first name), and a - # @person_pages Paginator instance. The current page is determined - # by the params[:page] variable. - # - # ==== Pagination for a single action - # - # def list - # @person_pages, @people = - # paginate :people, :order => 'last_name, first_name' - # end - # - # Like the previous example, but explicitly creates @person_pages - # and @people for a single action, and uses the default of 10 items - # per page. - # - # ==== Custom/"classic" pagination - # - # def list - # @person_pages = Paginator.new self, Person.count, 10, params[:page] - # @people = Person.find :all, :order => 'last_name, first_name', - # :limit => @person_pages.items_per_page, - # :offset => @person_pages.current.offset - # end - # - # Explicitly creates the paginator from the previous example and uses - # Paginator#to_sql to retrieve @people from the model. - # - module Pagination - if const_defined?(:OPTIONS) - DEFAULT_OPTIONS[:group] = nil - else - # A hash holding options for controllers using macro-style pagination - OPTIONS = {}.freeze - - # The default options for pagination - DEFAULT_OPTIONS = { - :class_name => nil, - :singular_name => nil, - :per_page => 10, - :conditions => nil, - :order_by => nil, - :order => nil, - :join => nil, - :joins => nil, - :count => nil, - :include => nil, - :select => nil, - :group => nil, - :parameter => "page" - }.freeze - end - - def self.included(base) # :nodoc: - super - base.extend(ClassMethods) - end - - def self.validate_options!(collection_id, options, in_action) # :nodoc: - options.merge!(DEFAULT_OPTIONS) { |_key, old, _new| old } - - valid_options = DEFAULT_OPTIONS.keys - valid_options << :actions unless in_action - - unknown_option_keys = options.keys - valid_options - unless unknown_option_keys.empty? - raise ActionController::ActionControllerError, - "Unknown options: #{unknown_option_keys.join(', ')}" - end - - options[:singular_name] ||= ActiveSupport::Inflector.singularize(collection_id.to_s) - options[:class_name] ||= ActiveSupport::Inflector.camelize(options[:singular_name]) - end - - # Returns a paginator and a collection of Active Record model instances - # for the paginator's current page. This is designed to be used in a - # single action; to automatically paginate multiple actions, consider - # ClassMethods#paginate. - # - # +options+ are: - # :singular_name:: the singular name to use, if it can't be inferred by singularizing the collection name - # :class_name:: the class name to use, if it can't be inferred by - # camelizing the singular name - # :per_page:: the maximum number of items to include in a - # single page. Defaults to 10 - # :conditions:: optional conditions passed to Model.find(:all, *params) and - # Model.count - # :order:: optional order parameter passed to Model.find(:all, *params) - # :order_by:: (deprecated, used :order) optional order parameter passed to Model.find(:all, *params) - # :joins:: optional joins parameter passed to Model.find(:all, *params) - # and Model.count - # :join:: (deprecated, used :joins or :include) optional join parameter passed to Model.find(:all, *params) - # and Model.count - # :include:: optional eager loading parameter passed to Model.find(:all, *params) - # and Model.count - # :select:: :select parameter passed to Model.find(:all, *params) - # - # :count:: parameter passed as :select option to Model.count(*params) - # - # :group:: :group parameter passed to Model.find(:all, *params). It forces the use of DISTINCT instead of plain COUNT to come up with the total number of records - # - def paginate(collection_id, options = {}) - Pagination.validate_options!(collection_id, options, true) - paginator_and_collection_for(collection_id, options) - end - - # These methods become class methods on any controller - module ClassMethods - # Creates a +before_action+ which automatically paginates an Active - # Record model for all actions in a controller (or certain actions if - # specified with the :actions option). - # - # +options+ are the same as PaginationHelper#paginate, with the addition - # of: - # :actions:: an array of actions for which the pagination is - # active. Defaults to +nil+ (i.e., every action) - def paginate(collection_id, options = {}) - Pagination.validate_options!(collection_id, options, false) - module_eval do - before_action :create_paginators_and_retrieve_collections - OPTIONS[self] ||= {} - OPTIONS[self][collection_id] = options - end - end - end - - protected - - def create_paginators_and_retrieve_collections # :nodoc: - Pagination::OPTIONS[self.class].each do |collection_id, options| - next if options[:actions]&.exclude?(action_name) - - paginator, collection = - paginator_and_collection_for(collection_id, options) - - paginator_name = "@#{options[:singular_name]}_pages" - instance_variable_set(paginator_name, paginator) - - collection_name = "@#{collection_id}" - instance_variable_set(collection_name, collection) - end - end - - # Returns the total number of items in the collection to be paginated for - # the +model+ and given +conditions+. Override this method to implement a - # custom counter. - def count_collection_for_pagination(model, options) - collection = model.joins(options[:join] || options[:joins]) - collection = collection.where(options[:conditions]) - collection = collection.includes(options[:include]) - - if options[:group] - collection = collection.select(options[:group]).distinct - elsif options[:count] - collection = collection.select(options[:count]) - end - - collection.count - end - - # Returns a collection of items for the given +model+ and +options[conditions]+, - # ordered by +options[order]+, for the current page in the given +paginator+. - # Override this method to implement a custom finder. - def find_collection_for_pagination(model, options, paginator) - collection = model.joins(options[:join] || options[:joins]) - collection = collection.where(options[:conditions]) - collection = collection.order(options[:order_by] || options[:order]) - collection = collection.includes(options[:include]) - collection = collection.group(options[:group]) - collection = collection.select(options[:select]) if options[:select] - - collection.offset(paginator.current.offset).limit(options[:per_page]) - end - - private - - def paginator_and_collection_for(_collection_id, options) # :nodoc: - klass = options[:class_name].constantize - page = params[options[:parameter]] - count = count_collection_for_pagination(klass, options) - paginator = Paginator.new(self, count, options[:per_page], page) - collection = find_collection_for_pagination(klass, options, paginator) - - [paginator, collection] - end - - # A class representing a paginator for an Active Record collection. - class Paginator - include Enumerable - - # Creates a new Paginator on the given +controller+ for a set of items - # of size +item_count+ and having +items_per_page+ items per page. - # Raises ArgumentError if items_per_page is out of bounds (i.e., less - # than or equal to zero). The page CGI parameter for links defaults to - # "page" and can be overridden with +page_parameter+. - def initialize(controller, item_count, items_per_page, current_page = 1) - raise ArgumentError, "must have at least one item per page" if - items_per_page <= 0 - - @controller = controller - @item_count = item_count || 0 - @items_per_page = items_per_page - @pages = {} - - self.current_page = current_page - end - attr_reader :controller, :item_count, :items_per_page - - # Sets the current page number of this paginator. If +page+ is a Page - # object, its +number+ attribute is used as the value; if the page does - # not belong to this Paginator, an ArgumentError is raised. - def current_page=(page) - raise ArgumentError, "Page/Paginator mismatch" if page.is_a?(Page) && page.paginator != self - - page = page.to_i - @current_page_number = contains_page?(page) ? page : 1 - end - - # Returns a Page object representing this paginator's current page. - def current_page - @current_page ||= self[@current_page_number] - end - alias current current_page - - # Returns a new Page representing the first page in this paginator. - def first_page - @first_page ||= self[1] - end - alias first first_page - - # Returns a new Page representing the last page in this paginator. - def last_page - @last_page ||= self[page_count] - end - alias last last_page - - # Returns the number of pages in this paginator. - def page_count - @page_count ||= if @item_count.zero? - 1 - else - q, r = @item_count.divmod(@items_per_page) - r.zero? ? q : q + 1 - end - end - - alias length page_count - - # Returns true if this paginator contains the page of index +number+. - def contains_page?(number) - number.between?(1, page_count) - end - - # Returns a new Page representing the page with the given index - # +number+. - def [](number) - @pages[number] ||= Page.new(self, number) - end - - # Successively yields all the paginator's pages to the given block. - def each(&) - page_count.times do |n| - yield self[n + 1] - end - end - - # A class representing a single page in a paginator. - class Page - include Comparable - - # Creates a new Page for the given +paginator+ with the index - # +number+. If +number+ is not in the range of valid page numbers or - # is not a number at all, it defaults to 1. - def initialize(paginator, number) - @paginator = paginator - @number = number.to_i - @number = 1 unless @paginator.contains_page? @number - end - attr_reader :paginator, :number - - alias to_i number - - # Compares two Page objects and returns true when they represent the - # same page (i.e., their paginators are the same and they have the - # same page number). - def ==(other) - return false if other.nil? - - @paginator == other.paginator && - @number == other.number - end - - # Compares two Page objects and returns -1 if the left-hand page comes - # before the right-hand page, 0 if the pages are equal, and 1 if the - # left-hand page comes after the right-hand page. Raises ArgumentError - # if the pages do not belong to the same Paginator object. - def <=>(other) - raise ArgumentError unless @paginator == other.paginator - - @number <=> other.number - end - - # Returns the item offset for the first item in this page. - def offset - @paginator.items_per_page * (@number - 1) - end - - # Returns the number of the first item displayed. - def first_item - offset + 1 - end - - # Returns the number of the last item displayed. - def last_item - [@paginator.items_per_page * @number, @paginator.item_count].min - end - - # Returns true if this page is the first page in the paginator. - def first? - self == @paginator.first - end - - # Returns true if this page is the last page in the paginator. - def last? - self == @paginator.last - end - - # Returns a new Page object representing the page just before this - # page, or nil if this is the first page. - def previous - first? ? nil : @paginator[@number - 1] - end - - # Returns a new Page object representing the page just after this - # page, or nil if this is the last page. - def next - last? ? nil : @paginator[@number + 1] - end - - # Returns a new Window object for this page with the specified - # +padding+. - def window(padding = 2) - Window.new(self, padding) - end - - # Returns the limit/offset array for this page. - def to_sql - [@paginator.items_per_page, offset] - end - - def to_param # :nodoc: - @number.to_s - end - end - - # A class for representing ranges around a given page. - class Window - # Creates a new Window object for the given +page+ with the specified - # +padding+. - def initialize(page, padding = 2) - @paginator = page.paginator - @page = page - self.padding = padding - end - attr_reader :paginator, :page, :padding, :first, :last - - # Sets the window's padding (the number of pages on either side of the - # window page). - def padding=(padding) - @padding = padding.negative? ? 0 : padding - # Find the beginning and end pages of the window - @first = if @paginator.contains_page?(@page.number - @padding) - @paginator[@page.number - @padding] - else - @paginator.first - end - @last = if @paginator.contains_page?(@page.number + @padding) - @paginator[@page.number + @padding] - else - @paginator.last - end - end - - # Returns an array of Page objects in the current window. - def pages - (@first.number..@last.number).to_a.collect! { |n| @paginator[n] } - end - alias to_a pages - end - end - end -end diff --git a/lib/classic_pagination/pagination_helper.rb b/lib/classic_pagination/pagination_helper.rb deleted file mode 100644 index c450de4e1..000000000 --- a/lib/classic_pagination/pagination_helper.rb +++ /dev/null @@ -1,169 +0,0 @@ -module ActionView - module Helpers - # Provides methods for linking to ActionController::Pagination objects using a simple generator API. You can optionally - # also build your links manually using ActionView::Helpers::AssetHelper#link_to like so: - # - # <%= link_to "Previous page", { :page => paginator.current.previous } if paginator.current.previous %> - # <%= link_to "Next page", { :page => paginator.current.next } if paginator.current.next %> - module PaginationHelper - unless const_defined?(:DEFAULT_OPTIONS) - DEFAULT_OPTIONS = { - :name => :page, - :window_size => 2, - :always_show_anchors => true, - :link_to_current_page => false, - :params => {} - }.freeze - end - - # Creates a basic HTML link bar for the given +paginator+. Links will be created - # for the next and/or previous page and for a number of other pages around the current - # pages position. The +html_options+ hash is passed to +link_to+ when the links are created. - # - # ==== Options - # :name:: the routing name for this paginator - # (defaults to +page+) - # :prefix:: prefix for pagination links - # (i.e. Older Pages: 1 2 3 4) - # :suffix:: suffix for pagination links - # (i.e. 1 2 3 4 <- Older Pages) - # :window_size:: the number of pages to show around - # the current page (defaults to 2) - # :always_show_anchors:: whether or not the first and last - # pages should always be shown - # (defaults to +true+) - # :link_to_current_page:: whether or not the current page - # should be linked to (defaults to - # +false+) - # :params:: any additional routing parameters - # for page URLs - # - # ==== Examples - # # We'll assume we have a paginator setup in @person_pages... - # - # pagination_links(@person_pages) - # # => 1 2 3 ... 10 - # - # pagination_links(@person_pages, :link_to_current_page => true) - # # => 1 2 3 ... 10 - # - # pagination_links(@person_pages, :always_show_anchors => false) - # # => 1 2 3 - # - # pagination_links(@person_pages, :window_size => 1) - # # => 1 2 ... 10 - # - # pagination_links(@person_pages, :params => { :viewer => "flash" }) - # # => 1 2 3 ... - # # 10 - def pagination_links(paginator, options = {}, html_options = {}) - name = options[:name] || DEFAULT_OPTIONS[:name] - params = (options[:params] || DEFAULT_OPTIONS[:params]).clone - - prefix = options[:prefix] || "" - suffix = options[:suffix] || "" - - pagination_links_each(paginator, options, prefix, suffix) do |n| - params[name] = n - link_to(n.to_s, params, html_options) - end - end - - # Iterate through the pages of a given +paginator+, invoking a - # block for each page number that needs to be rendered as a link. - # - # ==== Options - # :window_size:: the number of pages to show around - # the current page (defaults to +2+) - # :always_show_anchors:: whether or not the first and last - # pages should always be shown - # (defaults to +true+) - # :link_to_current_page:: whether or not the current page - # should be linked to (defaults to - # +false+) - # - # ==== Example - # # Turn paginated links into an Ajax call - # pagination_links_each(paginator, page_options) do |link| - # options = { :url => {:action => 'list'}, :update => 'results' } - # html_options = { :href => url_for(:action => 'list') } - # - # link_to_remote(link.to_s, options, html_options) - # end - def pagination_links_each(paginator, options, prefix = nil, suffix = nil) - options = DEFAULT_OPTIONS.merge(options) - link_to_current_page = options[:link_to_current_page] - always_show_anchors = options[:always_show_anchors] - - current_page = paginator.current_page - window_pages = current_page.window(options[:window_size]).pages - return unless link_to_current_page || window_pages.length > 1 - - first = paginator.first - last = paginator.last - - html = "" - - html << prefix if prefix - - if always_show_anchors && !(wp_first = window_pages[0]).first? - html << yield(first.number) - html << " ... " if wp_first.number - first.number > 1 - html << " " - end - - window_pages.each do |page| - html << if current_page == page && !link_to_current_page - page.number.to_s - else - yield(page.number) - end - html << " " - end - - if always_show_anchors && !(wp_last = window_pages[-1]).last? - html << " ... " if last.number - wp_last.number > 1 - html << yield(last.number) - end - - html << suffix if suffix - - html - end - - def pagination_items(paginator, options) - options = DEFAULT_OPTIONS.merge(options) - link_to_current_page = options[:link_to_current_page] - always_show_anchors = options[:always_show_anchors] - - current_page = paginator.current_page - window_pages = current_page.window(options[:window_size]).pages - - first = paginator.first - last = paginator.last - - items = [] - - if always_show_anchors && !(wp_first = window_pages[0]).first? - items.push [first.number.to_s, first] - items.push ["...", "disabled"] if wp_first.number - first.number > 1 - end - - window_pages.each do |page| - if current_page == page && !link_to_current_page - items.push [page.number.to_s, "active"] - else - items.push [page.number.to_s, page] - end - end - - if always_show_anchors && !(wp_last = window_pages[-1]).last? - items.push ["...", "disabled"] if last.number - wp_last.number > 1 - items.push [last.number.to_s, last] - end - - items - end - end - end -end -- 2.39.5