spirit_hands 2.0.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.
Files changed (44) hide show
  1. checksums.yaml +7 -0
  2. checksums.yaml.gz.sig +0 -0
  3. data/.gitignore +17 -0
  4. data/.hound.yml +20 -0
  5. data/.pryrc +2 -0
  6. data/.rubocop.yml +20 -0
  7. data/.ruby-gemset +1 -0
  8. data/CHANGELOG.md +147 -0
  9. data/CONTRIBUTING.md +18 -0
  10. data/CONTRIBUTORS.md +10 -0
  11. data/Gemfile +3 -0
  12. data/LICENSE.md +22 -0
  13. data/README.md +133 -0
  14. data/Rakefile +3 -0
  15. data/gem-public_cert.pem +32 -0
  16. data/lib/spirit_hands/hirb/fixes/enabled.rb +38 -0
  17. data/lib/spirit_hands/hirb/fixes/pager.rb +144 -0
  18. data/lib/spirit_hands/hirb/fixes/util.rb +23 -0
  19. data/lib/spirit_hands/hirb/fixes/view.rb +10 -0
  20. data/lib/spirit_hands/hirb/fixes.rb +5 -0
  21. data/lib/spirit_hands/hirb.rb +2 -0
  22. data/lib/spirit_hands/load_plugins.rb +10 -0
  23. data/lib/spirit_hands/mattr_accessor_with_default.rb +48 -0
  24. data/lib/spirit_hands/melody.rb +41 -0
  25. data/lib/spirit_hands/options/color.rb +12 -0
  26. data/lib/spirit_hands/options/hirb.rb +34 -0
  27. data/lib/spirit_hands/options/less/colorize.rb +42 -0
  28. data/lib/spirit_hands/options/less/show_raw_unicode.rb +38 -0
  29. data/lib/spirit_hands/options/less.rb +2 -0
  30. data/lib/spirit_hands/options.rb +57 -0
  31. data/lib/spirit_hands/plugin.rb +28 -0
  32. data/lib/spirit_hands/print.rb +72 -0
  33. data/lib/spirit_hands/prompt/base.rb +249 -0
  34. data/lib/spirit_hands/prompt/main.rb +18 -0
  35. data/lib/spirit_hands/prompt/multiline.rb +17 -0
  36. data/lib/spirit_hands/prompt.rb +13 -0
  37. data/lib/spirit_hands/railtie.rb +7 -0
  38. data/lib/spirit_hands/terminal.rb +14 -0
  39. data/lib/spirit_hands/version.rb +3 -0
  40. data/lib/spirit_hands.rb +13 -0
  41. data/spirit_hands.gemspec +37 -0
  42. data.tar.gz.sig +0 -0
  43. metadata +258 -0
  44. metadata.gz.sig +0 -0
@@ -0,0 +1,10 @@
1
+ require 'spirit_hands/plugin'
2
+
3
+ # awesome_print is autoloaded by Hirb::View patch and/or SpiritHands::Print
4
+ # pry was loaded earlier
5
+ SpiritHands.plugin 'pry-coolline'
6
+ SpiritHands.plugin 'pry-doc'
7
+ SpiritHands.plugin 'pry-git'
8
+ # pry-rails was loaded earlier (if needed)
9
+ SpiritHands.plugin 'pry-remote'
10
+ # hirb is autoloaded by SpiritHands.hirb = true
@@ -0,0 +1,48 @@
1
+ class Module
2
+ def mattr_accessor_with_default(property, default = nil, &block)
3
+ if block_given?
4
+ if default
5
+ raise ArgumentError, 'Must specify only one of +default+ or &block'
6
+ end
7
+ default = block
8
+ end
9
+
10
+ getter = property.to_sym
11
+ setter = "#{property}=".to_sym
12
+ class_var = "@@#{property}".to_sym
13
+
14
+ # self.property=
15
+ define_singleton_method(setter) do |value|
16
+ if value.nil?
17
+ remove_class_variable(class_var)
18
+ else
19
+ class_variable_set(class_var, value)
20
+ end
21
+ end
22
+
23
+ # self.property
24
+ if default.respond_to?(:call) # default is callable
25
+ define_singleton_method(getter) do
26
+ if class_variable_defined?(class_var)
27
+ class_variable_get(class_var)
28
+ else
29
+ default.()
30
+ end
31
+ end
32
+ else # default is literal object
33
+ default_value_name = "DEFAULT_#{property}".upcase.to_sym
34
+ const_set(default_value_name, default)
35
+ define_singleton_method(getter) do
36
+ if class_variable_defined?(class_var)
37
+ class_variable_get(class_var)
38
+ else
39
+ const_get(default_value_name)
40
+ end
41
+ end
42
+ end
43
+ end
44
+
45
+ private
46
+
47
+ NO_OP = -> { }.freeze
48
+ end
@@ -0,0 +1,41 @@
1
+ require 'pry'
2
+
3
+ # We're managing the loading of plugins. So don't let pry autoload them.
4
+ ::Pry.config.should_load_plugins = false
5
+
6
+ if defined? ::Rails
7
+ STDERR.puts 'JF pry-rails' if ENV['SPIRIT_FINGERS_PLUGIN_DEBUG']
8
+ require 'pry-rails'
9
+ end
10
+
11
+ module SpiritHands
12
+ autoload :Print, 'spirit_hands/print'
13
+ autoload :Prompt, 'spirit_hands/prompt'
14
+
15
+ class << self
16
+ @installed = false
17
+ # This modifies pry to play our tune
18
+ def melody!(app = nil)
19
+ return false if @installed
20
+
21
+ # Require all of our pry plugins
22
+ require 'spirit_hands/load_plugins'
23
+
24
+ setup_less_colorize
25
+ setup_less_show_raw_unicode
26
+ setup_hirb
27
+
28
+ # Use awesome_print for output, but keep pry's pager. If Hirb is
29
+ # enabled, try printing with it first.
30
+ ::SpiritHands::Print.install!
31
+
32
+ # Friendlier prompt - line number, app name, nesting levels look like
33
+ # directory paths.
34
+ #
35
+ # Configuration (like Pry.color) can be changed later or even during console usage.
36
+ ::SpiritHands::Prompt.install!(app)
37
+
38
+ @installed = true
39
+ end
40
+ end
41
+ end
@@ -0,0 +1,12 @@
1
+ module SpiritHands
2
+ class << self
3
+ # Alias for Pry.color
4
+ def color
5
+ ::Pry.color
6
+ end
7
+
8
+ def color=(v)
9
+ ::Pry.color = v
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,34 @@
1
+ autoload :Hirb, 'spirit_hands/hirb'
2
+
3
+ module SpiritHands
4
+ class << self
5
+ # Is hirb enabled?
6
+ def hirb
7
+ ::Hirb.enabled?
8
+ end
9
+
10
+ # Set whether hirb is enabled (default: true)
11
+ def hirb=(h)
12
+ h = DEFAULT_HIRB if h.nil?
13
+ if hirb != h
14
+ if h
15
+ ::Hirb.enable
16
+ else
17
+ ::Hirb.disable
18
+ end
19
+ end
20
+ @hirb = !!h
21
+ end
22
+
23
+ private
24
+
25
+ def setup_hirb
26
+ self.hirb = nil unless @hirb
27
+ end
28
+ end
29
+
30
+ DEFAULT_HIRB = true
31
+
32
+ # Whether to use hirb/unicode when hirb is enabled (default: true)
33
+ mattr_accessor_with_default :hirb_unicode, true
34
+ end
@@ -0,0 +1,42 @@
1
+ require 'shellwords'
2
+
3
+ module SpiritHands
4
+ class << self
5
+ # Allow less to display colorized output (default: true)
6
+ # (If, set updates LESS env var)
7
+ def less_colorize
8
+ ENV['LESS'].to_s.shellsplit.any? { |arg| arg == LESS_R_LONG || arg =~ LESS_R }
9
+ end
10
+
11
+ # true: add -R to LESS env var (default)
12
+ # false: remove -R from LESS env var
13
+ # nil: set to default (true)
14
+ def less_colorize=(n)
15
+ n = DEFAULT_LESS_COLORIZE if n.nil?
16
+
17
+ args = ENV['LESS'].to_s.shellsplit.map do |arg|
18
+ next if arg == LESS_R_LONG
19
+ if arg =~ LESS_R
20
+ arg = $1 + $2
21
+ end
22
+ arg unless arg.empty?
23
+ end
24
+ args << '-R' if n
25
+ new_less = args.collect.to_a.shelljoin
26
+ ENV['LESS'] = new_less.empty? ? nil : new_less
27
+ @less_colorize = !!n
28
+ end
29
+
30
+ private
31
+
32
+ def setup_less_colorize
33
+ self.less_colorize = nil unless @less_colorize
34
+ end
35
+ end
36
+
37
+ private
38
+
39
+ DEFAULT_LESS_COLORIZE = true
40
+ LESS_R_LONG = '--RAW-CONTROL-CHARS'.freeze
41
+ LESS_R = /\A(.*-[^-R]*)R(.*)\z/.freeze
42
+ end
@@ -0,0 +1,38 @@
1
+ require 'shellwords'
2
+
3
+ module SpiritHands
4
+ class << self
5
+ # Allow less to display colorized output (default: true)
6
+ # (If, set updates LESS env var)
7
+ def less_show_raw_unicode
8
+ ENV['LESSUTFBINFMT'] == LESS_SHOW_RAW_BINFMT
9
+ end
10
+
11
+ # true: set LESSUTFBINFMT to %*c
12
+ # false: unset LESSUTFBINFMT
13
+ # String: set custom LESSUTFBINFMT
14
+ # nil: set default(true)
15
+ def less_show_raw_unicode=(n)
16
+ n = DEFAULT_LESS_SHOW_RAW_UNICODE if n.nil?
17
+ ENV['LESSUTFBINFMT'] = if n.is_a?(String)
18
+ n
19
+ elsif n
20
+ LESS_SHOW_RAW_BINFMT
21
+ else
22
+ nil
23
+ end
24
+ @less_show_raw_unicode = !!n
25
+ end
26
+
27
+ private
28
+
29
+ def setup_less_show_raw_unicode
30
+ self.less_show_raw_unicode = nil unless @less_show_raw_unicode
31
+ end
32
+ end
33
+
34
+ private
35
+
36
+ DEFAULT_LESS_SHOW_RAW_UNICODE = true
37
+ LESS_SHOW_RAW_BINFMT = '*n%c'.freeze
38
+ end
@@ -0,0 +1,2 @@
1
+ require 'spirit_hands/options/less/colorize'
2
+ require 'spirit_hands/options/less/show_raw_unicode'
@@ -0,0 +1,57 @@
1
+ # encoding: UTF-8
2
+ require 'readline'
3
+ require 'spirit_hands/mattr_accessor_with_default'
4
+ require 'spirit_hands/options/color'
5
+ require 'spirit_hands/options/less'
6
+ require 'spirit_hands/options/hirb'
7
+
8
+ module SpiritHands
9
+ autoload :Terminal, 'spirit_hands/terminal'
10
+
11
+ ### Options ###
12
+
13
+ # When printing values, start with this (default: '=> ')
14
+ mattr_accessor_with_default :value_prompt, '=> '
15
+
16
+ # Spaces to indent value (default: 2 spaces)
17
+ mattr_accessor_with_default :value_indent, 2
18
+
19
+ # Name of the app, which can be displayed to <app/> tag in prompt
20
+ mattr_accessor_with_default :app, -> {
21
+ # Trumpet emoji or pry
22
+ (Terminal.unicode?) ? "\u{1F3BA}" : 'pry'
23
+ }
24
+
25
+ # <color>...</color>
26
+ # <bold>...</color>
27
+ # <cmd/> command number
28
+ # <app/> SpiritHands.app, which can be String or a Rails Applicatino object
29
+ # <sep/> SpiritHands.prompt_separator
30
+ #
31
+ # Use \ to escape literal <, so in a Ruby string constant, "\\<"
32
+ #
33
+ mattr_accessor_with_default :prompt,
34
+ '<b>[<cmd/>]</b> <blue><app/></blue><tgt/> <red><sep/></red> '
35
+
36
+ # Color the prompt?
37
+ #
38
+ # A different setting than Pry.color since some may like colored output, but a
39
+ # plain prompt.
40
+ #
41
+ # Default: 'true' for GNU readline or rb-readline which correctly count line
42
+ # widths with color codes when using \001 and \002 hints. 'false' for
43
+ # libedit-based wrapper (standard on OS X unless ruby is explicitly compiled
44
+ # otherwise).
45
+ mattr_accessor_with_default :colored_prompt, -> { ::Readline::VERSION !~ /EditLine/ }
46
+
47
+ # Separator between application name and input in the prompt.
48
+ #
49
+ # Default: right angle quote (chevron) or >
50
+ #
51
+ mattr_accessor_with_default :prompt_separator, -> {
52
+ (Terminal.unicode?) ? "\u{BB}" : '>'
53
+ }
54
+
55
+ # Enable or disable AwesomePrint (default: true)
56
+ mattr_accessor_with_default :awesome_print, true
57
+ end
@@ -0,0 +1,28 @@
1
+ module SpiritHands
2
+ class << self
3
+ # A thin wrapper around require for troubleshooting
4
+ def plugin(*requires)
5
+ cond = requires.pop if requires.last.respond_to? :call
6
+ requires.each do |r|
7
+ begin
8
+ if cond && !cond.()
9
+ plugin_debug "JF require #{r} (skipped)"
10
+ next
11
+ end
12
+ res = require r
13
+ rescue LoadError
14
+ plugin_debug "JF require #{r} FAILED"
15
+ else
16
+ plugin_debug "JF require #{r} -> #{res}"
17
+ end
18
+ end
19
+ end
20
+
21
+ private
22
+
23
+ def plugin_debug(*args)
24
+ return if !ENV['SPIRIT_FINGERS_PLUGIN_DEBUG']
25
+ STDERR.puts(*args)
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,72 @@
1
+ module SpiritHands
2
+ module Print
3
+ class << self
4
+ def install!
5
+ ::Pry.config.print = PRINT_FUNCTION
6
+ end
7
+
8
+ def pretty(value)
9
+ if ::SpiritHands.awesome_print
10
+ require 'awesome_print' unless defined?(AwesomePrint)
11
+ opts = { :indent => ::SpiritHands.value_indent }
12
+ opts[:plain] = true if !SpiritHands.color
13
+ value.ai(opts)
14
+ else
15
+ value.inspect
16
+ end
17
+ end
18
+
19
+ def hirb_unicode_enabled?
20
+ ::Hirb::Formatter.dynamic_config.keys.any? do |key|
21
+ if opts = ::Hirb::Formatter.dynamic_config[key][:options]
22
+ opts && opts[:unicode]
23
+ end
24
+ end
25
+ end
26
+
27
+ def print(_output, value, _pry_)
28
+ if ::Hirb.enabled?
29
+ setup_hirb_unicode
30
+ return if ::Hirb::View.view_or_page_output(value)
31
+ end
32
+ _pry_.pager.page("#{::SpiritHands.value_prompt}#{pretty(value)}")
33
+ end
34
+
35
+ private
36
+
37
+ PRINT_FUNCTION = ->(_output, value, _pry_) do
38
+ ::SpiritHands::Print.print(_output, value, _pry_)
39
+ end
40
+
41
+ def hirb_unicode_enable
42
+ return false unless ::SpiritHands::Terminal.unicode?
43
+ require 'hirb/unicode'
44
+
45
+ ::Hirb::Formatter.dynamic_config.keys.each do |key|
46
+ ::Hirb::Formatter.dynamic_config[key][:options] ||= {}
47
+ ::Hirb::Formatter.dynamic_config[key][:options][:unicode] = true
48
+ end
49
+ true
50
+ end
51
+
52
+ def hirb_unicode_disable
53
+ ::Hirb::Formatter.dynamic_config.keys.each do |key|
54
+ ::Hirb::Formatter.dynamic_config[key][:options] ||= {}
55
+ ::Hirb::Formatter.dynamic_config[key][:options][:unicode] = false
56
+ end
57
+ false
58
+ end
59
+
60
+ def setup_hirb_unicode
61
+ if hirb_unicode_enabled? != SpiritHands.hirb_unicode
62
+ if SpiritHands.hirb_unicode
63
+ hirb_unicode_enable
64
+ else
65
+ hirb_unicode_disable
66
+ end
67
+ end
68
+ nil
69
+ end
70
+ end
71
+ end
72
+ end
@@ -0,0 +1,249 @@
1
+ module SpiritHands
2
+ module Prompt
3
+ class << self
4
+ private
5
+
6
+ def render(state, prompt, color = true)
7
+ r = Render.new(state, prompt, color)
8
+ res = r.to_s
9
+ STDERR.puts "\n" + (r.errors * "\n") + "\n" if r.errors?
10
+ res
11
+ end
12
+ end
13
+
14
+ # :object Object
15
+ # :level Fixnum
16
+ # :pry Pry
17
+ # :app String or Rails::Application
18
+ # :multiline false: normal prompt, true: multiline prompt
19
+ State = Struct.new(:object, :level, :pry, :app, :multiline)
20
+
21
+ # <....>
22
+ # <..../>
23
+ # </....>
24
+ #
25
+ class Render
26
+ # <tag> ... </tag>, tag -> inner part of escape codes
27
+ MATCHED_TAG_CODES = {
28
+ 'b' => 1,
29
+ 'bold' => 1,
30
+ 'bright' => 1,
31
+ 'strong' => 1,
32
+
33
+ 'dark' => 2,
34
+ 'faint' => 2,
35
+
36
+ 'i' => 3,
37
+ 'italic' => 3,
38
+ 'em' => 3,
39
+
40
+ 'u' => 4,
41
+ 'underline' => 4,
42
+
43
+ 'blink' => 5, # evil
44
+ 'flash' => 5,
45
+
46
+ 'rapid-blink' => 6, # sinister
47
+ 'rapid-flash' => 6,
48
+
49
+ 'reverse' => 7,
50
+ 'negative' => 7,
51
+ 'inverse' => 7,
52
+
53
+ 'concealed' => 8,
54
+
55
+ 'strike' => 9,
56
+ 'strikethrough' => 9,
57
+
58
+ 'black' => 30,
59
+ 'red' => 31,
60
+ 'green' => 32,
61
+ 'yellow' => 33,
62
+ 'blue' => 34,
63
+ 'magenta' => 35,
64
+ 'cyan' => 36,
65
+ 'white' => 37,
66
+
67
+ 'bgblack' => 40,
68
+ 'bgred' => 41,
69
+ 'bggreen' => 42,
70
+ 'bgyellow' => 43,
71
+ 'bgblue' => 44,
72
+ 'bgmagenta' => 45,
73
+ 'bgcyan' => 46,
74
+ 'bgwhite' => 47,
75
+ }
76
+
77
+ # <.../>
78
+ SINGLE_TAGS = {
79
+ # <cmd/>: command number
80
+ 'cmd' => ->(state) { state.pry.input_array.size },
81
+
82
+ # <tgt/>: target string
83
+ 'tgt' => ->(state) {
84
+ unless (str = Pry.view_clip(state.object)) == 'main'
85
+ state.level = 0 if state.level < 0
86
+ "(#{'../' * state.level}#{str})"
87
+ else
88
+ ''
89
+ end
90
+ },
91
+
92
+ # <app/>: state.app (Object) converted to String
93
+ 'app' => ->(state) {
94
+ app = state.app
95
+ if app.class.respond_to?(:parent_name) && \
96
+ app.class.parent_name.respond_to?(:underscore)
97
+ app.class.parent_name.underscore
98
+ elsif app
99
+ app.to_s
100
+ else
101
+ ::SpiritHands.app
102
+ end
103
+ },
104
+
105
+ # <sep/>: SpiritHands.prompt_separator
106
+ 'sep' => ->(_state) {
107
+ ::SpiritHands.prompt_separator
108
+ }
109
+ }
110
+
111
+ # Array<String>
112
+ attr_reader :errors
113
+
114
+ def errors?
115
+ errors.any?
116
+ end
117
+
118
+ # :state SpiritHands::Prompt::State
119
+ # :prompt String
120
+ # :color true or false/nil
121
+ def initialize(state, prompt, color)
122
+ @state = state
123
+ @prompt = prompt
124
+ @color = color
125
+ end
126
+
127
+ def to_s
128
+ @errors = []
129
+ @tag_stack = []
130
+ @result = ''
131
+ @color_applied = false
132
+ @in_tag = false
133
+
134
+ @prompt.each_char do |c|
135
+ if @in_tag
136
+ tag_char(c)
137
+ else
138
+ nontag_char(c)
139
+ end
140
+ end
141
+
142
+ # @tag_stack.any? --> error/s
143
+ @tag_stack.each { |t| errors << "<#{t}>: Missing </#{t}>" }
144
+
145
+ (errors?) ? '' : @result
146
+ end
147
+
148
+ private
149
+
150
+ def tag_char(c)
151
+ case c
152
+ when '/'
153
+ # close: </
154
+ # single <.+/
155
+ @tag_type = (@tag.blank?) ? :close : :single
156
+ when '>' # close tag
157
+ @tag.downcase!
158
+ send @tag_type # :start, :close or :single
159
+ @in_tag = false
160
+ else # append to existing tag
161
+ @tag += c
162
+ end
163
+ end
164
+
165
+ def nontag_char(c)
166
+ if @escape
167
+ nontag_escaped_char(c)
168
+ else
169
+ nontag_unescaped_char(c)
170
+ end
171
+ end
172
+
173
+ def nontag_escaped_char(c)
174
+ @escape = false
175
+ @result += (@state.multiline) ? ' ' : c
176
+ end
177
+
178
+ def nontag_unescaped_char(c)
179
+ case c
180
+ when '\\' # escape next char
181
+ @escape = true
182
+ when '<' # start tag
183
+ @in_tag = true
184
+ @tag_type = :start
185
+ @tag = ''
186
+ else # normal char
187
+ @result += (@state.multiline) ? ' ' : c
188
+ end
189
+ end
190
+
191
+ # <...>
192
+ def start
193
+ code = MATCHED_TAG_CODES[@tag]
194
+ if !code
195
+ errors << "Unknown <#{@tag}>"
196
+ return
197
+ end
198
+ @result += esc(code)
199
+ @tag_stack << @tag
200
+ end
201
+
202
+ # </...>
203
+ def close
204
+ code = MATCHED_TAG_CODES[@tag]
205
+ if !code
206
+ errors << "Unknown </#{@tag}>"
207
+ return
208
+ end
209
+ idx = @tag_stack.rindex @tag
210
+ if idx.nil?
211
+ errors << "</#{@tag}>: missing start <#{@tag}>"
212
+ return
213
+ end
214
+ # remove the now closed tag from the stack
215
+ @tag_stack.delete_at idx
216
+ # reset and reapply all codes on the @tag_stack
217
+ @result += reset
218
+ @tag_stack.each { |tag| @result += esc(MATCHED_TAG_CODES[tag]) }
219
+ end
220
+
221
+ # <.../>
222
+ def single
223
+ f = SINGLE_TAGS[@tag]
224
+ if !f
225
+ errors << "Unknown </#{@tag}>"
226
+ return
227
+ end
228
+ result = f.(@state).to_s
229
+
230
+ # blank out all but sep for multiline prompt, vs. main (normal)
231
+ if @state.multiline && @tag != 'sep'
232
+ result = ' ' * result.length
233
+ end
234
+ @result += result
235
+ end
236
+
237
+ def reset
238
+ esc(0)
239
+ end
240
+
241
+ # convert a code to an actual character
242
+ def esc(code)
243
+ return '' if !@color
244
+ @color_applied = true
245
+ "\001\e[#{code}m\002".freeze
246
+ end
247
+ end
248
+ end
249
+ end
@@ -0,0 +1,18 @@
1
+ require 'spirit_hands/prompt/base'
2
+
3
+ module SpiritHands
4
+ module Prompt
5
+ class << self
6
+ private
7
+
8
+ # Normal, main pry prompt
9
+ def main
10
+ ->(object, level, pry) do
11
+ s = State.new(object, level, pry, ::SpiritHands.app, false)
12
+ color = ::SpiritHands.color && ::SpiritHands.colored_prompt
13
+ render(s, ::SpiritHands.prompt, color)
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,17 @@
1
+ require 'spirit_hands/prompt/base'
2
+
3
+ module SpiritHands
4
+ module Prompt
5
+ class << self
6
+ private
7
+
8
+ # Wait pry prompt in multiline input
9
+ def multiline
10
+ ->(object, level, pry) {
11
+ s = State.new(object, level, pry, ::SpiritHands.app, true)
12
+ render(s, ::SpiritHands.prompt, ::SpiritHands.color && ::SpiritHands.colored_prompt)
13
+ }
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,13 @@
1
+ require 'spirit_hands/prompt/main'
2
+ require 'spirit_hands/prompt/multiline'
3
+
4
+ module SpiritHands
5
+ module Prompt
6
+ class << self
7
+ def install!(app = nil)
8
+ ::SpiritHands.app ||= app
9
+ ::Pry.config.prompt = [ main, multiline ].freeze
10
+ end
11
+ end
12
+ end
13
+ end