moar 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 6c1b234cea1895e80c38ebe0568b780d05af5dab2bbff91aa02a43d30ac624b0
4
+ data.tar.gz: 44c2c5379aeb4b18fcbc4e5d5d957a48157228038567137f6316459d664fdb9c
5
+ SHA512:
6
+ metadata.gz: 5e6fb50987247ca2c73fe35ac359f56e0c854d641e0e5ad8448f05381c7788196df96bcefbe49dedd538bac13cf855998870049482e36e823b047932e7a58496
7
+ data.tar.gz: '068724bbd447a433e309c7eedf5d7ef6c21d64cf001107815e8e2ed8765fb091d57f68b482bbc69acc48446a0b0b799959fcbb35e6678732fed59f40ee3806c5'
@@ -0,0 +1,20 @@
1
+ Copyright 2018
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,123 @@
1
+ # moar
2
+
3
+ More-style pagination for Rails. As an example, consider the following
4
+ story:
5
+
6
+ * There are 175 posts in the database.
7
+ * User visits the posts index page; the first 10 posts are listed.
8
+ * User clicks a "More posts" link; the next 20 posts are appended to the
9
+ list (30 total) without refreshing the page.
10
+ * User clicks the "More posts" link again; the next 30 posts are
11
+ appended to the list (60 total) without refreshing the page.
12
+ * User clicks the "More posts" link again; the browser navigates to a
13
+ new page listing the next 60 posts.
14
+ * User clicks a "More posts" link; the browser navigates to a new page
15
+ listing the final 55 posts. No "More posts" link is rendered.
16
+ * At any point the user can manually refresh the page, and the same set
17
+ of posts will be shown. Likewise, the page can navigated away from
18
+ and back to, or bookmarked and returned to later, and the same set of
19
+ posts will be shown. (Assuming the database remains unchanged.)
20
+ * If JavaScript is disabled, the first and second "More posts" links
21
+ will simply navigate to a new page listing only the posts that would
22
+ have been fetched via Ajax.
23
+
24
+ With *moar*, this story can be realized using the following code:
25
+
26
+ ```ruby
27
+ ## app/controllers/posts_controller.rb
28
+ class PostsController < ApplicationController
29
+ # Step 1 (optional): set controller-specific pagination increments
30
+ moar_increments [10, 20, 30]
31
+
32
+ def index
33
+ # Step 2: apply pagination increments
34
+ @posts = moar(Post).order(:created_at)
35
+ end
36
+ end
37
+ ```
38
+
39
+ ```erb
40
+ <!-- app/views/posts/index.html.erb -->
41
+ <h1>Posts</h1>
42
+ <ul id="list-of-posts">
43
+ <% @posts.each do |post| %>
44
+ <li><%= link_to post.title, post %></li>
45
+ <% end %>
46
+ </ul>
47
+
48
+ <!-- Step 3: render pagination link -->
49
+ <%= link_to_more @posts, "#list-of-posts" %>
50
+ ```
51
+
52
+ A few things to note:
53
+
54
+ * No special code is required to perform the fetch and render of
55
+ incremental paginated results via Ajax.
56
+ * The maximum number of results per page (60, in this example) is the
57
+ sum of all pagination increments (10 + 20 + 30).
58
+ * The `link_to_more` helper automatically infers the link text ("More
59
+ posts") from the paginated results. This can be configured; see the
60
+ [Configuration](#configuration) section below.
61
+ * The second argument of the `link_to_more` helper is a CSS selector
62
+ which points to the paginated results container element. Results
63
+ fetched via Ajax are appended directly to that element, so the
64
+ selector must point to the rendered results' immediate container. For
65
+ example, if the paginated results are rendered as rows in a table, the
66
+ selector should point to the `<tbody>` element rather than the
67
+ `<table>` element.
68
+ * The `link_to_more` helper will render nothing when there are no more
69
+ paginated results &mdash; no `if` required.
70
+
71
+ For complete usage details, see the documentation for
72
+ [`moar_increments`](http://www.rubydoc.info/gems/moar/Moar/Controller/ClassMethods:moar_increments),
73
+ [`moar`](http://www.rubydoc.info/gems/moar/Moar/Controller:moar), and
74
+ [`link_to_more`](http://www.rubydoc.info/gems/moar/Moar/Helper:link_to_more).
75
+
76
+
77
+ ## Configuration
78
+
79
+ The *moar* install generator will create two configuration files in your
80
+ project directory: "config/initializers/moar.rb" and
81
+ "config/locales/moar.en.yml".
82
+
83
+ "config/initializers/moar.rb" can be edited to change the default
84
+ pagination increments used when `moar_increments` is not called, and to
85
+ change the query param used to indicate page number.
86
+
87
+ "config/locales/moar.en.yml" can be edited to change the link text
88
+ rendered by `link_to_more`. Translations listed in this file are
89
+ provided a `results_name` interpolation argument which contains the
90
+ humanized translated pluralized downcased name of the relevant model.
91
+ For example, if the translation string is `"Need more %{results_name}!"`
92
+ and the paginated results consist of `CowBell` models, the rendered text
93
+ will be "Need more cow bells!".
94
+
95
+ ## Installation
96
+
97
+ Add this line to your application's Gemfile:
98
+
99
+ ```ruby
100
+ gem "moar"
101
+ ```
102
+
103
+ Then execute:
104
+
105
+ ```bash
106
+ $ bundle install
107
+ ```
108
+
109
+ And finally, run the installation generator:
110
+
111
+ ```bash
112
+ $ rails generate moar:install
113
+ ```
114
+
115
+
116
+ ## Contributing
117
+
118
+ Run `rake test` to run the tests.
119
+
120
+
121
+ ## License
122
+
123
+ [MIT License](https://opensource.org/licenses/MIT)
@@ -0,0 +1,23 @@
1
+ begin
2
+ require 'bundler/setup'
3
+ rescue LoadError
4
+ puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
5
+ end
6
+
7
+ require 'yard'
8
+
9
+ YARD::Rake::YardocTask.new(:doc) do |t|
10
+ end
11
+
12
+
13
+ require 'bundler/gem_tasks'
14
+
15
+ require 'rake/testtask'
16
+
17
+ Rake::TestTask.new(:test) do |t|
18
+ t.libs << 'test'
19
+ t.pattern = 'test/**/*_test.rb'
20
+ t.verbose = false
21
+ end
22
+
23
+ task default: :test
@@ -0,0 +1,32 @@
1
+ document.addEventListener("ajax:success", function(event){
2
+ var link = event.target;
3
+ var containerSelector = link.getAttribute("data-paginates");
4
+ if (containerSelector) {
5
+ var response = event.detail[0];
6
+
7
+ // insert response elements
8
+ var container = document.querySelector(containerSelector);
9
+ if (!container) {
10
+ console.error("Invalid pagination target: " + containerSelector);
11
+ return;
12
+ }
13
+ var responseContainer = response.querySelector(containerSelector);
14
+ if (responseContainer) {
15
+ while (responseContainer.hasChildNodes()) {
16
+ container.appendChild(responseContainer.firstChild);
17
+ }
18
+ }
19
+
20
+ // update browser URL
21
+ var newUrl = link.href + "&" + link.getAttribute("data-accumulation-param") + "=1";
22
+ history.replaceState(history.state, "", newUrl);
23
+
24
+ // update pagination link
25
+ var responseLink = response.querySelector("a[data-paginates]");
26
+ if (responseLink) {
27
+ link.parentNode.replaceChild(responseLink, link);
28
+ } else {
29
+ link.parentNode.removeChild(link);
30
+ }
31
+ }
32
+ });
@@ -0,0 +1,30 @@
1
+ #require "rails/generators/base"
2
+
3
+ module Moar
4
+ # @!visibility private
5
+ module Generators
6
+ class InstallGenerator < Rails::Generators::Base
7
+ source_root File.join(__dir__, "templates")
8
+
9
+ def inject_javascript
10
+ inside do
11
+ manifest = Dir["app/assets/javascripts/application.js{,.coffee}"].first
12
+ raise Thor::Error.new("Could not find application.js") unless manifest
13
+
14
+ before, eq = File.read(manifest).match(%r"^(//=|\s*\*=|#=) require_tree.*").to_a
15
+ raise Thor::Error.new("Unable to inject `require moar` into #{manifest}") unless before
16
+
17
+ inject_into_file manifest, "#{eq} require moar\n", before: before
18
+ end
19
+ end
20
+
21
+ def copy_initializer
22
+ template "config/initializers/moar.rb"
23
+ end
24
+
25
+ def copy_locales
26
+ copy_file "config/locales/moar.en.yml"
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,12 @@
1
+ Moar.config.tap do |config|
2
+ # Default pagination increments. Controller-specific increments can
3
+ # also be set via the `moar_increments` controller class method.
4
+ config.increments = <%= Moar.config.increments.inspect %>
5
+
6
+ # Name of query param used to indicate page number.
7
+ config.page_param = <%= Moar.config.page_param.inspect %>
8
+
9
+ # Name of query param used to indicate when paginated results are
10
+ # accumulative.
11
+ config.accumulation_param = <%= Moar.config.accumulation_param.inspect %>
12
+ end
@@ -0,0 +1,12 @@
1
+ # All translations below are provided a `results_name` interpolation
2
+ # argument which contains the humanized translated pluralized downcased
3
+ # name of the relevant model. For example, if the paginated results
4
+ # consist of GeographicLocation models, the `results_name` argument will
5
+ # be "geographic locations".
6
+
7
+ en:
8
+ moar:
9
+ # Link text rendered by `link_to_more`.
10
+ more: "More %{results_name}"
11
+ # Disabled link text shown when fetching paginated results via Ajax.
12
+ loading: "Loading..."
@@ -0,0 +1,6 @@
1
+ require "moar/version"
2
+ require "moar/config"
3
+ require "moar/context"
4
+ require "moar/controller"
5
+ require "moar/helper"
6
+ require "moar/engine"
@@ -0,0 +1,43 @@
1
+ module Moar
2
+
3
+ class Config
4
+ # Pagination increments used by {Moar::Controller#moar}. Defaults
5
+ # to +[12,24,24]+. Controller-specific increments can also be set
6
+ # via {Moar::Controller::ClassMethods#moar_increments}.
7
+ #
8
+ # @return [Array<Integer>]
9
+ attr_accessor :increments
10
+
11
+ # Name of query param used to indicate page number. Defaults to
12
+ # +:page+.
13
+ #
14
+ # @return [Symbol]
15
+ attr_accessor :page_param
16
+
17
+ # Name of query param used to indicate when paginated results are
18
+ # accumulative. Defaults to +:accum+.
19
+ #
20
+ # @return [Symbol]
21
+ attr_accessor :accumulation_param
22
+
23
+ def initialize
24
+ @increments = [12, 24, 24]
25
+ @page_param = :page
26
+ @accumulation_param = :accum
27
+ end
28
+ end
29
+
30
+ # Moar global configuration object.
31
+ #
32
+ # @return [Moar::Config]
33
+ def self.config
34
+ @config ||= Moar::Config.new
35
+ end
36
+
37
+ # @param c [Moar::Config]
38
+ # @return [Moar::Config]
39
+ def self.config=(c)
40
+ @config = c
41
+ end
42
+
43
+ end
@@ -0,0 +1,26 @@
1
+ module Moar
2
+ class Context
3
+
4
+ attr_reader :increments, :page, :accumulative, :offset, :limit
5
+
6
+ # @!visibility private
7
+ def initialize(increments, page, accumulative)
8
+ @increments = increments
9
+ @page = [page, 1].max
10
+ @accumulative = accumulative
11
+
12
+ if @page <= @increments.length
13
+ @limit = @increments[@page - 1]
14
+ @offset = @increments.take(@page - 1).sum
15
+ if @accumulative
16
+ @limit += @offset
17
+ @offset = 0
18
+ end
19
+ else
20
+ @limit = @increments.sum
21
+ @offset = @limit * (@page - @increments.length)
22
+ end
23
+ end
24
+
25
+ end
26
+ end
@@ -0,0 +1,55 @@
1
+ module Moar
2
+ module Controller
3
+ extend ActiveSupport::Concern
4
+
5
+ # Paginates +relation+, returning an +ActiveRecord::Relation+ with
6
+ # an offset and limit applied. The offset and limit are calculated
7
+ # based on pagination increments (as specified by either
8
+ # {Moar::Controller::ClassMethods#moar_increments} or
9
+ # {Moar::Config#increments}), and the current page number (parsed
10
+ # from the request query param specified by
11
+ # {Moar::Config#page_param}).
12
+ #
13
+ # If the current page number is less than or equal to the number of
14
+ # pagination increments, the limit will be the pagination increment
15
+ # corresponding to the current page number. Otherwise, the limit
16
+ # will be the sum of all increments. For example, if the pagination
17
+ # increments are +[15,20,25]+, the offsets and limits are:
18
+ #
19
+ # * page 1: offset 0, limit 15
20
+ # * page 2: offset 15, limit 20
21
+ # * page 3: offset 35, limit 25
22
+ # * page 4: offset 60, limit 60
23
+ # * page 5: offset 120, limit 60
24
+ # * page 6: offset 180, limit 60
25
+ # * ...
26
+ #
27
+ # @param relation [ActiveRecord::Relation]
28
+ # @return [ActiveRecord::Relation]
29
+ def moar(relation)
30
+ @moar = Moar::Context.new(
31
+ _moar_increments || Moar.config.increments,
32
+ params[Moar.config.page_param].to_i,
33
+ params[Moar.config.accumulation_param].present?
34
+ )
35
+
36
+ relation.offset(@moar.offset).limit(@moar.limit)
37
+ end
38
+
39
+ included do
40
+ # @!visibility private
41
+ class_attribute :_moar_increments
42
+ end
43
+
44
+ module ClassMethods
45
+ # Sets controller-specific pagination increments to be used by
46
+ # {Moar::Controller#moar}. Pagination increments set this way
47
+ # take precedence over {Moar::Config#increments}.
48
+ #
49
+ # @param increments [Array<Integer>]
50
+ def moar_increments(increments)
51
+ self._moar_increments = increments
52
+ end
53
+ end
54
+ end
55
+ end
@@ -0,0 +1,14 @@
1
+ module Moar
2
+ # @!visibility private
3
+ class Engine < ::Rails::Engine
4
+ initializer "moar" do |app|
5
+ ActiveSupport.on_load :action_controller do
6
+ include Moar::Controller
7
+ end
8
+
9
+ ActiveSupport.on_load :action_view do
10
+ include Moar::Helper
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,73 @@
1
+ module Moar
2
+ module Helper
3
+
4
+ # Generates an anchor element that links to more paginated results.
5
+ # If JavaScript is active, and the current page number is less than
6
+ # the number of pagination increments (see {Moar::Config#increments}
7
+ # or {Moar::Controller::ClassMethods#moar_increments}), the link
8
+ # will use Ajax to fetch the results and inject them into the
9
+ # element matching the CSS selector specified by +target+.
10
+ # Otherwise, the link will behave normally and navigate to the next
11
+ # page of results.
12
+ #
13
+ # The text of the link is determined via I18n using translation key
14
+ # +:"moar.more"+. A +results_name+ interpolation argument is
15
+ # provided containing the humanized translated pluralized downcased
16
+ # name of the relevant model. For example, if the translation
17
+ # string is <code>"Need more %{results_name}!"</code> and +results+
18
+ # is an array of +CowBell+ models, the link text will be "Need more
19
+ # cow bells!".
20
+ #
21
+ # This helper method accepts an +html_options+ Hash, and passes it
22
+ # to Rails' +ActionView::Helpers::UrlHelper#link_to+. See its
23
+ # documentation for information about available options.
24
+ #
25
+ # If no more results are available, this helper method will return
26
+ # nil so that no link is rendered. Whether there are more results
27
+ # is estimated by comparing +results.length+ with the limit applied
28
+ # by {Moar::Controller#moar}. This technique eliminates the need
29
+ # for an extra database query, but can result in a false positive
30
+ # (i.e. rendering a link to an empty page) when the actual last page
31
+ # of results is also a full page. This is deemed an acceptable
32
+ # trade-off because with a large number of pages and a large total
33
+ # number of results per page it is an unlikely occurrence, and
34
+ # because an extra database query cannot entirely prevent a link to
35
+ # an empty page, in the case where records are deleted before the
36
+ # user can click through to the final page.
37
+ #
38
+ # @param results [ActiveRecord::Relation, Array<ActiveModel::Naming>]
39
+ # @param target [String]
40
+ # @param html_options [Hash]
41
+ # @return [String, nil]
42
+ # @raise [RuntimeError]
43
+ # if controller action did not invoke {Moar::Controller#moar}
44
+ def link_to_more(results, target, html_options = {})
45
+ raise "#{controller.class}##{action_name} did not invoke #moar" unless defined?(@moar)
46
+
47
+ unless results.length < @moar.limit
48
+ params = request.query_parameters.except(Moar.config.accumulation_param.to_s)
49
+ params[Moar.config.page_param.to_s] = @moar.page + 1
50
+
51
+ options = { controller: controller_path, action: action_name, params: params }
52
+
53
+ i18n_options = {
54
+ results_name: results.first.model_name.human(
55
+ count: 2, default: results.first.model_name.human.pluralize(I18n.locale)
56
+ ).downcase,
57
+ }
58
+
59
+ html_options = html_options.dup
60
+ html_options["data-paginates"] = target
61
+ if @moar.page < @moar.increments.length
62
+ html_options["data-accumulation-param"] = Moar.config.accumulation_param.to_s
63
+ html_options["data-remote"] = true
64
+ html_options["data-type"] = "html"
65
+ html_options["data-disable-with"] = I18n.t(:"moar.loading", i18n_options)
66
+ end
67
+
68
+ link_to I18n.t(:"moar.more", i18n_options), options, html_options
69
+ end
70
+ end
71
+
72
+ end
73
+ end
@@ -0,0 +1,3 @@
1
+ module Moar
2
+ VERSION = "1.0.0"
3
+ end
metadata ADDED
@@ -0,0 +1,176 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: moar
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Jonathan Hefner
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2018-08-18 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: rails
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '5.1'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '5.1'
27
+ - !ruby/object:Gem::Dependency
28
+ name: sqlite3
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: puma
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '3.11'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '3.11'
55
+ - !ruby/object:Gem::Dependency
56
+ name: capybara
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: '2.15'
62
+ - - "<"
63
+ - !ruby/object:Gem::Version
64
+ version: '4.0'
65
+ type: :development
66
+ prerelease: false
67
+ version_requirements: !ruby/object:Gem::Requirement
68
+ requirements:
69
+ - - ">="
70
+ - !ruby/object:Gem::Version
71
+ version: '2.15'
72
+ - - "<"
73
+ - !ruby/object:Gem::Version
74
+ version: '4.0'
75
+ - !ruby/object:Gem::Dependency
76
+ name: selenium-webdriver
77
+ requirement: !ruby/object:Gem::Requirement
78
+ requirements:
79
+ - - ">="
80
+ - !ruby/object:Gem::Version
81
+ version: '0'
82
+ type: :development
83
+ prerelease: false
84
+ version_requirements: !ruby/object:Gem::Requirement
85
+ requirements:
86
+ - - ">="
87
+ - !ruby/object:Gem::Version
88
+ version: '0'
89
+ - !ruby/object:Gem::Dependency
90
+ name: chromedriver-helper
91
+ requirement: !ruby/object:Gem::Requirement
92
+ requirements:
93
+ - - ">="
94
+ - !ruby/object:Gem::Version
95
+ version: '0'
96
+ type: :development
97
+ prerelease: false
98
+ version_requirements: !ruby/object:Gem::Requirement
99
+ requirements:
100
+ - - ">="
101
+ - !ruby/object:Gem::Version
102
+ version: '0'
103
+ - !ruby/object:Gem::Dependency
104
+ name: turbolinks
105
+ requirement: !ruby/object:Gem::Requirement
106
+ requirements:
107
+ - - "~>"
108
+ - !ruby/object:Gem::Version
109
+ version: '5.1'
110
+ type: :development
111
+ prerelease: false
112
+ version_requirements: !ruby/object:Gem::Requirement
113
+ requirements:
114
+ - - "~>"
115
+ - !ruby/object:Gem::Version
116
+ version: '5.1'
117
+ - !ruby/object:Gem::Dependency
118
+ name: yard
119
+ requirement: !ruby/object:Gem::Requirement
120
+ requirements:
121
+ - - "~>"
122
+ - !ruby/object:Gem::Version
123
+ version: '0.9'
124
+ type: :development
125
+ prerelease: false
126
+ version_requirements: !ruby/object:Gem::Requirement
127
+ requirements:
128
+ - - "~>"
129
+ - !ruby/object:Gem::Version
130
+ version: '0.9'
131
+ description:
132
+ email:
133
+ - jonathan.hefner@gmail.com
134
+ executables: []
135
+ extensions: []
136
+ extra_rdoc_files: []
137
+ files:
138
+ - MIT-LICENSE
139
+ - README.md
140
+ - Rakefile
141
+ - app/assets/javascripts/moar.js
142
+ - lib/generators/moar/install/install_generator.rb
143
+ - lib/generators/moar/install/templates/config/initializers/moar.rb.tt
144
+ - lib/generators/moar/install/templates/config/locales/moar.en.yml
145
+ - lib/moar.rb
146
+ - lib/moar/config.rb
147
+ - lib/moar/context.rb
148
+ - lib/moar/controller.rb
149
+ - lib/moar/engine.rb
150
+ - lib/moar/helper.rb
151
+ - lib/moar/version.rb
152
+ homepage: https://github.com/jonathanhefner/moar
153
+ licenses:
154
+ - MIT
155
+ metadata: {}
156
+ post_install_message:
157
+ rdoc_options: []
158
+ require_paths:
159
+ - lib
160
+ required_ruby_version: !ruby/object:Gem::Requirement
161
+ requirements:
162
+ - - ">="
163
+ - !ruby/object:Gem::Version
164
+ version: '0'
165
+ required_rubygems_version: !ruby/object:Gem::Requirement
166
+ requirements:
167
+ - - ">="
168
+ - !ruby/object:Gem::Version
169
+ version: '0'
170
+ requirements: []
171
+ rubyforge_project:
172
+ rubygems_version: 2.7.6
173
+ signing_key:
174
+ specification_version: 4
175
+ summary: More-style pagination for Rails
176
+ test_files: []