utils 0.68.0 → 0.69.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.
- checksums.yaml +4 -4
- data/README.md +251 -18
- data/bin/ascii7 +28 -0
- data/bin/blameline +17 -0
- data/bin/changes +69 -5
- data/bin/classify +128 -7
- data/bin/code_comment +102 -104
- data/bin/commit_message +26 -2
- data/bin/create_cstags +18 -0
- data/bin/create_tags +10 -0
- data/bin/discover +38 -1
- data/bin/edit +14 -1
- data/bin/edit_wait +14 -0
- data/bin/enum +139 -15
- data/bin/git-empty +50 -0
- data/bin/git-versions +20 -0
- data/bin/json_check +15 -1
- data/bin/long_lines +11 -2
- data/bin/myex +38 -0
- data/bin/on_change +22 -0
- data/bin/path +21 -0
- data/bin/print_method +29 -1
- data/bin/probe +52 -4
- data/bin/rainbow +52 -0
- data/bin/rd2md +15 -0
- data/bin/search +83 -1
- data/bin/sedit +6 -0
- data/bin/serve +18 -3
- data/bin/ssh-tunnel +14 -2
- data/bin/strip_spaces +17 -9
- data/bin/sync_dir +48 -1
- data/bin/untest +19 -1
- data/bin/utils-utilsrc +42 -6
- data/bin/vcf2alias +33 -0
- data/bin/yaml_check +24 -2
- data/lib/utils/config_dir.rb +127 -0
- data/lib/utils/config_file.rb +445 -1
- data/lib/utils/editor.rb +215 -3
- data/lib/utils/finder.rb +127 -16
- data/lib/utils/grepper.rb +90 -1
- data/lib/utils/irb.rb +387 -39
- data/lib/utils/line_blamer.rb +28 -0
- data/lib/utils/line_formatter.rb +198 -0
- data/lib/utils/md5.rb +14 -0
- data/lib/utils/patterns.rb +77 -3
- data/lib/utils/probe_server.rb +302 -23
- data/lib/utils/ssh_tunnel_specification.rb +58 -0
- data/lib/utils/version.rb +1 -1
- data/lib/utils/xt/source_location_extension.rb +18 -6
- data/lib/utils.rb +3 -1
- data/tests/utils_test.rb +7 -1
- data/utils.gemspec +5 -5
- metadata +4 -6
- data/bin/number_files +0 -26
- data/lib/utils/xdg_config.rb +0 -10
- /data/{COPYING → LICENSE} +0 -0
data/lib/utils/irb.rb
CHANGED
@@ -1,10 +1,9 @@
|
|
1
|
-
require 'tins/xt'
|
2
1
|
require 'irb/completion'
|
3
2
|
require 'enumerator'
|
4
3
|
require 'tempfile'
|
5
4
|
require 'pp'
|
6
|
-
require_maybe 'ap'
|
7
5
|
require 'utils'
|
6
|
+
require_maybe 'ap'
|
8
7
|
|
9
8
|
$editor = Utils::Editor.new
|
10
9
|
$pager = ENV['PAGER'] || 'less -r'
|
@@ -16,6 +15,14 @@ module Utils
|
|
16
15
|
include FileUtils
|
17
16
|
include Tins::Find
|
18
17
|
|
18
|
+
# The receiver_unless_main method retrieves the receiver name of a method
|
19
|
+
# unless it is the main object, optionally executing a block with the
|
20
|
+
# receiver name.
|
21
|
+
#
|
22
|
+
# @param method [ Method ] the method object to inspect
|
23
|
+
# @param block [ Proc ] an optional block to execute with the receiver name
|
24
|
+
#
|
25
|
+
# @return [ String, nil ] the receiver name if it is not 'main', otherwise nil
|
19
26
|
def receiver_unless_main(method, &block)
|
20
27
|
receiver_name = method.receiver.to_s
|
21
28
|
if receiver_name != 'main'
|
@@ -28,8 +35,16 @@ module Utils
|
|
28
35
|
end
|
29
36
|
private :receiver_unless_main
|
30
37
|
|
31
|
-
#
|
32
|
-
#
|
38
|
+
# The ri method invokes the ri documentation tool to display help
|
39
|
+
# information for the specified patterns. It automatically determines the
|
40
|
+
# pattern to search for when none are provided.
|
41
|
+
# The method handles different types of patterns including modules,
|
42
|
+
# objects that respond to to_str, and other objects. Documentation is
|
43
|
+
# displayed through the system's ri command with output piped to the
|
44
|
+
# pager.
|
45
|
+
#
|
46
|
+
# @param patterns [ Array ] the patterns to search for in the documentation
|
47
|
+
# @param doc [ String ] the documentation command to execute (defaults to 'ri')
|
33
48
|
def ri(*patterns, doc: 'ri')
|
34
49
|
patterns.empty? and
|
35
50
|
receiver_unless_main(method(__method__)) do |pattern|
|
@@ -48,10 +63,25 @@ module Utils
|
|
48
63
|
system "#{doc} #{patterns.map { |p| "'#{p}'" } * ' ' } | #$pager"
|
49
64
|
end
|
50
65
|
|
66
|
+
# The yri method invokes the ri documentation tool with yri as the
|
67
|
+
# documenter to display help information for the specified patterns.
|
68
|
+
#
|
69
|
+
# @param patterns [ Array<String> ] the patterns to look up documentation for
|
51
70
|
def yri(*patterns)
|
52
71
|
ri(*patterns, doc: 'yri')
|
53
72
|
end
|
54
73
|
|
74
|
+
# The irb_open method opens a URL or executes a block to capture output
|
75
|
+
# and open it.
|
76
|
+
#
|
77
|
+
# This method provides a way to open URLs or capture the output of a
|
78
|
+
# block and open it in the default application. If a URL is provided, it
|
79
|
+
# directly opens the URL. If a block is given, it captures the output of
|
80
|
+
# the block, writes it to a temporary file, and opens that file. If
|
81
|
+
# neither is provided, it raises an error.
|
82
|
+
#
|
83
|
+
# @param url [ String, nil ] the URL to open
|
84
|
+
# @param block [ Proc, nil ] the block to capture output from
|
55
85
|
def irb_open(url = nil, &block)
|
56
86
|
case
|
57
87
|
when url
|
@@ -69,22 +99,42 @@ module Utils
|
|
69
99
|
end
|
70
100
|
end
|
71
101
|
|
72
|
-
#
|
73
|
-
|
74
|
-
#
|
102
|
+
# This method obtains the complete list of instance methods available for
|
103
|
+
# the specified object's class, then processes them through the
|
104
|
+
# irb_wrap_methods helper to prepare them for interactive use in IRB.
|
105
|
+
#
|
106
|
+
# @param obj [ Object ] the object whose class instance methods are to be retrieved
|
107
|
+
#
|
108
|
+
# @return [ Array ] an array of wrapped method objects suitable for IRB interaction
|
75
109
|
def irb_all_class_instance_methods(obj = self)
|
76
110
|
methods = obj.class.instance_methods
|
77
111
|
irb_wrap_methods obj, methods
|
78
112
|
end
|
79
113
|
|
80
|
-
#
|
81
|
-
#
|
114
|
+
# The irb_class_instance_methods method retrieves instance methods
|
115
|
+
# defined directly in the class of the given object, excluding inherited
|
116
|
+
# methods, and wraps them for enhanced interactive exploration in IRB
|
117
|
+
# environment.
|
118
|
+
#
|
119
|
+
# @param obj [ Object ] the object whose class instance methods are to be retrieved
|
120
|
+
#
|
121
|
+
# @return [ Array ] an array of wrapped method objects suitable for IRB interaction
|
82
122
|
def irb_class_instance_methods(obj = self)
|
83
123
|
methods = obj.class.instance_methods(false)
|
84
124
|
irb_wrap_methods obj, methods
|
85
125
|
end
|
86
126
|
|
87
|
-
#
|
127
|
+
# The irb_all_instance_methods method retrieves all instance methods
|
128
|
+
# defined on a module.
|
129
|
+
#
|
130
|
+
# This method collects the instance methods from the specified module and
|
131
|
+
# wraps them for enhanced interactive exploration in IRB. It is designed
|
132
|
+
# to provide a more user-friendly interface for examining module methods
|
133
|
+
# within the interactive Ruby environment.
|
134
|
+
#
|
135
|
+
# @param modul [ Object ] the module from which to retrieve instance methods
|
136
|
+
#
|
137
|
+
# @return [ Array ] an array of wrapped method objects suitable for IRB interaction
|
88
138
|
def irb_all_instance_methods(modul = self)
|
89
139
|
methods = modul.instance_methods
|
90
140
|
irb_wrap_methods modul, methods, true
|
@@ -92,19 +142,48 @@ module Utils
|
|
92
142
|
|
93
143
|
# Return instance methods defined in module modul without the inherited/mixed
|
94
144
|
# in methods.
|
145
|
+
# The irb_instance_methods method retrieves instance methods defined directly in a module.
|
146
|
+
#
|
147
|
+
# This method fetches all instance methods that are explicitly defined within the specified module,
|
148
|
+
# excluding inherited methods. It then wraps these methods for enhanced interactive exploration
|
149
|
+
# within the IRB environment.
|
150
|
+
#
|
151
|
+
# @param modul [ Object ] the module from which to retrieve instance methods
|
152
|
+
#
|
153
|
+
# @return [ Array ] an array of wrapped method objects suitable for IRB interaction
|
95
154
|
def irb_instance_methods(modul = self)
|
96
155
|
methods = modul.instance_methods(false)
|
97
156
|
irb_wrap_methods modul, methods, true
|
98
157
|
end
|
99
158
|
|
100
|
-
#
|
159
|
+
# The irb_all_methods method retrieves all methods available on an
|
160
|
+
# object.
|
161
|
+
#
|
162
|
+
# This method collects all methods associated with the given object
|
163
|
+
# (including its singleton methods) and wraps them for enhanced
|
164
|
+
# interactive exploration in IRB. It provides a comprehensive list
|
165
|
+
# of methods that can be used to understand the object's capabilities and
|
166
|
+
# interface.
|
167
|
+
#
|
168
|
+
# @param obj [ Object ] the object whose methods are to be retrieved
|
169
|
+
#
|
170
|
+
# @return [ Array ] an array of wrapped method objects for interactive use
|
101
171
|
def irb_all_methods(obj = self)
|
102
172
|
methods = obj.methods
|
103
173
|
irb_wrap_methods obj, methods
|
104
174
|
end
|
105
175
|
|
106
|
-
#
|
107
|
-
#
|
176
|
+
# The irb_methods method retrieves instance methods defined in the class
|
177
|
+
# hierarchy excluding those inherited from ancestor classes.
|
178
|
+
#
|
179
|
+
# This method computes a list of instance methods that are directly
|
180
|
+
# defined in the class of the given object, excluding any methods that
|
181
|
+
# are inherited from its superclass or modules. It then wraps these
|
182
|
+
# methods for enhanced display in IRB.
|
183
|
+
#
|
184
|
+
# @param obj [ Object ] the object whose class methods are to be examined
|
185
|
+
#
|
186
|
+
# @return [ Array ] an array of wrapped method objects for display in IRB
|
108
187
|
def irb_methods(obj = self)
|
109
188
|
methods = obj.class.ancestors[1..-1].inject(obj.methods) do |all, a|
|
110
189
|
all -= a.instance_methods
|
@@ -112,11 +191,32 @@ module Utils
|
|
112
191
|
irb_wrap_methods obj, methods
|
113
192
|
end
|
114
193
|
|
115
|
-
#
|
116
|
-
|
194
|
+
# The irb_singleton_methods method retrieves singleton methods associated
|
195
|
+
# with an object.
|
196
|
+
#
|
197
|
+
# This method collects all singleton methods defined on the specified object,
|
198
|
+
# excluding inherited methods, and prepares them for display in an interactive
|
199
|
+
# Ruby environment.
|
200
|
+
#
|
201
|
+
# @param obj [ Object ] the object whose singleton methods are to be retrieved
|
202
|
+
#
|
203
|
+
# @return [ Array ] an array of singleton method names associated with the object
|
204
|
+
def irb_singleton_methods(obj = self)
|
117
205
|
irb_wrap_methods obj, obj.methods(false)
|
118
206
|
end
|
119
207
|
|
208
|
+
# The irb_wrap_methods method creates wrapped method objects for introspection.
|
209
|
+
#
|
210
|
+
# This method takes a set of method names and wraps them in a way that allows
|
211
|
+
# for easier inspection and display within an IRB session. It handles
|
212
|
+
# potential errors during the wrapping process by rescuing exceptions and
|
213
|
+
# filtering out invalid entries.
|
214
|
+
#
|
215
|
+
# @param obj [ Object ] the object whose methods are being wrapped
|
216
|
+
# @param methods [ Array ] the array of method names to wrap
|
217
|
+
# @param modul [ TrueClass, FalseClass ] flag indicating if the methods are module methods
|
218
|
+
#
|
219
|
+
# @return [ Array ] an array of wrapped method objects sorted in ascending order
|
120
220
|
def irb_wrap_methods(obj = self, methods = methods(), modul = false)
|
121
221
|
methods.map do |name|
|
122
222
|
MethodWrapper.new(obj, name, modul) rescue nil
|
@@ -126,6 +226,14 @@ module Utils
|
|
126
226
|
class WrapperBase
|
127
227
|
include Comparable
|
128
228
|
|
229
|
+
# The initialize method sets up the instance name by converting the
|
230
|
+
# input to a string representation.
|
231
|
+
#
|
232
|
+
# This method handles different input types by converting them to a
|
233
|
+
# string, prioritizing to_str over to_sym and falling back to to_s if
|
234
|
+
# neither is available.
|
235
|
+
#
|
236
|
+
# @param name [ Object ] the input name to be converted to a string
|
129
237
|
def initialize(name)
|
130
238
|
@name =
|
131
239
|
case
|
@@ -138,8 +246,16 @@ module Utils
|
|
138
246
|
end
|
139
247
|
end
|
140
248
|
|
249
|
+
# The name reader method returns the value of the name instance
|
250
|
+
# variable.
|
251
|
+
#
|
252
|
+
# @return [ String] the value stored in the name instance variable
|
141
253
|
attr_reader :name
|
142
254
|
|
255
|
+
# The description reader method provides access to the description
|
256
|
+
# attribute.
|
257
|
+
#
|
258
|
+
# @return [ String, nil ] the description value or nil if not set
|
143
259
|
attr_reader :description
|
144
260
|
|
145
261
|
alias to_str description
|
@@ -148,63 +264,148 @@ module Utils
|
|
148
264
|
|
149
265
|
alias to_s description
|
150
266
|
|
267
|
+
# The == method assigns a new name value to the instance variable.
|
268
|
+
#
|
269
|
+
# @param name [ Object ] the name value to be assigned
|
270
|
+
#
|
271
|
+
# @return [ Object ] returns the assigned name value
|
151
272
|
def ==(name)
|
152
273
|
@name = name
|
153
274
|
end
|
154
275
|
|
155
276
|
alias eql? ==
|
156
277
|
|
278
|
+
# The hash method returns the hash value of the name attribute.
|
279
|
+
#
|
280
|
+
# @return [ Integer ] the hash value used for object identification
|
157
281
|
def hash
|
158
282
|
@name.hash
|
159
283
|
end
|
160
284
|
|
285
|
+
# The <=> method compares the names of two objects for sorting purposes.
|
286
|
+
#
|
287
|
+
# @param other [ Object ] the other object to compare against
|
288
|
+
#
|
289
|
+
# @return [ Integer ] -1 if this object's name is less than the other's,
|
290
|
+
# 0 if they are equal, or 1 if this object's name is greater than the other's
|
161
291
|
def <=>(other)
|
162
292
|
@name <=> other.name
|
163
293
|
end
|
164
294
|
end
|
165
295
|
|
166
296
|
class MethodWrapper < WrapperBase
|
297
|
+
# The initialize method sets up a new instance with the specified
|
298
|
+
# object, method name, and module flag.
|
299
|
+
#
|
300
|
+
# This method creates and configures a new instance by storing the
|
301
|
+
# method object and its description, handling both instance methods and
|
302
|
+
# regular methods based on the module flag parameter.
|
303
|
+
#
|
304
|
+
# @param obj [ Object ] the object from which to retrieve the method
|
305
|
+
# @param name [ String ] the name of the method to retrieve
|
306
|
+
# @param modul [ TrueClass, FalseClass ] flag indicating whether to retrieve an instance method
|
167
307
|
def initialize(obj, name, modul)
|
168
308
|
super(name)
|
169
309
|
@method = modul ? obj.instance_method(name) : obj.method(name)
|
170
310
|
@description = @method.description(style: :namespace)
|
171
311
|
end
|
172
312
|
|
313
|
+
# The method reader returns the method object associated with the
|
314
|
+
# instance.
|
173
315
|
attr_reader :method
|
174
316
|
|
317
|
+
# The owner method retrieves the owner of the method object.
|
318
|
+
#
|
319
|
+
# This method checks if the wrapped method object responds to the owner
|
320
|
+
# message and returns the owner if available, otherwise it returns nil.
|
321
|
+
#
|
322
|
+
# @return [ Object, nil ] the owner of the method or nil if not applicable
|
175
323
|
def owner
|
176
324
|
method.respond_to?(:owner) ? method.owner : nil
|
177
325
|
end
|
178
326
|
|
327
|
+
# The arity method returns the number of parameters expected by the method.
|
328
|
+
#
|
329
|
+
# @return [ Integer ] the number of required parameters for the method
|
179
330
|
def arity
|
180
331
|
method.arity
|
181
332
|
end
|
182
333
|
|
334
|
+
# The source_location method retrieves the file path and line number
|
335
|
+
# where the method is defined.
|
336
|
+
#
|
337
|
+
# This method accesses the underlying source location information for
|
338
|
+
# the method object, returning an array that contains the filename and
|
339
|
+
# line number of the method's definition.
|
340
|
+
#
|
341
|
+
# @return [ Array<String, Integer> ] an array containing the filename and line number
|
342
|
+
# where the method is defined, or nil if the location cannot be determined
|
183
343
|
def source_location
|
184
344
|
method.source_location
|
185
345
|
end
|
186
346
|
|
347
|
+
# The <=> method compares the descriptions of two objects for ordering
|
348
|
+
# purposes.
|
349
|
+
#
|
350
|
+
# @param other [ Object ] the other object to compare against
|
351
|
+
#
|
352
|
+
# @return [ Integer ] -1 if this object's description is less than the other's,
|
353
|
+
# 0 if they are equal, or 1 if this object's description is greater than the other's
|
187
354
|
def <=>(other)
|
188
355
|
@description <=> other.description
|
189
356
|
end
|
190
357
|
end
|
191
358
|
|
192
359
|
class ConstantWrapper < WrapperBase
|
360
|
+
# The initialize method sets up a new instance with the provided object
|
361
|
+
# and name.
|
362
|
+
#
|
363
|
+
# This method configures the instance by storing a reference to the
|
364
|
+
# object's class and creating a description string that combines the
|
365
|
+
# name with the class name.
|
366
|
+
#
|
367
|
+
# @param obj [ Object ] the object whose class will be referenced
|
368
|
+
# @param name [ String ] the name to be used in the description
|
369
|
+
#
|
370
|
+
# @return [ Utils::Patterns::Pattern ] a new pattern instance configured with the provided arguments
|
193
371
|
def initialize(obj, name)
|
194
372
|
super(name)
|
195
373
|
@klass = obj.class
|
196
374
|
@description = "#@name:#@klass"
|
197
375
|
end
|
198
376
|
|
377
|
+
# The klass reader method provides access to the class value stored in the instance.
|
378
|
+
#
|
379
|
+
# @return [ Object ] the class value
|
199
380
|
attr_reader :klass
|
200
381
|
end
|
201
382
|
|
202
|
-
#
|
383
|
+
# The irb_constants method retrieves and wraps all constants from a given
|
384
|
+
# module.
|
385
|
+
#
|
386
|
+
# This method collects all constants defined in the specified module,
|
387
|
+
# creates ConstantWrapper instances for each constant, and returns them
|
388
|
+
# sorted in ascending order.
|
389
|
+
#
|
390
|
+
# @param modul [ Object ] the module from which to retrieve constants
|
391
|
+
#
|
392
|
+
# @return [ Array<ConstantWrapper> ] an array of ConstantWrapper objects
|
393
|
+
# representing the constants in the module, sorted alphabetically
|
203
394
|
def irb_constants(modul = self)
|
204
395
|
modul.constants.map { |c| ConstantWrapper.new(modul.const_get(c), c) }.sort
|
205
396
|
end
|
206
397
|
|
207
|
-
#
|
398
|
+
# The irb_subclasses method retrieves and wraps subclass information for
|
399
|
+
# a given class.
|
400
|
+
#
|
401
|
+
# This method fetches the subclasses of the specified class and creates
|
402
|
+
# ConstantWrapper instances for each subclass, allowing them to be sorted
|
403
|
+
# and displayed in a structured format.
|
404
|
+
#
|
405
|
+
# @param klass [ Object ] the class object to retrieve subclasses from
|
406
|
+
#
|
407
|
+
# @return [ Array<ConstantWrapper> ] an array of ConstantWrapper objects
|
408
|
+
# representing the subclasses
|
208
409
|
def irb_subclasses(klass = self)
|
209
410
|
klass.subclasses.map { |c| ConstantWrapper.new(eval(c), c) }.sort
|
210
411
|
end
|
@@ -213,6 +414,18 @@ module Utils
|
|
213
414
|
Infinity = 1.0 / 0 # I like to define the infinite.
|
214
415
|
end
|
215
416
|
|
417
|
+
# The capture_output method captures stdout and optionally stderr output
|
418
|
+
# during code execution.
|
419
|
+
#
|
420
|
+
# This method temporarily redirects standard output (and optionally
|
421
|
+
# standard error) to a temporary file, executes the provided block, and
|
422
|
+
# then returns the captured output as a string.
|
423
|
+
#
|
424
|
+
# @param with_stderr [ TrueClass, FalseClass ] whether to also capture standard error output
|
425
|
+
#
|
426
|
+
# @yield [ void ] the block of code to execute while capturing output
|
427
|
+
#
|
428
|
+
# @return [ String ] the captured output as a string
|
216
429
|
def capture_output(with_stderr = false)
|
217
430
|
require 'tempfile'
|
218
431
|
begin
|
@@ -229,11 +442,16 @@ module Utils
|
|
229
442
|
temp.read
|
230
443
|
end
|
231
444
|
|
232
|
-
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
#
|
445
|
+
# Use pager on the output of the commands given in the block. The less
|
446
|
+
# method executes a block and outputs its result through the pager.
|
447
|
+
#
|
448
|
+
# This method runs the provided block in a controlled environment,
|
449
|
+
# captures its output, and streams that output through the system's
|
450
|
+
# configured pager for display.
|
451
|
+
#
|
452
|
+
# @param with_stderr [ TrueClass, FalseClass ] whether to include standard error in the capture
|
453
|
+
#
|
454
|
+
# @yield [ void ]
|
237
455
|
def less(with_stderr = false, &block)
|
238
456
|
IO.popen($pager, 'w') do |f|
|
239
457
|
f.write capture_output(with_stderr, &block)
|
@@ -242,35 +460,67 @@ module Utils
|
|
242
460
|
nil
|
243
461
|
end
|
244
462
|
|
245
|
-
|
463
|
+
# The irb_time method measures the execution time of a block and outputs
|
464
|
+
# the duration to standard error.
|
465
|
+
#
|
466
|
+
# @param n [ Integer ] the number of times to execute the block, defaults
|
467
|
+
# to 1
|
468
|
+
#
|
469
|
+
# @yield [ block ] the block to be executed and timed
|
470
|
+
def irb_time(n = 1, &block)
|
246
471
|
s = Time.now
|
247
|
-
n.times
|
248
|
-
yield
|
249
|
-
end
|
472
|
+
n.times(&block)
|
250
473
|
d = Time.now - s
|
474
|
+
ensure
|
475
|
+
d ||= Time.now - s
|
251
476
|
if n == 1
|
252
477
|
warn "Took %.3fs seconds." % d
|
253
478
|
else
|
254
479
|
warn "Took %.3fs seconds, %.3fs per call (avg)." % [ d, d / n ]
|
255
480
|
end
|
256
|
-
d
|
257
481
|
end
|
258
482
|
|
259
|
-
|
483
|
+
# The irb_time_result method executes a block n times while measuring
|
484
|
+
# execution time and returns the result of the last execution.
|
485
|
+
#
|
486
|
+
# @param n [ Integer ] the number of times to execute the block
|
487
|
+
#
|
488
|
+
# @yield [ i ]
|
489
|
+
#
|
490
|
+
# @return [ Object ] the result of the last block execution
|
491
|
+
def irb_time_result(n = 1)
|
260
492
|
r = nil
|
261
|
-
irb_time(n) { r = yield }
|
493
|
+
irb_time(n) { |i| r = yield(i) }
|
262
494
|
r
|
263
495
|
end
|
264
496
|
|
497
|
+
# The irb_time_watch method monitors and reports performance metrics over
|
498
|
+
# time.
|
499
|
+
#
|
500
|
+
# This method continuously measures the output of a provided block,
|
501
|
+
# calculating differences and rates of change between successive
|
502
|
+
# measurements. It tracks these metrics and displays them with timing
|
503
|
+
# information, useful for observing how values evolve during execution.
|
504
|
+
#
|
505
|
+
# @param duration [ Integer ] the time interval in seconds between
|
506
|
+
# measurements
|
507
|
+
#
|
508
|
+
# @yield [ i ] the block to be measured, receiving the iteration count as an argument
|
265
509
|
def irb_time_watch(duration = 1)
|
266
510
|
start = Time.now
|
267
511
|
pre = nil
|
268
512
|
avg = Hash.new
|
513
|
+
i = 0
|
514
|
+
fetch_next = -> cur do
|
515
|
+
pre = cur.map(&:to_f)
|
516
|
+
i += 1
|
517
|
+
sleep duration
|
518
|
+
end
|
269
519
|
loop do
|
270
|
-
cur = [ yield ].flatten
|
520
|
+
cur = [ yield(i) ].flatten
|
271
521
|
unless pre
|
272
|
-
|
273
|
-
|
522
|
+
fetch_next.(cur)
|
523
|
+
redo
|
274
524
|
end
|
275
525
|
expired = Time.now - start
|
276
526
|
diffs = cur.zip(pre).map { |c, p| c - p }
|
@@ -288,12 +538,25 @@ module Utils
|
|
288
538
|
end
|
289
539
|
avg[i]
|
290
540
|
}
|
291
|
-
warn "#{expired} #{cur.zip(diffs, rates, durs)
|
292
|
-
|
541
|
+
warn "#{expired} #{cur.zip(diffs, rates, durs) * ' '} 𝝙 / per sec."
|
542
|
+
fetch_next.(cur)
|
293
543
|
sleep duration
|
294
544
|
end
|
295
545
|
end
|
296
546
|
|
547
|
+
# The irb_write method writes text to a file or executes a block to
|
548
|
+
# generate content for writing.
|
549
|
+
#
|
550
|
+
# This method provides a convenient way to write content to a file,
|
551
|
+
# either by passing the text directly or by executing a block that
|
552
|
+
# generates the content. It uses secure file writing to ensure safety.
|
553
|
+
#
|
554
|
+
# @param filename [ String ] the path to the file where content will be
|
555
|
+
# written
|
556
|
+
# @param text [ String, nil ] the text content to write to the file, or
|
557
|
+
# nil if using a block
|
558
|
+
#
|
559
|
+
# @yield [ ] a block that generates content to be written to the file
|
297
560
|
def irb_write(filename, text = nil, &block)
|
298
561
|
if text.nil? && block
|
299
562
|
File.secure_write filename, nil, 'wb', &block
|
@@ -302,6 +565,21 @@ module Utils
|
|
302
565
|
end
|
303
566
|
end
|
304
567
|
|
568
|
+
# The irb_read method reads the contents of a file either entirely or in
|
569
|
+
# chunks. When a block is provided, it reads the file in chunks of the
|
570
|
+
# specified size and yields each chunk to the block.
|
571
|
+
# If no block is given, it reads the entire file content at once and
|
572
|
+
# returns it as a string.
|
573
|
+
#
|
574
|
+
# @param filename [ String ] the path to the file to be read
|
575
|
+
# @param chunk_size [ Integer ] the size of each chunk to read when a
|
576
|
+
# block is provided
|
577
|
+
#
|
578
|
+
# @yield [ chunk ] yields each chunk of the file to the block
|
579
|
+
# @yieldparam chunk [ String ] a portion of the file content
|
580
|
+
#
|
581
|
+
# @return [ String, nil ] the entire file content if no block is given,
|
582
|
+
# otherwise nil
|
305
583
|
def irb_read(filename, chunk_size = 8_192)
|
306
584
|
if block_given?
|
307
585
|
File.open(filename) do |file|
|
@@ -309,11 +587,25 @@ module Utils
|
|
309
587
|
yield file.read(chunk_size)
|
310
588
|
end
|
311
589
|
end
|
590
|
+
nil
|
312
591
|
else
|
313
592
|
File.read filename
|
314
593
|
end
|
315
594
|
end
|
316
595
|
|
596
|
+
# The irb_load! method loads Ruby files by their names into the current
|
597
|
+
# environment.
|
598
|
+
#
|
599
|
+
# This method takes one or more file names and attempts to locate and
|
600
|
+
# load the corresponding Ruby files from the current directory and its
|
601
|
+
# subdirectories. It ensures that each file is loaded only once by
|
602
|
+
# tracking loaded files using their MD5 checksums. The method outputs
|
603
|
+
# messages to standard error indicating which files have been
|
604
|
+
# successfully loaded.
|
605
|
+
#
|
606
|
+
# @param files [ Array<String> ] the names of the Ruby files to be loaded
|
607
|
+
#
|
608
|
+
# @return [ nil ] always returns nil after processing all specified files
|
317
609
|
def irb_load!(*files)
|
318
610
|
files = files.map { |f| f.gsub(/(\.rb)?\Z/, '.rb') }
|
319
611
|
loaded = {}
|
@@ -333,6 +625,14 @@ module Utils
|
|
333
625
|
nil
|
334
626
|
end
|
335
627
|
|
628
|
+
# The ed method opens files for editing using the system editor.
|
629
|
+
#
|
630
|
+
# This method provides a convenient way to edit files by invoking the
|
631
|
+
# configured editor. When called without arguments, it edits the current
|
632
|
+
# object's representation. When called with file arguments, it edits those
|
633
|
+
# specific files.
|
634
|
+
#
|
635
|
+
# @param files [ Array ] an array of file paths to be edited
|
336
636
|
def ed(*files)
|
337
637
|
if files.empty?
|
338
638
|
$editor.full?(:edit, self)
|
@@ -343,6 +643,16 @@ module Utils
|
|
343
643
|
|
344
644
|
if defined?(ActiveRecord::Base)
|
345
645
|
$logger = Logger.new(STDERR)
|
646
|
+
# The irb_toggle_logging method toggles the logging configuration for
|
647
|
+
# ActiveRecord.
|
648
|
+
#
|
649
|
+
# This method manages the logger setting for ActiveRecord by switching
|
650
|
+
# between a custom logger and the previously configured logger. It
|
651
|
+
# returns true when switching to the custom logger, and false when
|
652
|
+
# reverting to the original logger.
|
653
|
+
#
|
654
|
+
# @return [ TrueClass, FalseClass ] true if the logger was switched to
|
655
|
+
# the custom logger, false if it was reverted to the original logger
|
346
656
|
def irb_toggle_logging
|
347
657
|
require 'logger'
|
348
658
|
if ActiveRecord::Base.logger != $logger
|
@@ -358,14 +668,39 @@ module Utils
|
|
358
668
|
end
|
359
669
|
|
360
670
|
module Regexp
|
361
|
-
#
|
362
|
-
|
363
|
-
|
671
|
+
# The show_match method evaluates a string against the receiver pattern
|
672
|
+
# and highlights matching portions.
|
673
|
+
#
|
674
|
+
# This method tests whether the provided string matches the pattern
|
675
|
+
# represented by the receiver. When a match is found, it applies the
|
676
|
+
# success proc to highlight the matched portion of the string. If no
|
677
|
+
# match is found, it applies the failure proc to indicate that no match
|
678
|
+
# was found.
|
679
|
+
#
|
680
|
+
# @param string [ String ] the string to be tested against the pattern
|
681
|
+
# @param success [ Proc ] a proc that processes the matched portion of the string
|
682
|
+
# @param failure [ Proc ] a proc that processes the "no match" indication
|
683
|
+
#
|
684
|
+
# @return [ String ] the formatted string with matched portions highlighted or a no match message
|
685
|
+
def show_match(
|
686
|
+
string,
|
687
|
+
success: -> s { Term::ANSIColor.green { s } },
|
688
|
+
failure: -> s { Term::ANSIColor.red { s } }
|
689
|
+
)
|
690
|
+
string =~ self ? "#{$`}#{success.($&)}#{$'}" : failure.("no match")
|
364
691
|
end
|
365
692
|
end
|
366
693
|
|
367
694
|
module String
|
368
|
-
#
|
695
|
+
# The | method executes a shell command and returns its output.
|
696
|
+
#
|
697
|
+
# This method takes a command string, pipes the current string to it via
|
698
|
+
# stdin, captures the command's stdout, and returns the resulting output
|
699
|
+
# as a string.
|
700
|
+
#
|
701
|
+
# @param cmd [ String ] the shell command to execute
|
702
|
+
#
|
703
|
+
# @return [ String ] the output of the executed command
|
369
704
|
def |(cmd)
|
370
705
|
IO.popen(cmd, 'w+') do |f|
|
371
706
|
f.write self
|
@@ -374,12 +709,25 @@ module Utils
|
|
374
709
|
end
|
375
710
|
end
|
376
711
|
|
377
|
-
#
|
712
|
+
# The >> method writes the string content to a file securely.
|
713
|
+
#
|
714
|
+
# This method takes a filename and uses File.secure_write to write the
|
715
|
+
# string's content to that file, ensuring secure file handling practices
|
716
|
+
# are followed.
|
717
|
+
#
|
718
|
+
# @param filename [ String ] the path to the file where the string content will be written
|
719
|
+
#
|
720
|
+
# @return [ Integer ] the number of bytes written to the file
|
378
721
|
def >>(filename)
|
379
722
|
File.secure_write(filename, self)
|
380
723
|
end
|
381
724
|
end
|
382
725
|
|
726
|
+
# The configure method sets up IRB configuration options.
|
727
|
+
#
|
728
|
+
# This method configures the IRB environment by setting the history save
|
729
|
+
# limit and customizing the prompt display when IRB is running in
|
730
|
+
# interactive mode.
|
383
731
|
def self.configure
|
384
732
|
::IRB.conf[:SAVE_HISTORY] = 1000
|
385
733
|
if ::IRB.conf[:PROMPT]
|