k_log 0.0.17 → 0.0.27
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.rubocop.yml +15 -0
- data/Gemfile +3 -8
- data/k_log.gemspec +1 -0
- data/lib/k_log/examples.rb +9 -0
- data/lib/k_log/log_helper.rb +63 -2
- data/lib/k_log/log_structure.rb +399 -0
- data/lib/k_log/log_util.rb +408 -381
- data/lib/k_log/tools/build_formatter_configuration_for_log_structure.rb +51 -0
- data/lib/k_log/version.rb +5 -5
- data/lib/k_log.rb +40 -39
- metadata +18 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 2035ee429ccfbb7cd0307d243e9b8bd303f44444d1b356c28ad079bc8219de8f
|
4
|
+
data.tar.gz: c7eeff9ee82d1514859052d264cfcb06216ad939f3c215c34dfee6f64ef0d21f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f12d2c0fae01798339647d3905fefe8e5e63049d074965c04b878e3ba4df7b8571cba637877395f8fa033d2c780d53bfc4aaa2da605af647908fdb7e29bd1e3a
|
7
|
+
data.tar.gz: 3d780ecca23bac05227ff96629c464f3ecf2ed61f908a6f28145e9b00786fae625e37d751210ccaaf03d613e1683bbfbb15cf009d35e57909ac3110488b34b0f
|
data/.rubocop.yml
CHANGED
@@ -40,6 +40,8 @@ Layout/LineLength:
|
|
40
40
|
# Ignores annotate output
|
41
41
|
IgnoredPatterns: ['\A# \*\*']
|
42
42
|
IgnoreCopDirectives: true
|
43
|
+
Exclude:
|
44
|
+
- "**/spec/**/*"
|
43
45
|
|
44
46
|
Lint/UnusedMethodArgument:
|
45
47
|
AllowUnusedKeywordArguments: true
|
@@ -52,12 +54,25 @@ Style/BlockComments:
|
|
52
54
|
Include:
|
53
55
|
- "**/spec/*"
|
54
56
|
|
57
|
+
Layout/EndOfLine:
|
58
|
+
EnforcedStyle: lf
|
59
|
+
|
55
60
|
# My Preferences - Start
|
56
61
|
Metrics/ClassLength:
|
57
62
|
Enabled: false
|
58
63
|
Metrics/ModuleLength:
|
59
64
|
Exclude:
|
60
65
|
- "**/spec/**/*"
|
66
|
+
Metrics/CyclomaticComplexity:
|
67
|
+
Exclude:
|
68
|
+
- "lib/k_log/log_structure.rb"
|
69
|
+
Metrics/PerceivedComplexity:
|
70
|
+
Exclude:
|
71
|
+
- "lib/k_log/log_structure.rb"
|
72
|
+
Metrics/AbcSize:
|
73
|
+
Exclude:
|
74
|
+
- "lib/k_log/log_structure.rb"
|
75
|
+
|
61
76
|
Naming/MemoizedInstanceVariableName:
|
62
77
|
Enabled: false
|
63
78
|
Naming/VariableNumber:
|
data/Gemfile
CHANGED
@@ -2,23 +2,18 @@
|
|
2
2
|
|
3
3
|
source 'https://rubygems.org'
|
4
4
|
|
5
|
-
# Specify your gem's dependencies in handlebars_helpers.gemspec
|
6
5
|
gemspec
|
7
6
|
|
8
|
-
# group :development do
|
9
|
-
# # Currently conflicts with GitHub actions and so I remove it on push
|
10
|
-
# # pry on steroids
|
11
|
-
# gem 'jazz_fingers'
|
12
|
-
# gem 'pry-coolline', github: 'owst/pry-coolline', branch: 'support_new_pry_config_api'
|
13
|
-
# end
|
14
|
-
|
15
7
|
group :development, :test do
|
8
|
+
gem 'dry-struct', '~> 1'
|
9
|
+
|
16
10
|
gem 'guard-bundler'
|
17
11
|
gem 'guard-rspec'
|
18
12
|
gem 'guard-rubocop'
|
19
13
|
gem 'rake', '~> 12.0'
|
20
14
|
gem 'rake-compiler', require: false
|
21
15
|
gem 'rspec', '~> 3.0'
|
16
|
+
gem 'rspec-collection_matchers'
|
22
17
|
gem 'rubocop'
|
23
18
|
gem 'rubocop-rake', require: false
|
24
19
|
gem 'rubocop-rspec', require: false
|
data/k_log.gemspec
CHANGED
data/lib/k_log/examples.rb
CHANGED
@@ -25,6 +25,15 @@ module KLog
|
|
25
25
|
log.heading('Heading')
|
26
26
|
log.subheading('Sub Heading')
|
27
27
|
log.section_heading('Section Heading')
|
28
|
+
|
29
|
+
data = OpenStruct.new
|
30
|
+
data.title = 'Software Architect'
|
31
|
+
data.age = 45
|
32
|
+
data.name = 'David'
|
33
|
+
data.names = %w[David Bill]
|
34
|
+
data.status = :debug
|
35
|
+
data.statuses = %i[debug info blah]
|
36
|
+
log.open_struct(data, section_heading: 'Display Open Struct')
|
28
37
|
end
|
29
38
|
|
30
39
|
def examples_complex
|
data/lib/k_log/log_helper.rb
CHANGED
@@ -43,6 +43,14 @@ module KLog
|
|
43
43
|
green(character * size)
|
44
44
|
end
|
45
45
|
|
46
|
+
def self.dynamic_heading(heading, size: 70, type: :heading)
|
47
|
+
return heading(heading, size) if type == :heading
|
48
|
+
return subheading(heading, size) if type == :subheading
|
49
|
+
return [section_heading(heading, size)] if %i[section_heading section].include?(type)
|
50
|
+
|
51
|
+
[]
|
52
|
+
end
|
53
|
+
|
46
54
|
def self.heading(heading, size = 70)
|
47
55
|
line = line(size)
|
48
56
|
|
@@ -69,7 +77,8 @@ module KLog
|
|
69
77
|
def self.section_heading(heading, size = 70)
|
70
78
|
brace_open = green('[ ')
|
71
79
|
brace_close = green(' ]')
|
72
|
-
|
80
|
+
line_length = size - heading.length - 4
|
81
|
+
line = line_length.positive? ? line(line_length, '-') : ''
|
73
82
|
|
74
83
|
# It is important that you set the colour after you have calculated the size
|
75
84
|
"#{brace_open}#{heading}#{brace_close}#{green(line)}"
|
@@ -89,7 +98,7 @@ module KLog
|
|
89
98
|
|
90
99
|
unless title.nil?
|
91
100
|
result.push(title)
|
92
|
-
result.push(line(70, '
|
101
|
+
result.push(line(70, '-'))
|
93
102
|
end
|
94
103
|
|
95
104
|
result.push messages if messages.is_a?(String) || messages.is_a?(Integer)
|
@@ -106,8 +115,60 @@ module KLog
|
|
106
115
|
end
|
107
116
|
# rubocop:enable Metrics/CyclomaticComplexity
|
108
117
|
|
118
|
+
def self.red(value)
|
119
|
+
"\033[31m#{value}\033[0m"
|
120
|
+
end
|
121
|
+
|
109
122
|
def self.green(value)
|
110
123
|
"\033[32m#{value}\033[0m"
|
111
124
|
end
|
125
|
+
|
126
|
+
def self.yellow(value)
|
127
|
+
"\033[33m#{value}\033[0m"
|
128
|
+
end
|
129
|
+
|
130
|
+
def self.blue(value)
|
131
|
+
"\033[34m#{value}\033[0m"
|
132
|
+
end
|
133
|
+
|
134
|
+
def self.purple(value)
|
135
|
+
"\033[35m#{value}\033[0m"
|
136
|
+
end
|
137
|
+
|
138
|
+
def self.cyan(value)
|
139
|
+
"\033[36m#{value}\033[0m"
|
140
|
+
end
|
141
|
+
|
142
|
+
def self.grey(value)
|
143
|
+
"\033[37m#{value}\033[0m"
|
144
|
+
end
|
145
|
+
|
146
|
+
def self.bg_red(value)
|
147
|
+
"\033[41m#{value}\033[0m"
|
148
|
+
end
|
149
|
+
|
150
|
+
def self.bg_green(value)
|
151
|
+
"\033[42m#{value}\033[0m"
|
152
|
+
end
|
153
|
+
|
154
|
+
def self.bg_yellow(value)
|
155
|
+
"\033[43m#{value}\033[0m"
|
156
|
+
end
|
157
|
+
|
158
|
+
def self.bg_blue(value)
|
159
|
+
"\033[44m#{value}\033[0m"
|
160
|
+
end
|
161
|
+
|
162
|
+
def self.bg_purple(value)
|
163
|
+
"\033[45m#{value}\033[0m"
|
164
|
+
end
|
165
|
+
|
166
|
+
def self.bg_cyan(value)
|
167
|
+
"\033[46m#{value}\033[0m"
|
168
|
+
end
|
169
|
+
|
170
|
+
def self.bg_grey(value)
|
171
|
+
"\033[47m#{value}\033[0m"
|
172
|
+
end
|
112
173
|
end
|
113
174
|
end
|
@@ -0,0 +1,399 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'k_util'
|
4
|
+
|
5
|
+
module KLog
|
6
|
+
# Log Structure is flexible logger for working through a complex object graph
|
7
|
+
class LogStructure
|
8
|
+
attr_reader :indent
|
9
|
+
attr_reader :title
|
10
|
+
attr_reader :title_type
|
11
|
+
attr_reader :heading
|
12
|
+
attr_reader :heading_type
|
13
|
+
attr_reader :line_width
|
14
|
+
attr_reader :graph
|
15
|
+
attr_reader :formatter
|
16
|
+
attr_reader :convert_data_to
|
17
|
+
|
18
|
+
attr_reader :recursion_depth
|
19
|
+
attr_reader :key_format
|
20
|
+
attr_reader :graph_path
|
21
|
+
attr_reader :graph_node
|
22
|
+
|
23
|
+
attr_reader :lines
|
24
|
+
attr_reader :output_as
|
25
|
+
attr_reader :output_file
|
26
|
+
|
27
|
+
# Log a structure
|
28
|
+
#
|
29
|
+
# Can handle Hash, Array, OpenStruct, Struct, DryStruct, Hash convertible custom classes
|
30
|
+
#
|
31
|
+
# @option opts [String] :indent Indent with string, defaults to ' '
|
32
|
+
# @option opts [String] :heading Log heading using logger.dynamic_heading
|
33
|
+
# @option opts [String] :heading_type :heading, :subheading, :section_heading
|
34
|
+
# @option opts [String] :line_width line width defaults to 80, but can be overridden here
|
35
|
+
# @option opts [String] :formatter is a complex configuration for formatting different data within the structure
|
36
|
+
def initialize(opts)
|
37
|
+
@indent = opts[:indent] || ' '
|
38
|
+
@title = opts[:title]
|
39
|
+
@title_type = opts[:title_type] || :heading
|
40
|
+
|
41
|
+
@heading = opts[:heading]
|
42
|
+
@heading_type = opts[:heading_type] || :heading
|
43
|
+
puts ':heading should be :title' if opts[:heading]
|
44
|
+
puts ':heading_type should be :title_type' if opts[:heading_type]
|
45
|
+
|
46
|
+
@formatter = opts[:formatter] || {}
|
47
|
+
@graph = parse_graph(opts[:graph] || {})
|
48
|
+
@convert_data_to = opts[:convert_data_to] || :raw # by default leave data as is
|
49
|
+
|
50
|
+
@line_width = opts[:line_width] || 80
|
51
|
+
@output_as = opts[:output_as] || [:console]
|
52
|
+
@output_as = [@output_as] unless @output_as.is_a?(Array)
|
53
|
+
@output_file = opts[:output_file]
|
54
|
+
|
55
|
+
@recursion_depth = 0
|
56
|
+
@key_format = nil
|
57
|
+
@graph_path = []
|
58
|
+
@lines = []
|
59
|
+
|
60
|
+
update_indent_label
|
61
|
+
end
|
62
|
+
|
63
|
+
def l
|
64
|
+
@l ||= KLog::LogUtil.new(KLog.logger)
|
65
|
+
end
|
66
|
+
|
67
|
+
def log(data)
|
68
|
+
log_heading(title, title_type) if title
|
69
|
+
|
70
|
+
data = convert_data(data)
|
71
|
+
|
72
|
+
log_data(data)
|
73
|
+
|
74
|
+
add_line(KLog::LogHelper.line(line_width))
|
75
|
+
|
76
|
+
render_output
|
77
|
+
end
|
78
|
+
|
79
|
+
def content
|
80
|
+
@content ||= lines.join("\n")
|
81
|
+
end
|
82
|
+
|
83
|
+
def clean_content
|
84
|
+
# remove color escape codes
|
85
|
+
@clean_content ||= content.gsub(/\x1B\[\d*m/, '')
|
86
|
+
end
|
87
|
+
|
88
|
+
def clean_lines
|
89
|
+
# remove color escape codes
|
90
|
+
lines.flat_map { |line| line.gsub(/\x1B\[\d*m/, '').split("\n") }
|
91
|
+
end
|
92
|
+
|
93
|
+
def add_lines(lines)
|
94
|
+
@lines += lines
|
95
|
+
end
|
96
|
+
|
97
|
+
def add_line(line)
|
98
|
+
@lines << line
|
99
|
+
end
|
100
|
+
|
101
|
+
private
|
102
|
+
|
103
|
+
# format_config = @formatter[:_root] if format_config.nil? && @recursion_depth.zero?
|
104
|
+
|
105
|
+
def log_data(data)
|
106
|
+
data.each_pair do |k, v|
|
107
|
+
key = k.is_a?(String) ? k.to_sym : k
|
108
|
+
|
109
|
+
graph_path.push(key)
|
110
|
+
@graph_node = GraphNode.for(graph, graph_path)
|
111
|
+
# l.kv 'key', "#{key.to_s.ljust(15)}#{graph_node.skip?.to_s.ljust(6)}#{@recursion_depth}"
|
112
|
+
|
113
|
+
if graph_node.skip?
|
114
|
+
# l.kv 'key', 'skipping...'
|
115
|
+
@graph_path.pop
|
116
|
+
next
|
117
|
+
end
|
118
|
+
|
119
|
+
value = graph_node.transform? ? graph_node.transform(v) : v
|
120
|
+
|
121
|
+
case value
|
122
|
+
when OpenStruct
|
123
|
+
# l.kv 'go', 'open struct ->'
|
124
|
+
log_structure(key, value)
|
125
|
+
# l.kv 'go', 'open struct <-'
|
126
|
+
when Array
|
127
|
+
# l.kv 'go', 'array ->'
|
128
|
+
log_array(key, value)
|
129
|
+
# l.kv 'go', 'array <-'
|
130
|
+
else
|
131
|
+
# l.kv 'go', 'value ->'
|
132
|
+
log_heading(graph_node.heading, graph_node.heading_type) if graph_node.heading
|
133
|
+
add_line KLog::LogHelper.kv "#{@indent_label}#{key}", value
|
134
|
+
# l.kv 'go', 'value <-'
|
135
|
+
end
|
136
|
+
|
137
|
+
# l.line
|
138
|
+
# @graph_node = graph.for_path(graph_path)
|
139
|
+
# l.line
|
140
|
+
@graph_path.pop
|
141
|
+
end
|
142
|
+
nil
|
143
|
+
end
|
144
|
+
|
145
|
+
def log_structure(key, value)
|
146
|
+
log_heading(graph_node.heading, graph_node.heading_type) if graph_node.heading
|
147
|
+
add_line(KLog::LogHelper.green("#{@indent_label}#{key}"))
|
148
|
+
log_child_data(value)
|
149
|
+
end
|
150
|
+
|
151
|
+
def log_child_data(value)
|
152
|
+
depth_down
|
153
|
+
log_data(value)
|
154
|
+
depth_up
|
155
|
+
end
|
156
|
+
|
157
|
+
def log_array(key, array)
|
158
|
+
# return if items.length.zero? && graph_node.skip_empty?
|
159
|
+
|
160
|
+
items = array.clone
|
161
|
+
items.select! { |item| graph_node.filter(item) } if graph_node.filter?
|
162
|
+
items = items.take(graph_node.take) if graph_node.limited?
|
163
|
+
items.sort!(&graph_node.sort) if graph_node.sort?
|
164
|
+
|
165
|
+
return if items.length.zero? && graph_node.skip_empty?
|
166
|
+
|
167
|
+
log_heading(graph_node.heading, graph_node.heading_type) if graph_node.heading
|
168
|
+
|
169
|
+
if primitive?(items)
|
170
|
+
add_line KLog::LogHelper.kv "#{@indent_label}#{key}", items.map(&:to_s).join(', ')
|
171
|
+
else
|
172
|
+
table_print items, tp_columns(items)
|
173
|
+
end
|
174
|
+
rescue StandardError
|
175
|
+
#
|
176
|
+
end
|
177
|
+
|
178
|
+
def table_print(items, columns)
|
179
|
+
io = TablePrintIo.new(self)
|
180
|
+
|
181
|
+
tp.set :io, io
|
182
|
+
tp items, columns
|
183
|
+
tp.clear :io
|
184
|
+
end
|
185
|
+
|
186
|
+
def primitive?(items)
|
187
|
+
item = items.first
|
188
|
+
KUtil.data.basic_type?(item)
|
189
|
+
end
|
190
|
+
|
191
|
+
def log_heading(heading, heading_type)
|
192
|
+
add_lines(KLog::LogHelper.dynamic_heading(heading, size: line_width, type: heading_type))
|
193
|
+
end
|
194
|
+
|
195
|
+
def tp_columns(items)
|
196
|
+
# Use configured array columns
|
197
|
+
return graph_node.columns if graph_node.columns
|
198
|
+
|
199
|
+
# Slow but complete list of keys
|
200
|
+
# items.flat_map { |v| v.to_h.keys }.uniq
|
201
|
+
|
202
|
+
items.first.to_h.keys
|
203
|
+
end
|
204
|
+
|
205
|
+
def update_indent_label
|
206
|
+
# puts "indent_label: #{indent} - #{@recursion_depth} - #{(indent * @recursion_depth)}"
|
207
|
+
@indent_label = (indent * @recursion_depth)
|
208
|
+
end
|
209
|
+
|
210
|
+
def indent_in
|
211
|
+
@indent = "#{@indent} "
|
212
|
+
end
|
213
|
+
|
214
|
+
def indent_out
|
215
|
+
@indent = indent.chomp(' ')
|
216
|
+
end
|
217
|
+
|
218
|
+
def depth_down
|
219
|
+
@recursion_depth = recursion_depth + 1
|
220
|
+
update_indent_label
|
221
|
+
end
|
222
|
+
|
223
|
+
def depth_up
|
224
|
+
@recursion_depth = recursion_depth - 1
|
225
|
+
update_indent_label
|
226
|
+
end
|
227
|
+
|
228
|
+
def render_output
|
229
|
+
puts content if output_as.include?(:console)
|
230
|
+
File.write(output_file, clean_content) if output_as.include?(:file) && output_file
|
231
|
+
end
|
232
|
+
|
233
|
+
# convert_data_to: :open_struct
|
234
|
+
def convert_data(data)
|
235
|
+
return KUtil.data.to_open_struct(data) if convert_data_to == :open_struct
|
236
|
+
|
237
|
+
data
|
238
|
+
end
|
239
|
+
|
240
|
+
def parse_graph(data)
|
241
|
+
if data.is_a?(Hash)
|
242
|
+
transform_hash = data.each_with_object({}) do |(key, value), new_hash|
|
243
|
+
new_hash[key] = if key == :columns && value.is_a?(Array)
|
244
|
+
# Don't transform the table_print GEM columns definition as it must stay as a hash
|
245
|
+
value
|
246
|
+
else
|
247
|
+
parse_graph(value)
|
248
|
+
end
|
249
|
+
end
|
250
|
+
|
251
|
+
return OpenStruct.new(transform_hash.to_h)
|
252
|
+
end
|
253
|
+
|
254
|
+
return data.map { |o| parse_graph(o) } if data.is_a?(Array)
|
255
|
+
return parse_graph(data.to_h) if data.respond_to?(:to_h) # hash_convertible?(data)
|
256
|
+
|
257
|
+
# Some primitave type: String, True/False or an ObjectStruct
|
258
|
+
data
|
259
|
+
end
|
260
|
+
|
261
|
+
# def hash_convertible?(value)
|
262
|
+
# # Nil is a special case, it responds to :to_h but generally
|
263
|
+
# # you only want to convert nil to {} in specific scenarios
|
264
|
+
# return false if value.nil?
|
265
|
+
|
266
|
+
# value.is_a?(Array) ||
|
267
|
+
# value.is_a?(Hash) ||
|
268
|
+
# value.is_a?(Struct) ||
|
269
|
+
# value.is_a?(OpenStruct) ||
|
270
|
+
# value.respond_to?(:to_h)
|
271
|
+
# end
|
272
|
+
|
273
|
+
# Format configuration for a specific key
|
274
|
+
#
|
275
|
+
# @example Example configuration for key: tables
|
276
|
+
#
|
277
|
+
# configuration = {
|
278
|
+
# tables: {
|
279
|
+
# heading: 'Database Tables',
|
280
|
+
# take: :all,
|
281
|
+
# columns: [
|
282
|
+
# :name,
|
283
|
+
# :force,
|
284
|
+
# :primary_key,
|
285
|
+
# :id,
|
286
|
+
# columns: { display_method: lambda { |row| row.columns.map { |c| c.name }.join(', ') }, width: 100 }
|
287
|
+
# ]
|
288
|
+
# },
|
289
|
+
# people: {
|
290
|
+
# ... people configuration goes here
|
291
|
+
# }
|
292
|
+
# }
|
293
|
+
#
|
294
|
+
|
295
|
+
# Override table_print IO stream so that it writes into the structure
|
296
|
+
class TablePrintIo
|
297
|
+
def initialize(log_structure)
|
298
|
+
@log_structure = log_structure
|
299
|
+
end
|
300
|
+
|
301
|
+
def puts(line)
|
302
|
+
@log_structure.add_line(line)
|
303
|
+
end
|
304
|
+
end
|
305
|
+
|
306
|
+
class GraphNode
|
307
|
+
attr_accessor :config
|
308
|
+
|
309
|
+
class << self
|
310
|
+
def null
|
311
|
+
@null ||= OpenStruct.new
|
312
|
+
end
|
313
|
+
|
314
|
+
def for(graph, graph_path)
|
315
|
+
# node_config = graph_path.inject(graph, :send) # (uses deep nesting, but fails when nil is returned) https://stackoverflow.com/questions/15862455/ruby-nested-send
|
316
|
+
# node.nil? ? null : node.send(name) || null
|
317
|
+
node_config = graph_path.reduce(graph) do |node, name|
|
318
|
+
result = node.send(name)
|
319
|
+
|
320
|
+
break null if result.nil?
|
321
|
+
|
322
|
+
result
|
323
|
+
end
|
324
|
+
|
325
|
+
new(node_config)
|
326
|
+
end
|
327
|
+
end
|
328
|
+
|
329
|
+
def initialize(config)
|
330
|
+
@config = config || OpenStruct.new
|
331
|
+
end
|
332
|
+
|
333
|
+
# table_print compatible configuration for displaying columns for an array
|
334
|
+
def columns
|
335
|
+
config.columns
|
336
|
+
end
|
337
|
+
|
338
|
+
# Optional heading for the node
|
339
|
+
def heading
|
340
|
+
config.heading
|
341
|
+
end
|
342
|
+
|
343
|
+
# Type of heading [:heading, :subheading, :section]
|
344
|
+
def heading_type
|
345
|
+
config.heading_type || :section
|
346
|
+
end
|
347
|
+
|
348
|
+
# Node data is to be transformed
|
349
|
+
def transform?
|
350
|
+
config&.transform.respond_to?(:call)
|
351
|
+
end
|
352
|
+
|
353
|
+
# Transform node value
|
354
|
+
def transform(value)
|
355
|
+
config.transform.call(value)
|
356
|
+
end
|
357
|
+
|
358
|
+
# Array rows are filtered
|
359
|
+
def filter?
|
360
|
+
config&.filter.respond_to?(:call)
|
361
|
+
end
|
362
|
+
|
363
|
+
# Array rows are filtered via this predicate
|
364
|
+
def filter(value)
|
365
|
+
config.filter.call(value)
|
366
|
+
end
|
367
|
+
|
368
|
+
# How any array rows to take
|
369
|
+
def take
|
370
|
+
config.take
|
371
|
+
end
|
372
|
+
|
373
|
+
# Array rows are limited, see take
|
374
|
+
def limited?
|
375
|
+
config.take&.is_a?(Integer)
|
376
|
+
end
|
377
|
+
|
378
|
+
# Array rows are sorted using .sort
|
379
|
+
def sort?
|
380
|
+
config&.sort.respond_to?(:call)
|
381
|
+
end
|
382
|
+
|
383
|
+
# Use array.sort?
|
384
|
+
def sort
|
385
|
+
config.sort
|
386
|
+
end
|
387
|
+
|
388
|
+
# Skip this node
|
389
|
+
def skip?
|
390
|
+
config.skip == true
|
391
|
+
end
|
392
|
+
|
393
|
+
# Skip empty array node (my be useful for other nodes, but not yet)
|
394
|
+
def skip_empty?
|
395
|
+
config.skip_empty == true
|
396
|
+
end
|
397
|
+
end
|
398
|
+
end
|
399
|
+
end
|