rcodetools 0.7.0.0 → 0.8.0.0
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGES +12 -0
- data/README +1 -1
- data/README.emacs +21 -4
- data/README.ja +1 -1
- data/README.xmpfilter +159 -74
- data/Rakefile +3 -37
- data/anything-rcodetools.el +142 -0
- data/bin/rct-complete +1 -1
- data/bin/rct-doc +1 -1
- data/bin/rct-meth-args +33 -2
- data/bin/xmpfilter +5 -1
- data/lib/rcodetools/compat.rb +14 -0
- data/lib/rcodetools/completion.rb +8 -6
- data/lib/rcodetools/fork.rb +15 -8
- data/lib/rcodetools/options.rb +8 -0
- data/lib/rcodetools/xmpfilter.rb +80 -33
- data/lib/rcodetools/xmptestunitfilter.rb +76 -21
- data/lib/ruby_toggle_file.rb +1 -1
- data/rcodetools.el +213 -20
- data/test/test_functional.rb +36 -68
- data/test/test_method_analyzer.rb +28 -20
- data/test/test_ruby_toggle_file.rb +118 -69
- data/test/test_xmpfilter.rb +75 -47
- data/test/test_xmptestunitfilter.rb +12 -11
- metadata +83 -133
- data/test/data/add_markers-input.rb +0 -2
- data/test/data/add_markers-output.rb +0 -2
- data/test/data/bindings-input.rb +0 -26
- data/test/data/bindings-output.rb +0 -31
- data/test/data/completion-input.rb +0 -1
- data/test/data/completion-output.rb +0 -2
- data/test/data/completion_class_info-input.rb +0 -1
- data/test/data/completion_class_info-output.rb +0 -10
- data/test/data/completion_class_info_no_candidates-input.rb +0 -1
- data/test/data/completion_class_info_no_candidates-output.rb +0 -1
- data/test/data/completion_detect_rbtest-input.rb +0 -7
- data/test/data/completion_detect_rbtest-output.rb +0 -2
- data/test/data/completion_detect_rbtest2-input.rb +0 -1
- data/test/data/completion_detect_rbtest2-output.rb +0 -2
- data/test/data/completion_emacs-input.rb +0 -1
- data/test/data/completion_emacs-output.rb +0 -6
- data/test/data/completion_emacs_icicles-input.rb +0 -1
- data/test/data/completion_emacs_icicles-output.rb +0 -6
- data/test/data/completion_in_method-input.rb +0 -3
- data/test/data/completion_in_method-output.rb +0 -1
- data/test/data/completion_in_method-test.rb +0 -6
- data/test/data/completion_rbtest-input.rb +0 -7
- data/test/data/completion_rbtest-output.rb +0 -2
- data/test/data/doc-input.rb +0 -1
- data/test/data/doc-output.rb +0 -1
- data/test/data/doc_detect_rbtest-input.rb +0 -1
- data/test/data/doc_detect_rbtest-output.rb +0 -1
- data/test/data/doc_detect_rbtest2-input.rb +0 -7
- data/test/data/doc_detect_rbtest2-output.rb +0 -1
- data/test/data/doc_rbtest-input.rb +0 -7
- data/test/data/doc_rbtest-output.rb +0 -1
- data/test/data/no_warnings-input.rb +0 -3
- data/test/data/no_warnings-output.rb +0 -4
- data/test/data/refe-input.rb +0 -1
- data/test/data/refe-output.rb +0 -1
- data/test/data/ri-input.rb +0 -1
- data/test/data/ri-output.rb +0 -1
- data/test/data/ri_emacs-input.rb +0 -1
- data/test/data/ri_emacs-output.rb +0 -1
- data/test/data/ri_vim-input.rb +0 -1
- data/test/data/ri_vim-output.rb +0 -1
- data/test/data/rspec-input.rb +0 -48
- data/test/data/rspec-output.rb +0 -52
- data/test/data/rspec_poetry-input.rb +0 -48
- data/test/data/rspec_poetry-output.rb +0 -52
- data/test/data/simple_annotation-input.rb +0 -8
- data/test/data/simple_annotation-output.rb +0 -8
- data/test/data/unit_test-input.rb +0 -50
- data/test/data/unit_test-output.rb +0 -52
- data/test/data/unit_test_detect_rbtest-input.rb +0 -50
- data/test/data/unit_test_detect_rbtest-output.rb +0 -52
- data/test/data/unit_test_detect_rbtest2-input.rb +0 -6
- data/test/data/unit_test_detect_rbtest2-output.rb +0 -6
- data/test/data/unit_test_poetry-input.rb +0 -50
- data/test/data/unit_test_poetry-output.rb +0 -52
- data/test/data/unit_test_rbtest-input.rb +0 -6
- data/test/data/unit_test_rbtest-output.rb +0 -6
- data/test/test_run.rb +0 -45
data/bin/rct-complete
CHANGED
data/bin/rct-doc
CHANGED
data/bin/rct-meth-args
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
#! /home/
|
1
|
+
#! /home/mfp/ruby1.8/bin/ruby
|
2
2
|
# Copyright (c)
|
3
3
|
# 2006-2007 Mauricio Fernandez <mfp@acm.org> http://eigenclass.org
|
4
4
|
# 2006-2007 rubikitch <rubikitch@ruby-lang.org> http://www.rubyist.net/~rubikitch/
|
@@ -6,6 +6,7 @@
|
|
6
6
|
# Use and distribution subject to the same conditions as Ruby.
|
7
7
|
|
8
8
|
require 'rcodetools/options'
|
9
|
+
include Rcodetools
|
9
10
|
$VERBOSE = nil
|
10
11
|
$__method_args_off = true
|
11
12
|
|
@@ -22,6 +23,7 @@ rct-meth-args [-Idirectory] [-i] [-m] [-c] [-n] <file> [<file> ...]
|
|
22
23
|
|
23
24
|
-n print the filename and line number with output lines
|
24
25
|
-t generate TAGS output
|
26
|
+
--summarize summary output sorted by method name
|
25
27
|
|
26
28
|
The given files will be #require()d in order.
|
27
29
|
Examples:
|
@@ -29,7 +31,7 @@ Examples:
|
|
29
31
|
rct-meth-args thread
|
30
32
|
rct-meth-args -c rubygems
|
31
33
|
EOF
|
32
|
-
exit
|
34
|
+
exit # '
|
33
35
|
end
|
34
36
|
|
35
37
|
def debugprint(*args)
|
@@ -98,6 +100,33 @@ module MethodArgs
|
|
98
100
|
end
|
99
101
|
end
|
100
102
|
|
103
|
+
class SummarizePrinter
|
104
|
+
def initialize
|
105
|
+
@hash = Hash.new
|
106
|
+
at_exit { print_result }
|
107
|
+
end
|
108
|
+
|
109
|
+
def method_info(io, x)
|
110
|
+
@io = io
|
111
|
+
prefix = x[:location] ? "#{x[:location].filename}:#{x[:location].lineno}:" : ""
|
112
|
+
(@hash[x[:meth]]||=[]) << "#{prefix}#{x[:fullname]}#{x[:arg_desc]}" unless x[:klass].to_s == "<Struct>"
|
113
|
+
end
|
114
|
+
|
115
|
+
def included_location(io, x)
|
116
|
+
# not implemented
|
117
|
+
end
|
118
|
+
|
119
|
+
def print_result
|
120
|
+
@hash.keys.sort.each do |meth|
|
121
|
+
@io.puts meth
|
122
|
+
@hash[meth].each do |line|
|
123
|
+
@io.puts line
|
124
|
+
end
|
125
|
+
@io.puts
|
126
|
+
end
|
127
|
+
end
|
128
|
+
end
|
129
|
+
|
101
130
|
class TagsPrinter
|
102
131
|
def initialize
|
103
132
|
@previous_filename = ""
|
@@ -129,6 +158,7 @@ module MethodArgs
|
|
129
158
|
arg_desc = " " + arg_desc unless arg_desc.empty?
|
130
159
|
flag = is_singleton ? "." : "#"
|
131
160
|
x = { :arg_desc => arg_desc, :klass => klass,
|
161
|
+
:meth => meth.to_s,
|
132
162
|
:fullname => [klass, flag, meth].join,
|
133
163
|
:location => with_location && location,
|
134
164
|
}
|
@@ -255,6 +285,7 @@ ARGV.each do |arg|
|
|
255
285
|
case arg
|
256
286
|
when "-n"; $__with_location = true
|
257
287
|
when "-t"; $__printer = TagsPrinter.new; $__with_location = true
|
288
|
+
when "--summarize"; $__printer = SummarizePrinter.new
|
258
289
|
when /-I(.+)$/; $:.unshift $1
|
259
290
|
when "-I"; i_opt_p = true
|
260
291
|
when "--dev"; OptionHandler.auto_include_paths($:, Dir.pwd)
|
data/bin/xmpfilter
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
#! /home/
|
1
|
+
#! /home/mfp/ruby1.8/bin/ruby
|
2
2
|
require 'rcodetools/xmpfilter'
|
3
3
|
require 'rcodetools/options'
|
4
4
|
|
@@ -25,6 +25,10 @@ opts = OptionParser.new do |opts|
|
|
25
25
|
klass = XMPRSpecFilter
|
26
26
|
options[:interpreter] = "spec"
|
27
27
|
end
|
28
|
+
opts.on("--expectations", "Complete expectations expectations.") do
|
29
|
+
require 'rcodetools/xmptestunitfilter'
|
30
|
+
klass = XMPExpectationsFilter
|
31
|
+
end
|
28
32
|
opts.on("-m", "--markers", "Add # => markers.") do
|
29
33
|
klass = XMPAddMarkers
|
30
34
|
end
|
@@ -81,8 +81,8 @@ module ProcessParticularLine
|
|
81
81
|
def aref_or_aset?(right_stripped, last_char)
|
82
82
|
if last_char == ?[
|
83
83
|
case right_stripped
|
84
|
-
when /\]\s
|
85
|
-
when /\]
|
84
|
+
when /\]\s*=/ then "[]="
|
85
|
+
when /\]/ then "[]"
|
86
86
|
end
|
87
87
|
end
|
88
88
|
end
|
@@ -182,7 +182,7 @@ XXX
|
|
182
182
|
code = <<-EOC
|
183
183
|
#{result} = #{v}.method(#{meth}).inspect.match( %r[\\A#<(?:Unbound)?Method: (.*?)>\\Z] )[1].sub(/\\A.*?\\((.*?)\\)(.*)\\Z/){ "\#{$1}\#{$2}" }.sub(/#<Class:(.*?)>#/) { "\#{$1}." }
|
184
184
|
#{result} = #{v}.to_s + ".new" if #{result} == 'Class#new' and #{v}.private_method_defined?(:initialize)
|
185
|
-
#{result} = "Object#" + #{meth} if #{result} =~ /^Kernel#/ and Kernel.instance_methods(false).include? #{meth}
|
185
|
+
#{result} = "Object#" + #{meth} if #{result} =~ /^Kernel#/ and Kernel.instance_methods(false).map{|x| x.to_s}.include? #{meth}
|
186
186
|
#{result}
|
187
187
|
EOC
|
188
188
|
end
|
@@ -212,7 +212,9 @@ class XMPCompletionFilter < XMPFilter
|
|
212
212
|
|
213
213
|
def methods_map_code(recv)
|
214
214
|
# delimiter is \0
|
215
|
-
|
215
|
+
m = "#{VAR}_m"
|
216
|
+
mhc = magic_help_code((recv), m)
|
217
|
+
%Q[map{|%s| "\#{%s}\\0" + %s}] % [m, m, mhc]
|
216
218
|
end
|
217
219
|
|
218
220
|
def split_method_info(minfo)
|
@@ -235,7 +237,7 @@ class XMPCompletionFilter < XMPFilter
|
|
235
237
|
%Q[#$1.constants + #$1.methods(true).#{methods_map_code($1)}]
|
236
238
|
when /^[A-Z]\w*$/ # normal constants
|
237
239
|
__prepare_line 'nil', 'Module.constants', '%n'
|
238
|
-
when /^(.*::.+)\.(
|
240
|
+
when /^(.*::.+)\.(.*)$/ # toplevel class methods
|
239
241
|
@prefix = $2
|
240
242
|
__prepare_line $1, "#$1.methods",
|
241
243
|
%Q[%n.#{methods_map_code($1)}]
|
@@ -274,7 +276,7 @@ class XMPCompletionFilter < XMPFilter
|
|
274
276
|
idx = 1
|
275
277
|
oneline_ize(<<EOC)
|
276
278
|
#{rcv} = (#{recv})
|
277
|
-
#{v} = (#{all_completion_expr}).grep(/^#{Regexp.quote(@prefix)}/)
|
279
|
+
#{v} = (#{all_completion_expr}).map{|x| x.to_s}.grep(/^#{Regexp.quote(@prefix)}/)
|
278
280
|
#{rcv} = Module === #{rcv} ? #{rcv} : #{rcv}.class
|
279
281
|
$stderr.puts("#{MARKER}[#{idx}] => " + #{rcv}.to_s + " " + #{v}.join(" ")) || #{v}
|
280
282
|
exit
|
data/lib/rcodetools/fork.rb
CHANGED
@@ -39,7 +39,7 @@ rct-fork and rct-fork-client (we) are originally ruby_fork/ruby_fork_client in Z
|
|
39
39
|
Completion or document browsing in a script with heavy libraries such as Rails takes a significant latency.
|
40
40
|
We eliminate constant overhead of loading heavy libraries.
|
41
41
|
|
42
|
-
rct-fork loads libraries you want to pre-load and opens up a server socket and waits for connection. When a connection comes in rct-fork forks to make a copy of the environment.
|
42
|
+
rct-fork loads libraries you want to pre-load and opens up a server socket and waits for connection. When a connection comes in rct-fork forks to make a copy of the environment. rct-fork loads rubygems at startup.
|
43
43
|
|
44
44
|
rct-fork-client connects to the rct-fork server and runs script in server's environment.
|
45
45
|
|
@@ -89,10 +89,9 @@ XXX
|
|
89
89
|
Process.setsid
|
90
90
|
fork and exit!
|
91
91
|
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
# STDERR.reopen io
|
92
|
+
STDIN.reopen io
|
93
|
+
STDOUT.reopen io
|
94
|
+
STDERR.reopen io
|
96
95
|
|
97
96
|
yield if block_given?
|
98
97
|
end
|
@@ -170,6 +169,10 @@ XXX
|
|
170
169
|
end
|
171
170
|
|
172
171
|
def self.start_server(args = ARGV)
|
172
|
+
begin
|
173
|
+
require 'rubygems'
|
174
|
+
rescue LoadError
|
175
|
+
end
|
173
176
|
write_pwd
|
174
177
|
settings = parse_server_args args
|
175
178
|
setup_environment settings
|
@@ -212,9 +215,13 @@ XXX
|
|
212
215
|
settings[:extra_paths].flatten!
|
213
216
|
settings[:extra_paths].each { |dir| $:.unshift dir }
|
214
217
|
|
215
|
-
|
216
|
-
|
217
|
-
|
218
|
+
begin
|
219
|
+
settings[:requires].each { |file| require file }
|
220
|
+
settings[:code].each { |code| eval code, TOPLEVEL_BINDING }
|
221
|
+
rescue Exception
|
222
|
+
$@.reject! {|s| s =~ %r!rcodetools/fork\.rb!}
|
223
|
+
raise
|
224
|
+
end
|
218
225
|
end
|
219
226
|
|
220
227
|
end
|
data/lib/rcodetools/options.rb
CHANGED
@@ -66,6 +66,12 @@ module OptionHandler
|
|
66
66
|
on("--debug", "Write transformed source code to xmp-tmp.PID.rb.") do
|
67
67
|
options[:dump] = "xmp-tmp.#{Process.pid}.rb"
|
68
68
|
end
|
69
|
+
on("--tmpfile", "--tempfile", "Use tmpfile instead of open3. (non-windows)") do
|
70
|
+
options[:execute_ruby_tmpfile] = true
|
71
|
+
end
|
72
|
+
on("-w N", "--width N", Integer, "Set width of multi-line annotation. (xmpfilter only)") do |width|
|
73
|
+
options[:width] = width
|
74
|
+
end
|
69
75
|
separator ""
|
70
76
|
on("-h", "--help", "Show this message") do
|
71
77
|
puts self
|
@@ -110,6 +116,7 @@ DEFAULT_OPTIONS = {
|
|
110
116
|
:interpreter => "ruby",
|
111
117
|
:options => ["hoge"],
|
112
118
|
:min_codeline_size => 50,
|
119
|
+
:width => 79,
|
113
120
|
:libs => [],
|
114
121
|
:evals => [],
|
115
122
|
:include_paths => [],
|
@@ -124,5 +131,6 @@ DEFAULT_OPTIONS = {
|
|
124
131
|
:detect_rct_fork => false,
|
125
132
|
:use_rbtest => false,
|
126
133
|
:detect_rbtest => false,
|
134
|
+
:execute_ruby_tmpfile => false,
|
127
135
|
}
|
128
136
|
end # /Rcodetools
|
data/lib/rcodetools/xmpfilter.rb
CHANGED
@@ -1,14 +1,17 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
|
-
# Copyright (c) 2005-
|
2
|
+
# Copyright (c) 2005-2008 Mauricio Fernandez <mfp@acm.org> http://eigenclass.org
|
3
3
|
# rubikitch <rubikitch@ruby-lang.org>
|
4
4
|
# Use and distribution subject to the terms of the Ruby license.
|
5
5
|
|
6
|
+
ENV['HOME'] ||= "#{ENV['HOMEDRIVE']}#{ENV['HOMEPATH']}"
|
6
7
|
require 'rcodetools/fork_config'
|
8
|
+
require 'rcodetools/compat'
|
9
|
+
require 'tmpdir'
|
7
10
|
|
8
11
|
module Rcodetools
|
9
12
|
|
10
13
|
class XMPFilter
|
11
|
-
VERSION = "0.
|
14
|
+
VERSION = "0.8.0"
|
12
15
|
|
13
16
|
MARKER = "!XMP#{Time.new.to_i}_#{Process.pid}_#{rand(1000000)}!"
|
14
17
|
XMP_RE = Regexp.new("^" + Regexp.escape(MARKER) + '\[([0-9]+)\] (=>|~>|==>) (.*)')
|
@@ -21,17 +24,18 @@ class XMPFilter
|
|
21
24
|
:include_paths => [], :warnings => true,
|
22
25
|
:use_parentheses => true}
|
23
26
|
|
24
|
-
def
|
27
|
+
def windows?
|
25
28
|
/win|mingw/ =~ RUBY_PLATFORM && /darwin/ !~ RUBY_PLATFORM
|
26
29
|
end
|
27
30
|
|
28
|
-
Interpreter = Struct.new(:options, :execute_method, :accept_debug, :chdir_proc)
|
31
|
+
Interpreter = Struct.new(:options, :execute_method, :accept_debug, :accept_include_paths, :chdir_proc)
|
29
32
|
INTERPRETER_RUBY = Interpreter.new(["-w"],
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
INTERPRETER_FORK = Interpreter.new(["-S", "rct-fork-client"],
|
34
|
-
|
33
|
+
:execute_ruby, true, true, nil)
|
34
|
+
INTERPRETER_RBTEST = Interpreter.new(["-S", "rbtest"],
|
35
|
+
:execute_script, false, false, nil)
|
36
|
+
INTERPRETER_FORK = Interpreter.new(["-S", "rct-fork-client"],
|
37
|
+
:execute_tmpfile, false, true,
|
38
|
+
lambda { Fork::chdir_fork_directory })
|
35
39
|
|
36
40
|
def self.detect_rbtest(code, opts)
|
37
41
|
opts[:use_rbtest] ||= (opts[:detect_rbtest] and code =~ /^=begin test./) ? true : false
|
@@ -58,7 +62,10 @@ class XMPFilter
|
|
58
62
|
test_script = options[:test_script]
|
59
63
|
test_method = options[:test_method]
|
60
64
|
filename = options[:filename]
|
65
|
+
@execute_ruby_tmpfile = options[:execute_ruby_tmpfile]
|
61
66
|
@postfix = ""
|
67
|
+
@stdin_path = nil
|
68
|
+
@width = options[:width]
|
62
69
|
|
63
70
|
initialize_rct_fork if options[:detect_rct_fork]
|
64
71
|
initialize_rbtest if options[:use_rbtest]
|
@@ -82,7 +89,7 @@ class XMPFilter
|
|
82
89
|
basedir = common_path(test_script, filename)
|
83
90
|
relative_filename = filename[basedir.length+1 .. -1].sub(%r!^lib/!, '')
|
84
91
|
@evals << %Q!$LOADED_FEATURES << #{relative_filename.dump}!
|
85
|
-
@evals <<
|
92
|
+
@evals << safe_require_code('test/unit')
|
86
93
|
@evals << %Q!load #{test_script.dump}!
|
87
94
|
end
|
88
95
|
test_method = get_test_method_from_lineno(test_script, test_method.to_i) if test_method =~ /^\d/
|
@@ -114,24 +121,30 @@ class XMPFilter
|
|
114
121
|
ret
|
115
122
|
end
|
116
123
|
|
124
|
+
SINGLE_LINE_RE = /^(?!(?:\s+|(?:\s*#.+)?)# ?=>)(.*) # ?=>.*/
|
125
|
+
MULTI_LINE_RE = /^(.*)\n(( *)# ?=>.*(?:\n|\z))(?: *# .*\n)*/
|
117
126
|
def annotate(code)
|
118
127
|
idx = 0
|
119
|
-
newcode = code.gsub(
|
120
|
-
|
121
|
-
|
122
|
-
end
|
128
|
+
newcode = code.gsub(SINGLE_LINE_RE){ prepare_line($1, idx += 1) }
|
129
|
+
newcode.gsub!(MULTI_LINE_RE){ prepare_line($1, idx += 1, true)}
|
130
|
+
File.open(@dump, "w"){|f| f.puts newcode} if @dump
|
123
131
|
stdout, stderr = execute(newcode)
|
124
132
|
output = stderr.readlines
|
125
133
|
runtime_data = extract_data(output)
|
126
134
|
idx = 0
|
127
|
-
annotated = code.gsub(
|
135
|
+
annotated = code.gsub(SINGLE_LINE_RE) { |l|
|
128
136
|
expr = $1
|
129
137
|
if /^\s*#/ =~ l
|
130
138
|
l
|
131
139
|
else
|
132
140
|
annotated_line(l, expr, runtime_data, idx += 1)
|
133
141
|
end
|
134
|
-
|
142
|
+
}
|
143
|
+
annotated.gsub!(/ # !>.*/, '')
|
144
|
+
annotated.gsub!(/# (>>|~>)[^\n]*\n/m, "");
|
145
|
+
annotated.gsub!(MULTI_LINE_RE) { |l|
|
146
|
+
annotated_multi_line(l, $1, $3, runtime_data, idx += 1)
|
147
|
+
}
|
135
148
|
ret = final_decoration(annotated, output)
|
136
149
|
if @output_stdout and (s = stdout.read) != ""
|
137
150
|
ret << s.inject(""){|s,line| s + "# >> #{line}".chomp + "\n" }
|
@@ -143,13 +156,28 @@ class XMPFilter
|
|
143
156
|
"#{expression} # => " + (runtime_data.results[idx].map{|x| x[1]} || []).join(", ")
|
144
157
|
end
|
145
158
|
|
146
|
-
def
|
159
|
+
def annotated_multi_line(line, expression, indent, runtime_data, idx)
|
160
|
+
pretty = (runtime_data.results[idx].map{|x| x[1]} || []).join(", ")
|
161
|
+
first, *rest = pretty.to_a
|
162
|
+
rest.inject("#{expression}\n#{indent}# => #{first}") {|s, l| s << "#{indent}# " << l }
|
163
|
+
end
|
164
|
+
|
165
|
+
def prepare_line_annotation(expr, idx, multi_line=false)
|
147
166
|
v = "#{VAR}"
|
148
167
|
blocal = "__#{VAR}"
|
149
168
|
blocal2 = "___#{VAR}"
|
169
|
+
lastmatch = "____#{VAR}"
|
170
|
+
if multi_line
|
171
|
+
pp = safe_require_code "pp"
|
172
|
+
result = "((begin; #{lastmatch} = $~; PP.pp(#{v}, '', #{@width-5}).gsub(/\\r?\\n/, 'PPPROTECT'); ensure; $~ = #{lastmatch} end))"
|
173
|
+
else
|
174
|
+
pp = ''
|
175
|
+
result = "#{v}.inspect"
|
176
|
+
end
|
150
177
|
oneline_ize(<<-EOF).chomp
|
178
|
+
#{pp}
|
151
179
|
#{v} = (#{expr})
|
152
|
-
$stderr.puts("#{MARKER}[#{idx}] => " + #{v}.class.to_s + " " + #{
|
180
|
+
$stderr.puts("#{MARKER}[#{idx}] => " + #{v}.class.to_s + " " + #{result}) || begin
|
153
181
|
$stderr.puts local_variables
|
154
182
|
local_variables.each{|#{blocal}|
|
155
183
|
#{blocal2} = eval(#{blocal})
|
@@ -168,6 +196,17 @@ end || #{v}
|
|
168
196
|
end
|
169
197
|
alias_method :prepare_line, :prepare_line_annotation
|
170
198
|
|
199
|
+
def safe_require_code(lib)
|
200
|
+
oldverbose = "$#{VAR}_old_verbose"
|
201
|
+
"#{oldverbose} = $VERBOSE; $VERBOSE = false; require '#{lib}'; $VERBOSE = #{oldverbose}"
|
202
|
+
end
|
203
|
+
private :safe_require_code
|
204
|
+
|
205
|
+
def execute_ruby(code)
|
206
|
+
meth = (windows? or @execute_ruby_tmpfile) ? :execute_tmpfile : :execute_popen
|
207
|
+
__send__ meth, code
|
208
|
+
end
|
209
|
+
|
171
210
|
def execute_tmpfile(code)
|
172
211
|
ios = %w[_ stdin stdout stderr]
|
173
212
|
stdin, stdout, stderr = (1..3).map do |i|
|
@@ -182,6 +221,7 @@ end || #{v}
|
|
182
221
|
end
|
183
222
|
stdin.puts code
|
184
223
|
stdin.close
|
224
|
+
@stdin_path = File.expand_path stdin.path
|
185
225
|
exe_line = <<-EOF.map{|l| l.strip}.join(";")
|
186
226
|
$stdout.reopen('#{File.expand_path(stdout.path)}', 'w')
|
187
227
|
$stderr.reopen('#{File.expand_path(stderr.path)}', 'w')
|
@@ -209,20 +249,25 @@ end || #{v}
|
|
209
249
|
end
|
210
250
|
|
211
251
|
def execute_script(code)
|
212
|
-
|
213
|
-
File.open(
|
214
|
-
path = File.expand_path(codefile)
|
252
|
+
path = File.expand_path("xmpfilter.tmpfile_#{Process.pid}.rb", Dir.tmpdir)
|
253
|
+
File.open(path, "w"){|f| f.puts code}
|
215
254
|
at_exit { File.unlink path if File.exist? path}
|
216
|
-
|
255
|
+
stdout_path, stderr_path = (1..2).map do |i|
|
217
256
|
fname = "xmpfilter.tmpfile_#{Process.pid}-#{i}.rb"
|
218
|
-
|
219
|
-
at_exit { File.unlink fullname if File.exist? fullname}
|
220
|
-
File.open(fname, "w+")
|
257
|
+
File.expand_path(fname, Dir.tmpdir)
|
221
258
|
end
|
222
|
-
args = *(interpreter_command << %["#{
|
223
|
-
|
259
|
+
args = *(interpreter_command << %["#{path}"] << "2>" <<
|
260
|
+
%["#{stderr_path}"] << ">" << %["#{stdout_path}"])
|
224
261
|
system(args.join(" "))
|
225
|
-
|
262
|
+
|
263
|
+
[stdout_path, stderr_path].map do |fullname|
|
264
|
+
f = File.open(fullname, "r")
|
265
|
+
at_exit {
|
266
|
+
f.close unless f.closed?
|
267
|
+
File.unlink fullname if File.exist? fullname
|
268
|
+
}
|
269
|
+
f
|
270
|
+
end
|
226
271
|
end
|
227
272
|
|
228
273
|
def execute(code)
|
@@ -232,7 +277,7 @@ end || #{v}
|
|
232
277
|
def interpreter_command
|
233
278
|
r = [ @interpreter ] + @interpreter_info.options
|
234
279
|
r << "-d" if $DEBUG and @interpreter_info.accept_debug
|
235
|
-
r << "-I#{@include_paths.join(":")}"
|
280
|
+
r << "-I#{@include_paths.join(":")}" if @interpreter_info.accept_include_paths and !@include_paths.empty?
|
236
281
|
@libs.each{|x| r << "-r#{x}" } unless @libs.empty?
|
237
282
|
(r << "-").concat @options unless @options.empty?
|
238
283
|
r
|
@@ -247,7 +292,7 @@ end || #{v}
|
|
247
292
|
case op
|
248
293
|
when "=>"
|
249
294
|
klass, value = /(\S+)\s+(.*)/.match(result).captures
|
250
|
-
results[result_id.to_i] << [klass, value]
|
295
|
+
results[result_id.to_i] << [klass, value.gsub(/PPPROTECT/, "\n")]
|
251
296
|
when "~>"
|
252
297
|
exceptions[result_id.to_i] << result
|
253
298
|
when "==>"
|
@@ -273,14 +318,16 @@ end || #{v}
|
|
273
318
|
end
|
274
319
|
end
|
275
320
|
output = output.reject{|x| /^-:[0-9]+: warning/.match(x)}
|
276
|
-
if exception =
|
277
|
-
|
321
|
+
if exception = /^-e?:[0-9]+:.*|^(?!!XMP)[^\n]+:[0-9]+:in .*/m.match(output.join)
|
322
|
+
err = exception[0]
|
323
|
+
err.gsub!(Regexp.union(@stdin_path), '-') if @stdin_path
|
324
|
+
ret << err.map{|line| "# ~> " + line }
|
278
325
|
end
|
279
326
|
ret
|
280
327
|
end
|
281
328
|
|
282
329
|
def oneline_ize(code)
|
283
|
-
"((" + code.gsub(/\r?\n|\r/, ';') + "))
|
330
|
+
"((" + code.gsub(/\r?\n|\r/, ';') + "));#{@postfix}\n"
|
284
331
|
end
|
285
332
|
|
286
333
|
def debugprint(*args)
|