diff options
Diffstat (limited to 'lib/Reply')
-rw-r--r-- | lib/Reply/Plugin.pm | 117 | ||||
-rw-r--r-- | lib/Reply/Plugin/Colors.pm | 20 | ||||
-rw-r--r-- | lib/Reply/Plugin/DataDump.pm | 12 | ||||
-rw-r--r-- | lib/Reply/Plugin/DataDumper.pm | 12 | ||||
-rw-r--r-- | lib/Reply/Plugin/Editor.pm | 20 | ||||
-rw-r--r-- | lib/Reply/Plugin/FancyPrompt.pm | 14 | ||||
-rw-r--r-- | lib/Reply/Plugin/Hints.pm | 15 | ||||
-rw-r--r-- | lib/Reply/Plugin/Interrupt.pm | 13 | ||||
-rw-r--r-- | lib/Reply/Plugin/LexicalPersistence.pm | 14 | ||||
-rw-r--r-- | lib/Reply/Plugin/LoadClass.pm | 16 | ||||
-rw-r--r-- | lib/Reply/Plugin/Nopaste.pm | 22 | ||||
-rw-r--r-- | lib/Reply/Plugin/Packages.pm | 16 | ||||
-rw-r--r-- | lib/Reply/Plugin/ReadLine.pm | 23 | ||||
-rw-r--r-- | lib/Reply/Plugin/ResultCache.pm | 17 |
14 files changed, 329 insertions, 2 deletions
diff --git a/lib/Reply/Plugin.pm b/lib/Reply/Plugin.pm index 0858758..ec16ddf 100644 --- a/lib/Reply/Plugin.pm +++ b/lib/Reply/Plugin.pm @@ -1,6 +1,123 @@ package Reply::Plugin; use strict; use warnings; +# ABSTRACT: base class for Reply plugins + +=head1 SYNOPSIS + + package Reply::Plugin::Foo; + use strict; + use warnings; + + use base 'Reply::Plugin'; + + # ... + +=head1 DESCRIPTION + +A L<Reply> plugin is an object which adds some functionality to a Reply +instance by implementing some specific methods which the Reply object will call +at various points during execution. Plugins may implement as many callback +methods as necessary to implement their functionality (although the more +callbacks a given plugin implements, the more likely it is that the plugin may +be more useful as multiple independent plugins). + +Callback methods have two potential calling conventions: + +=over 4 + +=item wrapped + +Wrapped plugins receive a coderef as their first argument (before any arguments +to the callback itself), and that coderef can be used to call the next callback +in the list (if more than one plugin implements a given callback). In +particular, this allows calling the next plugin multiple times, or not at all +if necessary. Wrapped plugins should always call their coderef in list context. +All plugins listed below are wrapped plugins unless indicated otherwise. + +=item chained + +Chained plugins receive a list of arguments, and return a new list of arguments +which will be passed to the next plugin in the chain. This allows each plugin a +chance to modify a value before it's actually used by the repl. + +=back + +=head2 CALLBACKS + +=over 4 + +=item prompt + +Called to determine the prompt to use when reading the next line. Takes no +arguments, and returns a single string to use as the prompt. The default +implementation returns C<< ">" >> + +=item read_line + +Called to actually read a line from the user. Takes no arguments, and returns a +single string. The default implementation uses the C<< <> >> operator to read a +single line from the user. + +=item command_C<$name> (chained) + +If the line read from the user is of the form "#foo args...", then plugins will +be searched for a callback method named C<command_foo>. This callback takes a +single string containing the provided arguments, and returns a new line to +evaluate instead, if any. + +=item mangle_line (chained) + +Modifies the line read from the user before it's evaluated. Takes the line as a +string and returns the modified line. + +=item compile + +Compiles the string of Perl code into a coderef. Takes the line of code as a +string and a hash of extra parameters, and returns the coderef to be executed. +The default implementation uses L<Eval::Closure> to compile the given string. +The extra parameters are passed directly to the C<eval_closure> call. + +=item execute + +Executes the coderef which has just been compiled. Takes the coderef and a list +of parameters to pass to it, and returns the list of results returned by +calling the coderef. The default implementation just calls the coderef +directly. + +=item mangle_error (chained) + +If the C<compile> or C<execute> callbacks throw an exception, this callback +will be called to modify the exception before it is passed to C<print_error>. +It receives the exception and returns the modified exception. + +=item print_error + +If the C<compile> or C<execute> callbacks throw an exception, this callback +will be called to display it to the user. It receives the exception and returns +nothing. The default implementation just uses C<print> to print it to the +screen. + +=item mangle_result (chained) + +This callback is used to modify the result of evaluating the line of code +before it is displayed. It receives the list of results and returns a modified +list of results. + +=item print_result + +This callback displays to the user the results of evaluating the given line of +code. It receives the list of results, and returns nothing. The default +implementation just uses C<print> to print them to the screen. + +=item loop (chained) + +This callback is called at the end of each evaluation. It receives no +parameters and returns nothing. + +=back + +=cut sub new { bless {}, shift } diff --git a/lib/Reply/Plugin/Colors.pm b/lib/Reply/Plugin/Colors.pm index 8b68119..839654d 100644 --- a/lib/Reply/Plugin/Colors.pm +++ b/lib/Reply/Plugin/Colors.pm @@ -1,11 +1,31 @@ package Reply::Plugin::Colors; use strict; use warnings; +# ABSTRACT: colorize output use base 'Reply::Plugin'; use Term::ANSIColor; +=head1 SYNOPSIS + + ; .replyrc + [Colors] + error = bright red + warning = bright yellow + result = bright green + +=head1 DESCRIPTION + +This plugin adds coloring to the results when they are printed to the screen. +By default, errors are C<red>, warnings are C<yellow>, and normal results are +C<green>, although this can be overridden through configuration as shown in the +synopsis. L<Term::ANSIColor> is used to generate the colors, so any value that +is accepted by that module is a valid value for the C<error>, C<warning>, and +C<result> options. + +=cut + sub new { my $class = shift; my %opts = @_; diff --git a/lib/Reply/Plugin/DataDump.pm b/lib/Reply/Plugin/DataDump.pm index e80deab..64d756e 100644 --- a/lib/Reply/Plugin/DataDump.pm +++ b/lib/Reply/Plugin/DataDump.pm @@ -1,11 +1,23 @@ package Reply::Plugin::DataDump; use strict; use warnings; +# ABSTRACT: format results using Data::Dump use base 'Reply::Plugin'; use Data::Dump 'pp'; +=head1 SYNOPSIS + + ; .replyrc + [DataDumper] + +=head1 DESCRIPTION + +This plugin uses L<Data::Dump> to format results. + +=cut + sub mangle_result { my $self = shift; my (@result) = @_; diff --git a/lib/Reply/Plugin/DataDumper.pm b/lib/Reply/Plugin/DataDumper.pm index 676344a..7491c60 100644 --- a/lib/Reply/Plugin/DataDumper.pm +++ b/lib/Reply/Plugin/DataDumper.pm @@ -1,11 +1,23 @@ package Reply::Plugin::DataDumper; use strict; use warnings; +# ABSTRACT: format results using Data::Dumper use base 'Reply::Plugin'; use Data::Dumper; +=head1 SYNOPSIS + + ; .replyrc + [DataDumper] + +=head1 DESCRIPTION + +This plugin uses L<Data::Dumper> to format results. + +=cut + sub mangle_result { my $self = shift; my (@result) = @_; diff --git a/lib/Reply/Plugin/Editor.pm b/lib/Reply/Plugin/Editor.pm index fe5c23e..e7ff91d 100644 --- a/lib/Reply/Plugin/Editor.pm +++ b/lib/Reply/Plugin/Editor.pm @@ -1,6 +1,7 @@ package Reply::Plugin::Editor; use strict; use warnings; +# ABSTRACT: command to edit the current line in a text editor use base 'Reply::Plugin'; @@ -8,6 +9,25 @@ use File::HomeDir; use File::Spec; use Proc::InvokeEditor; +=head1 SYNOPSIS + + ; .replyrc + [Editor] + editor = emacs + +=head1 DESCRIPTION + +This plugin provides the C<#e> command. It will launch your editor, and allow +you to edit bits of code in your editor, which will then be evaluated all at +once. The text you entered will be saved, and restored the next time you enter +the command. Alternatively, you can pass a filename to the C<#e> command, and +the contents of that file will be preloaded instead. + +The C<editor> option can be specified to provide a different editor to use, +otherwise it will use the value of C<$ENV{VISUAL}> or C<$ENV{EDITOR}>. + +=cut + sub new { my $class = shift; my %opts = @_; diff --git a/lib/Reply/Plugin/FancyPrompt.pm b/lib/Reply/Plugin/FancyPrompt.pm index d998763..d0afc38 100644 --- a/lib/Reply/Plugin/FancyPrompt.pm +++ b/lib/Reply/Plugin/FancyPrompt.pm @@ -1,9 +1,23 @@ package Reply::Plugin::FancyPrompt; use strict; use warnings; +# ABSTRACT: provides a more informative prompt use base 'Reply::Plugin'; +=head1 SYNOPSIS + + ; .replyrc + [FancyPrompt] + +=head1 DESCRIPTION + +This plugin enhances the default Reply prompt. Currently, the only difference +is that it includes a counter of the number of lines evaluated so far in the +current session. + +=cut + sub new { my $class = shift; my $self = $class->SUPER::new(@_); diff --git a/lib/Reply/Plugin/Hints.pm b/lib/Reply/Plugin/Hints.pm index ac31ceb..d36d14a 100644 --- a/lib/Reply/Plugin/Hints.pm +++ b/lib/Reply/Plugin/Hints.pm @@ -11,9 +11,24 @@ BEGIN { use strict; use warnings; +# ABSTRACT: persists lexical hints across input lines use base 'Reply::Plugin'; +=head1 SYNOPSIS + + ; .replyrc + [Hints] + +=head1 DESCRIPTION + +This plugin persists the values of various compile time lexical hints between +evaluated lines. This means, for instance, that entering a line like C<use +strict> at the Reply prompt will cause C<strict> to be enabled for all future +lines (at least until C<no strict> is given). + +=cut + sub new { my $class = shift; diff --git a/lib/Reply/Plugin/Interrupt.pm b/lib/Reply/Plugin/Interrupt.pm index a5c2b37..1aab2b8 100644 --- a/lib/Reply/Plugin/Interrupt.pm +++ b/lib/Reply/Plugin/Interrupt.pm @@ -1,9 +1,22 @@ package Reply::Plugin::Interrupt; use strict; use warnings; +# ABSTRACT: allows using Ctrl+C to interrupt long-running lines use base 'Reply::Plugin'; +=head1 SYNOPSIS + + ; .replyrc + [Interrupt] + +=head1 DESCRIPTION + +This plugin allows you to use Ctrl+C to interrupt long running commands without +exiting the Reply shell entirely. + +=cut + sub compile { my $self = shift; my ($next, @args) = @_; diff --git a/lib/Reply/Plugin/LexicalPersistence.pm b/lib/Reply/Plugin/LexicalPersistence.pm index deb8d94..3b1f3f5 100644 --- a/lib/Reply/Plugin/LexicalPersistence.pm +++ b/lib/Reply/Plugin/LexicalPersistence.pm @@ -1,11 +1,25 @@ package Reply::Plugin::LexicalPersistence; use strict; use warnings; +# ABSTRACT: persists lexical variables between lines use base 'Reply::Plugin'; use Lexical::Persistence; +=head1 SYNOPSIS + + ; .replyrc + [LexicalPersistence] + +=head1 DESCRIPTION + +This plugin persists the values of lexical variables between input lines. For +instance, with this plugin you can enter C<my $x = 2> into the Reply shell, and +then use C<$x> as expected in subsequent lines. + +=cut + sub new { my $class = shift; my $self = $class->SUPER::new(@_); diff --git a/lib/Reply/Plugin/LoadClass.pm b/lib/Reply/Plugin/LoadClass.pm index 8bba634..a225cdd 100644 --- a/lib/Reply/Plugin/LoadClass.pm +++ b/lib/Reply/Plugin/LoadClass.pm @@ -1,12 +1,28 @@ package Reply::Plugin::LoadClass; use strict; use warnings; +# ABSTRACT: attempts to load classes implicitly if possible use base 'Reply::Plugin'; use Module::Runtime 'use_package_optimistically'; use Try::Tiny; +=head1 SYNOPSIS + + ; .replyrc + [LoadClass] + +=head1 DESCRIPTION + +If executing a line of code fails due to a method not being defined on a +package, this plugin will load the corresponding module and then try executing +the line again. This simplifies common cases like running C<< DateTime->now >> +at the prompt before loading L<DateTime> - this plugin will cause DateTime to +be loaded implicitly. + +=cut + sub execute { my $self = shift; my ($next, @args) = @_; diff --git a/lib/Reply/Plugin/Nopaste.pm b/lib/Reply/Plugin/Nopaste.pm index 1f64f85..085e478 100644 --- a/lib/Reply/Plugin/Nopaste.pm +++ b/lib/Reply/Plugin/Nopaste.pm @@ -1,13 +1,31 @@ package Reply::Plugin::Nopaste; use strict; use warnings; +# ABSTRACT: command to nopaste a transcript of the current session use base 'Reply::Plugin'; use App::Nopaste; -# XXX note that this has to be loaded early, in order to catch all of the -# appropriate manipulations that plugins do ([DataDump], etc) +=head1 SYNOPSIS + + ; .replyrc + [Nopaste] + service = Gist + +=head1 DESCRIPTION + +This plugin provides a C<#nopaste> command, which will use L<App::Nopaste> to +nopaste a transcript of the current Reply session. The C<service> option can be +used to choose an alternate service to use, rather than using the one that +App::Nopaste chooses on its own. If arguments are passed to the C<#nopaste> +command, they will be used as the title of the paste. + +Note that this plugin should be loaded early in your configuration file, in +order to ensure that it sees all modifications to the result (due to plugins +like [DataDump], etc). + +=cut sub new { my $class = shift; diff --git a/lib/Reply/Plugin/Packages.pm b/lib/Reply/Plugin/Packages.pm index fd48737..eb69f96 100644 --- a/lib/Reply/Plugin/Packages.pm +++ b/lib/Reply/Plugin/Packages.pm @@ -1,9 +1,25 @@ package Reply::Plugin::Packages; use strict; use warnings; +# ABSTRACT: persist the current package between lines use base 'Reply::Plugin'; +=head1 SYNOPSIS + + ; .replyrc + [Packages] + default_package = My::Scratchpad + +=head1 DESCRIPTION + +This plugin persists the state of the current package between lines. This +allows lines such as C<package Foo;> in the Reply shell to do what you'd +expect. The C<default_package> configuration option can also be used to set the +initial package to use when Reply starts up. + +=cut + sub new { my $class = shift; my %opts = @_; diff --git a/lib/Reply/Plugin/ReadLine.pm b/lib/Reply/Plugin/ReadLine.pm index 39126d1..6fcb0ad 100644 --- a/lib/Reply/Plugin/ReadLine.pm +++ b/lib/Reply/Plugin/ReadLine.pm @@ -1,6 +1,7 @@ package Reply::Plugin::ReadLine; use strict; use warnings; +# ABSTRACT: use Term::ReadLine for user input use base 'Reply::Plugin'; @@ -8,6 +9,28 @@ use File::HomeDir; use File::Spec; use Term::ReadLine; +=head1 SYNOPSIS + + ; .replyrc + [ReadLine] + history_file = '.hist' + history_length = 100 + +=head1 DESCRIPTION + +This plugin uses L<Term::ReadLine> to read lines from the user. This enables +useful features such as line editing and command history. The history will be +persisted between runs, by default in C<~/.reply_history>, although this is +changeable with the C<history_file> option. To limit the number of lines +written to this file, you can use the C<history_length> option. Setting a +C<history_length> of C<0> will disable writing history to a file entirely. + +NOTE: you probably want to install a reasonable L<Term::ReadLine> backend in +order for this plugin to be very useful. L<Term::ReadLine::Gnu> is highly +recommended if possible. + +=cut + sub new { my $class = shift; my %opts = @_; diff --git a/lib/Reply/Plugin/ResultCache.pm b/lib/Reply/Plugin/ResultCache.pm index fc260f5..a973d05 100644 --- a/lib/Reply/Plugin/ResultCache.pm +++ b/lib/Reply/Plugin/ResultCache.pm @@ -1,9 +1,26 @@ package Reply::Plugin::ResultCache; use strict; use warnings; +# ABSTRACT: retain previous results to be able to refer to them later use base 'Reply::Plugin'; +=head1 SYNOPSIS + + ; .replyrc + [ResultCache] + variable = r + +=head1 DESCRIPTION + +This plugin caches the results of successful evaluations, and provides them in +a lexical array (by default C<@res>, although this can be changed via the +C<variable> option). This means that you can, for instance, access the value +returned by the previous line with C<$res[-1]>. It also modifies the output to +include an indication of where the value is stored, for later reference. + +=cut + sub new { my $class = shift; my %opts = @_; |