Memoize array of drop getter method names (#8421)

Merge pull request 8421
This commit is contained in:
Ashwin Maroli 2020-10-16 18:01:09 +05:30 committed by GitHub
parent 20abb8f62b
commit 7c56e397c9
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 52 additions and 3 deletions

View File

@ -6,6 +6,8 @@ module Jekyll
include Enumerable
NON_CONTENT_METHODS = [:fallback_data, :collapse_document].freeze
NON_CONTENT_METHOD_NAMES = NON_CONTENT_METHODS.map(&:to_s).freeze
private_constant :NON_CONTENT_METHOD_NAMES
# A private stash to avoid repeatedly generating the setter method name string for
# a call to `Drops::Drop#[]=`.
@ -88,6 +90,17 @@ module Jekyll
def data_delegator(key)
define_method(key.to_sym) { @obj.data[key] }
end
# Array of stringified instance methods that do not end with the assignment operator.
#
# (<klass>.instance_methods always generates a new Array object so it can be mutated)
#
# Returns array of strings.
def getter_method_names
@getter_method_names ||= instance_methods.map!(&:to_s).tap do |list|
list.reject! { |item| item.end_with?("=") }
end
end
end
# Create a new Drop
@ -152,9 +165,10 @@ module Jekyll
#
# Returns an Array of strings which represent method-specific keys.
def content_methods
@content_methods ||= (
self.class.instance_methods - Jekyll::Drops::Drop.instance_methods - NON_CONTENT_METHODS
).map!(&:to_s).tap { |result| result.reject! { |method| method.end_with?("=") } }
@content_methods ||= \
self.class.getter_method_names \
- Jekyll::Drops::Drop.getter_method_names \
- NON_CONTENT_METHOD_NAMES
end
# Check if key exists in Drop

View File

@ -5,6 +5,8 @@ require "helper"
class DropFixture < Jekyll::Drops::Drop
mutable true
attr_accessor :lipsum
def foo
"bar"
end
@ -40,6 +42,39 @@ class TestDrop < JekyllUnitTest
assert_equal "bar", @drop.invoke_drop("foo")
end
should "return array of strings for .getter_methods" do
assert(@drop.class.getter_method_names.all? { |entry| entry.is_a?(String) })
end
should "return array of only getter method name strings for .getter_methods" do
[:lipsum, :lipsum=].each { |id| assert_includes(@drop.class.instance_methods, id) }
assert_includes @drop.class.getter_method_names, "lipsum"
refute_includes @drop.class.getter_method_names, "lipsum="
end
should "not munge results for another Jekyll::Drops::Drop subclass" do
fixture_ids = [:lipsum, :lipsum=, :foo]
fixture_getter_names = %w(lipsum foo)
fixture_ids.each { |id| assert_includes(@drop.class.instance_methods, id) }
fixture_getter_names.each do |name|
assert_includes @drop.class.getter_method_names, name
refute_includes @document_drop.class.getter_method_names, name
end
end
should "return only getter method names for #content_methods" do
drop_base_class_method_names = Jekyll::Drops::Drop.instance_methods.map(&:to_s)
sample_method_names = ["lipsum=", "fallback_data", "collapse_document"]
(sample_method_names + drop_base_class_method_names).each do |entry|
refute_includes @drop.content_methods, entry
end
assert_equal %w(foo lipsum), @drop.content_methods.sort
end
context "mutations" do
should "return mutations for #[]" do
@drop["foo"] = "baz"