diff --git a/lib/liquid/standardfilters.rb b/lib/liquid/standardfilters.rb index 1f5a97cc..2340a745 100644 --- a/lib/liquid/standardfilters.rb +++ b/lib/liquid/standardfilters.rb @@ -165,6 +165,20 @@ module Liquid end end end + + # Remove nils within an array + # provide optional property with which to check for nil + def compact(input, property = nil) + ary = InputIterator.new(input) + + if property.nil? + ary.compact + elsif ary.first.respond_to?(:[]) + ary.reject{ |a| a[property].nil? } + elsif ary.first.respond_to?(property) + ary.reject { |a| a.send(property).nil? } + end + end # Replace occurrences of a string with another def replace(input, string, replacement = ''.freeze) @@ -397,6 +411,10 @@ module Liquid to_a.uniq(&block) end + def compact + to_a.compact + end + def each @input.each do |e| yield(e.respond_to?(:to_liquid) ? e.to_liquid : e) diff --git a/test/integration/filter_test.rb b/test/integration/filter_test.rb index cf407bfc..1e904ab1 100644 --- a/test/integration/filter_test.rb +++ b/test/integration/filter_test.rb @@ -104,6 +104,27 @@ class FiltersTest < Minitest::Test assert_equal sorted[2].a, 'C' end + def test_compact + @context['words'] = ['a', nil, 'b', nil, 'c'] + @context['hashes'] = [{ 'a' => 'A' }, { 'a' => nil }, { 'a' => 'C' }] + @context['objects'] = [TestObject.new('A'), TestObject.new(nil), TestObject.new('C')] + + # Test strings + assert_equal ['a', 'b', 'c'], Variable.new("words | compact").render(@context) + + # Test hashes + sorted = Variable.new("hashes | compact: 'a'").render(@context) + assert_equal sorted[0]['a'], 'A' + assert_equal sorted[1]['a'], 'C' + assert_nil sorted[2] + + # Test objects + sorted = Variable.new("objects | compact: 'a'").render(@context) + assert_equal sorted[0].a, 'A' + assert_equal sorted[1].a, 'C' + assert_nil sorted[2] + end + def test_strip_html @context['var'] = "bla blub"