1
0
Fork 0
mirror of https://github.com/pry/pry.git synced 2022-11-09 12:35:05 -05:00
pry--pry/lib/pry/commands/watch_expression.rb
Kyrylo Silin edaa1383f2 Require files from pry.rb; deps from each file that uses them
This change brings some order to how we require files. Previously, we required
app files from everywhere, including pry.rb. Now we require app files only from
pry.rb.

External and stdlib dependencies are required at places where they're used, not
globally.
2019-03-10 13:20:03 +02:00

108 lines
3.4 KiB
Ruby

class Pry
class Command
class WatchExpression < Pry::ClassCommand
match 'watch'
group 'Context'
description 'Watch the value of an expression and print a notification ' \
'whenever it changes.'
command_options use_prefix: false
banner <<-'BANNER'
Usage: watch [EXPRESSION]
watch
watch --delete [INDEX]
watch [EXPRESSION] adds an expression to the list of those being watched.
It will be re-evaluated every time you hit enter in pry. If its value has
changed, the new value will be printed to the console.
This is useful if you are step-through debugging and want to see how
something changes over time. It's also useful if you're trying to write
a method inside pry and want to check that it gives the right answers
every time you redefine it.
watch on its own displays all the currently watched expressions and their
values, and watch --delete [INDEX] allows you to delete expressions from
the list being watched.
BANNER
def options(opt)
opt.on :d, :delete,
"Delete the watch expression with the given index. If no index " \
"is given; clear all watch expressions.",
optional_argument: true, as: Integer
opt.on :l, :list,
"Show all current watch expressions and their values. Calling " \
"watch with no expressions or options will also show the watch " \
"expressions."
end
def process
if opts.present?(:delete)
delete opts[:delete]
elsif opts.present?(:list) || args.empty?
list
else
add_hook
add_expression(args)
end
end
private
def expressions
_pry_.config.watch_expressions ||= []
end
def delete(index)
if index
output.puts "Deleting watch expression ##{index}: #{expressions[index - 1]}"
expressions.delete_at(index - 1)
else
output.puts "Deleting all watched expressions"
expressions.clear
end
end
def list
if expressions.empty?
output.puts "No watched expressions"
else
_pry_.pager.open do |pager|
pager.puts "Listing all watched expressions:"
pager.puts ""
expressions.each_with_index do |expr, index|
pager.print with_line_numbers(expr.to_s, index + 1)
end
pager.puts ""
end
end
end
def eval_and_print_changed(output)
expressions.each do |expr|
expr.eval!
output.puts "#{blue 'watch'}: #{expr}" if expr.changed?
end
end
# TODO: fix arguments.
# https://github.com/pry/pry/commit/b031df2f2f5850ee6e9018f33d35f3485a9b0423
def add_expression(_arguments)
expressions << Expression.new(_pry_, target, arg_string)
output.puts "Watching #{Code.new(arg_string).highlighted}"
end
def add_hook
hook = [:after_eval, :watch_expression]
unless _pry_.hooks.hook_exists?(*hook)
_pry_.hooks.add_hook(*hook) do |_, _pry_|
eval_and_print_changed _pry_.output
end
end
end
end
Pry::Commands.add_command(Pry::Command::WatchExpression)
end
end