glark 1.9.0 → 1.10.0
Sign up to get free protection for your applications and to get access to all the features.
- data/bin/glark +2 -2
- data/lib/glark.rb +1 -1
- data/lib/glark/app/app.rb +48 -0
- data/lib/glark/app/help.rb +103 -0
- data/lib/glark/app/info/options.rb +84 -0
- data/lib/glark/app/options.rb +201 -0
- data/lib/glark/app/rcfile.rb +49 -0
- data/lib/glark/app/runner.rb +140 -0
- data/lib/glark/app/spec.rb +19 -0
- data/lib/glark/input/filter/criteria_opts.rb +41 -0
- data/lib/glark/input/filter/dir_criteria_opts.rb +37 -0
- data/lib/glark/input/filter/file_criteria_opts.rb +33 -0
- data/lib/glark/input/filter/filter.rb +59 -0
- data/lib/glark/input/filter/options.rb +171 -0
- data/lib/glark/input/options.rb +120 -0
- data/lib/glark/input/range.rb +104 -0
- data/lib/glark/input/spec.rb +39 -0
- data/lib/glark/io/file/archive_file.rb +64 -0
- data/lib/glark/io/file/binary_file.rb +19 -0
- data/lib/glark/io/file/file.rb +57 -0
- data/lib/glark/io/file/gz_file.rb +21 -0
- data/lib/glark/io/file/tar_file.rb +35 -0
- data/lib/glark/io/file/tar_gz_file.rb +52 -0
- data/lib/glark/io/file/zip_file.rb +39 -0
- data/lib/glark/match/and.rb +83 -0
- data/lib/glark/match/and_distance.rb +58 -0
- data/lib/glark/match/compound.rb +34 -0
- data/lib/glark/match/expression.rb +63 -0
- data/lib/glark/match/factory.rb +173 -0
- data/lib/glark/match/ior.rb +20 -0
- data/lib/glark/match/options.rb +74 -0
- data/lib/glark/match/or.rb +41 -0
- data/lib/glark/match/re.rb +81 -0
- data/lib/glark/match/re_factory.rb +44 -0
- data/lib/glark/match/spec.rb +59 -0
- data/lib/glark/match/xor.rb +20 -0
- data/lib/glark/output/binary_file_summary.rb +17 -0
- data/lib/glark/output/common.rb +43 -0
- data/lib/glark/output/context.rb +57 -0
- data/lib/glark/output/count.rb +26 -0
- data/lib/glark/output/file_header.rb +20 -0
- data/lib/glark/output/file_name_only.rb +35 -0
- data/lib/glark/output/formatted.rb +22 -0
- data/lib/glark/output/glark_count.rb +23 -0
- data/lib/glark/output/glark_format.rb +62 -0
- data/lib/glark/output/glark_lines.rb +36 -0
- data/lib/glark/output/grep_count.rb +18 -0
- data/lib/glark/output/grep_lines.rb +42 -0
- data/lib/glark/output/line_status.rb +46 -0
- data/lib/glark/output/lines.rb +100 -0
- data/lib/glark/output/match_list.rb +15 -0
- data/lib/glark/output/options.rb +103 -0
- data/lib/glark/output/results.rb +23 -0
- data/lib/glark/output/spec.rb +105 -0
- data/lib/glark/output/unfiltered_lines.rb +28 -0
- data/lib/glark/util/colors/options.rb +143 -0
- data/lib/glark/util/colors/spec.rb +21 -0
- data/lib/glark/util/highlight.rb +108 -0
- data/lib/glark/util/io/depth.rb +29 -0
- data/lib/glark/util/io/fileset.rb +162 -0
- data/lib/glark/util/io/filter/criteria.rb +49 -0
- data/lib/glark/util/io/filter/filter.rb +10 -0
- data/lib/glark/util/io/lines.rb +117 -0
- data/lib/glark/util/option.rb +34 -0
- data/lib/glark/util/options.rb +12 -0
- data/lib/glark/util/optutil.rb +69 -0
- data/lib/glark/util/timestamper.rb +18 -0
- data/man/glark.1 +1134 -0
- data/test/glark/app/and_test.rb +82 -0
- data/test/glark/app/compound_test.rb +33 -0
- data/test/glark/app/context_test.rb +43 -0
- data/test/glark/app/count_test.rb +89 -0
- data/test/glark/app/dump_test.rb +16 -0
- data/test/glark/app/expression_file_test.rb +22 -0
- data/test/glark/app/extended_regexp_test.rb +17 -0
- data/test/glark/app/extract_matches_test.rb +27 -0
- data/test/glark/app/files_with_match_test.rb +32 -0
- data/test/glark/app/files_without_match_test.rb +26 -0
- data/test/glark/app/filter_test.rb +118 -0
- data/test/glark/app/highlight_test.rb +78 -0
- data/test/glark/app/ignore_case_test.rb +22 -0
- data/test/glark/app/invert_test.rb +49 -0
- data/test/glark/app/ior_test.rb +21 -0
- data/test/glark/app/label_test.rb +28 -0
- data/test/glark/app/line_number_color_test.rb +42 -0
- data/test/glark/app/line_numbers_test.rb +42 -0
- data/test/glark/app/match_limit_test.rb +49 -0
- data/test/glark/app/options_test.rb +722 -0
- data/test/glark/app/range_test.rb +101 -0
- data/test/glark/app/rcfile_test.rb +113 -0
- data/test/glark/app/record_separator_test.rb +32 -0
- data/test/glark/app/regexp_test.rb +48 -0
- data/test/glark/app/tc.rb +92 -0
- data/test/glark/app/text_color_test.rb +31 -0
- data/test/glark/app/whole_lines_test.rb +17 -0
- data/test/glark/app/whole_words_test.rb +42 -0
- data/test/glark/app/xor_test.rb +19 -0
- data/test/glark/input/binary_file_test.rb +0 -0
- data/test/glark/input/directory_test.rb +202 -0
- data/test/glark/input/dirname_test.rb +69 -0
- data/test/glark/input/exclude_matching_test.rb +20 -0
- data/test/glark/input/ext_test.rb +65 -0
- data/test/glark/input/filter/criteria_test.rb +91 -0
- data/test/glark/input/filter/filter_spec_test.rb +27 -0
- data/test/glark/input/filter/filter_test.rb +21 -0
- data/test/glark/input/name_test.rb +75 -0
- data/test/glark/input/path_test.rb +72 -0
- data/test/glark/input/range_test.rb +82 -0
- data/test/glark/input/size_limit_test.rb +51 -0
- data/test/glark/input/split_as_path_test.rb +28 -0
- data/test/glark/match_test.rb +192 -0
- data/test/glark/resources.rb +21 -0
- data/test/glark/tc.rb +37 -0
- data/test/resources/add.rb +10 -0
- data/test/resources/echo.rb +2 -0
- data/test/resources/greet.rb +13 -0
- metadata +198 -28
- data/README +0 -0
- data/bin/jlark +0 -63
- data/lib/glark/expression.rb +0 -440
- data/lib/glark/exprfactory.rb +0 -248
- data/lib/glark/glark.rb +0 -297
- data/lib/glark/help.rb +0 -85
- data/lib/glark/input.rb +0 -183
- data/lib/glark/options.rb +0 -757
- data/lib/glark/output.rb +0 -266
- data/test/lib/glark/glark_test.rb +0 -317
- data/test/lib/glark/options_test.rb +0 -891
@@ -0,0 +1,108 @@
|
|
1
|
+
#!/usr/bin/ruby -w
|
2
|
+
# -*- ruby -*-
|
3
|
+
|
4
|
+
$rielold = false
|
5
|
+
|
6
|
+
require 'rubygems'
|
7
|
+
require 'rainbow'
|
8
|
+
require 'singleton'
|
9
|
+
|
10
|
+
if $rielold
|
11
|
+
require 'riel/ansicolor'
|
12
|
+
else
|
13
|
+
require 'riel/text/ansi/ansi_highlight'
|
14
|
+
end
|
15
|
+
|
16
|
+
module Highlight
|
17
|
+
RESET = "\x1b[0m"
|
18
|
+
|
19
|
+
def adorn hl, str
|
20
|
+
if $rielold
|
21
|
+
hl.highlight str
|
22
|
+
else
|
23
|
+
hl + str + RESET
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
module Sickill
|
29
|
+
module Rainbow
|
30
|
+
class AnsiColor
|
31
|
+
$-w = false
|
32
|
+
# includes the aberrant color name in the error message.
|
33
|
+
def validate_color_name #:nodoc:
|
34
|
+
color_names = TERM_COLORS.keys
|
35
|
+
|
36
|
+
unless color_names.include?(@color)
|
37
|
+
raise ArgumentError.new "Unknown color name: '#{@color}'; valid names: #{color_names.join(', ')}"
|
38
|
+
end
|
39
|
+
end
|
40
|
+
$-w = true
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
class RainbowHighlighter
|
46
|
+
include Singleton
|
47
|
+
|
48
|
+
COLORS = %w{ black red green yellow blue magenta cyan white [\dA-Fa-f]{6} }
|
49
|
+
DECORATIONS = %w{ none reset bold underscore underline blink reverse inverse negative concealed }
|
50
|
+
|
51
|
+
BACKGROUND_COLORS = COLORS.collect { |color| "on_#{color}" }
|
52
|
+
FOREGROUND_COLORS = COLORS
|
53
|
+
|
54
|
+
COLORS_RE = Regexp.new('(?: ' +
|
55
|
+
# background will be in capture 0
|
56
|
+
'on(?:\s+|_) ( ' + COLORS.join(' | ') + ' ) | ' +
|
57
|
+
# foreground will be in capture 1
|
58
|
+
'( ' + (COLORS + DECORATIONS).join(' | ') + ' ) ' +
|
59
|
+
')', Regexp::EXTENDED)
|
60
|
+
|
61
|
+
def get_code color, type
|
62
|
+
case color
|
63
|
+
when 'bold', 'bright'
|
64
|
+
Sickill::Rainbow::TERM_EFFECTS[:bright]
|
65
|
+
when 'reverse', 'negative', 'inverse'
|
66
|
+
Sickill::Rainbow::TERM_EFFECTS[:inverse]
|
67
|
+
when 'underline'
|
68
|
+
Sickill::Rainbow::TERM_EFFECTS[:underline]
|
69
|
+
when 'blink'
|
70
|
+
Sickill::Rainbow::TERM_EFFECTS[:blink]
|
71
|
+
when %r{^[\dA-Fa-f]{6}$}
|
72
|
+
ac = Sickill::Rainbow::AnsiColor.new type, color
|
73
|
+
ac.code
|
74
|
+
else
|
75
|
+
ac = Sickill::Rainbow::AnsiColor.new type, color.to_sym
|
76
|
+
ac.code
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
def to_codes color
|
81
|
+
codes = ""
|
82
|
+
return codes unless Sickill::Rainbow.enabled
|
83
|
+
color.scan(COLORS_RE).collect do |md|
|
84
|
+
color, type = md[0] ? [ md[0], :background ] : [ md[1], :foreground ]
|
85
|
+
code = get_code color, type
|
86
|
+
"\e[#{code}m"
|
87
|
+
end.join ''
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
class HlWrapper
|
92
|
+
def initialize
|
93
|
+
# @hl = $rielold ? Text::ANSIHighlighter : Text::ANSIHighlighter.instance
|
94
|
+
@hl = RainbowHighlighter.instance
|
95
|
+
end
|
96
|
+
|
97
|
+
def make_color color
|
98
|
+
if $rielold
|
99
|
+
result = @hl.make color
|
100
|
+
else
|
101
|
+
@hl.to_codes color
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
def make_rgb_color red, green, blue, fgbg
|
106
|
+
@hl.instance.to_rgb_code red, green, blue, fgbg
|
107
|
+
end
|
108
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
#!/usr/bin/ruby -w
|
2
|
+
#!ruby -w
|
3
|
+
# vim: set filetype=ruby : set sw=2
|
4
|
+
|
5
|
+
module Glark
|
6
|
+
# Depth for recursing directories.
|
7
|
+
class Depth
|
8
|
+
INFINITY = :infinity
|
9
|
+
|
10
|
+
attr_reader :value
|
11
|
+
|
12
|
+
def initialize value
|
13
|
+
@value = value
|
14
|
+
end
|
15
|
+
|
16
|
+
def infinity?
|
17
|
+
@value == INFINITY
|
18
|
+
end
|
19
|
+
|
20
|
+
def - num
|
21
|
+
return self if infinity? || @value.nil?
|
22
|
+
self.class.new @value - 1
|
23
|
+
end
|
24
|
+
|
25
|
+
def nonzero?
|
26
|
+
infinity? || @value.nil? || @value >= 0
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,162 @@
|
|
1
|
+
#!/usr/bin/ruby -w
|
2
|
+
#!ruby -w
|
3
|
+
# vim: set filetype=ruby : set sw=2
|
4
|
+
|
5
|
+
require 'rubygems'
|
6
|
+
require 'glark/util/io/depth'
|
7
|
+
require 'riel/filetype'
|
8
|
+
|
9
|
+
module Glark
|
10
|
+
# Files and directories. And standard input, just for fun.
|
11
|
+
class FileSet
|
12
|
+
include Loggable, Enumerable
|
13
|
+
|
14
|
+
attr_reader :files
|
15
|
+
|
16
|
+
DEPTH_RE = Regexp.new '\.\.\.(\d*)$'
|
17
|
+
|
18
|
+
def initialize fnames, args
|
19
|
+
@max_depth = Depth.new args[:max_depth]
|
20
|
+
@binary_files = args[:binary_files] || 'skip'
|
21
|
+
@dir_criteria = args[:dir_criteria]
|
22
|
+
@file_criteria = args[:file_criteria]
|
23
|
+
@split_as_path = args[:split_as_path]
|
24
|
+
|
25
|
+
@dir_to_max_depth = Hash.new
|
26
|
+
@files = Array.new
|
27
|
+
|
28
|
+
if fnames.size == 0
|
29
|
+
@files << '-'
|
30
|
+
else
|
31
|
+
add_files fnames
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
def size
|
36
|
+
@files.size
|
37
|
+
end
|
38
|
+
|
39
|
+
def add_files fnames
|
40
|
+
fnames.each do |fname|
|
41
|
+
if @split_as_path
|
42
|
+
add_as_path fname
|
43
|
+
else
|
44
|
+
add_fd fname
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
# this is a path in the form /usr/bin:/home/me/projects
|
50
|
+
def add_as_path path
|
51
|
+
path.to_s.split(::File::PATH_SEPARATOR).each do |element|
|
52
|
+
add_fd element
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
def add_fd fname
|
57
|
+
pn = nil
|
58
|
+
|
59
|
+
if md = DEPTH_RE.match(fname)
|
60
|
+
val = md[1].empty? ? nil : md[1].to_i
|
61
|
+
fname.sub! DEPTH_RE, ''
|
62
|
+
fname = '.' if fname.empty?
|
63
|
+
pn = Pathname.new fname
|
64
|
+
@dir_to_max_depth[pn] = Depth.new val
|
65
|
+
else
|
66
|
+
pn = Pathname.new fname
|
67
|
+
end
|
68
|
+
|
69
|
+
return if pn.file? && @file_criteria.skipped?(pn)
|
70
|
+
@files << pn
|
71
|
+
end
|
72
|
+
|
73
|
+
def stdin?
|
74
|
+
@files.size == 1 && @files.first == '-'
|
75
|
+
end
|
76
|
+
|
77
|
+
def each &blk
|
78
|
+
# to keep from cycling through links:
|
79
|
+
@yielded_files = Array.new
|
80
|
+
|
81
|
+
(0 ... @files.size).each do |idx|
|
82
|
+
pn = @files[idx]
|
83
|
+
type = FileType.type pn.to_s
|
84
|
+
|
85
|
+
if stdin?
|
86
|
+
blk.call [ :text, '-' ]
|
87
|
+
next
|
88
|
+
end
|
89
|
+
|
90
|
+
unless pn.readable?
|
91
|
+
write "directory not readable: #{pn}"
|
92
|
+
next
|
93
|
+
end
|
94
|
+
|
95
|
+
dirmax = @dir_to_max_depth[pn] || @max_depth
|
96
|
+
handle_pathname pn, dirmax, &blk
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
def handle_pathname pn, depth, &blk
|
101
|
+
if pn.directory?
|
102
|
+
handle_directory pn, depth, &blk
|
103
|
+
elsif pn.file?
|
104
|
+
handle_file pn, &blk
|
105
|
+
else
|
106
|
+
write "unknown file type: #{pn}"
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
def handle_directory pn, depth, &blk
|
111
|
+
return if @dir_criteria.skipped? pn, depth
|
112
|
+
|
113
|
+
subdepth = depth - 1
|
114
|
+
|
115
|
+
pn.children.sort.each do |entry|
|
116
|
+
next if @yielded_files.include?(entry)
|
117
|
+
if entry.file?
|
118
|
+
type = FileType.type entry.to_s
|
119
|
+
next if type == FileType::BINARY && @binary_files == 'skip'
|
120
|
+
end
|
121
|
+
@yielded_files << entry
|
122
|
+
handle_pathname entry, subdepth, &blk
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
def handle_file pn, &blk
|
127
|
+
return if @file_criteria.skipped? pn
|
128
|
+
|
129
|
+
type = FileType.type pn.to_s
|
130
|
+
case type
|
131
|
+
when FileType::TEXT
|
132
|
+
handle_text pn, &blk
|
133
|
+
when FileType::BINARY
|
134
|
+
handle_binary pn, &blk
|
135
|
+
when FileType::NONE
|
136
|
+
write "no such file: #{pn}"
|
137
|
+
when FileType::UNKNOWN
|
138
|
+
write "unknown file type: #{pn}"
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
def handle_text pn, &blk
|
143
|
+
blk.call [ :text, pn ]
|
144
|
+
end
|
145
|
+
|
146
|
+
def handle_binary pn, &blk
|
147
|
+
type = case @binary_files
|
148
|
+
when 'binary'
|
149
|
+
:binary
|
150
|
+
when 'skip', 'without-match'
|
151
|
+
return
|
152
|
+
when 'decompress', 'read'
|
153
|
+
:read
|
154
|
+
when 'list'
|
155
|
+
:list
|
156
|
+
else
|
157
|
+
:text
|
158
|
+
end
|
159
|
+
blk.call [ type, pn ]
|
160
|
+
end
|
161
|
+
end
|
162
|
+
end
|
@@ -0,0 +1,49 @@
|
|
1
|
+
#!/usr/bin/ruby -w
|
2
|
+
#!ruby -w
|
3
|
+
# vim: set filetype=ruby : set sw=2
|
4
|
+
|
5
|
+
require 'glark/util/io/filter/filter'
|
6
|
+
|
7
|
+
module Glark
|
8
|
+
class Criteria
|
9
|
+
include Loggable
|
10
|
+
|
11
|
+
def initialize
|
12
|
+
# by type (hash) => by positive/negative (hash) => filter list (array)
|
13
|
+
@type_to_posneg = Hash.new
|
14
|
+
end
|
15
|
+
|
16
|
+
def add type, posneg, filter
|
17
|
+
posneg_to_filters = (@type_to_posneg[type] ||= Hash.new)
|
18
|
+
filters = (posneg_to_filters[posneg] ||= Array.new)
|
19
|
+
filters << filter
|
20
|
+
end
|
21
|
+
|
22
|
+
def get type, posneg
|
23
|
+
return nil unless posneg_to_filters = @type_to_posneg[type]
|
24
|
+
posneg_to_filters[posneg]
|
25
|
+
end
|
26
|
+
|
27
|
+
def find_by_class type, posneg, cls
|
28
|
+
return unless filters = get(type, posneg)
|
29
|
+
filters.detect { |filter| filter.kind_of? cls }
|
30
|
+
end
|
31
|
+
|
32
|
+
def skipped? pn
|
33
|
+
!match? pn
|
34
|
+
end
|
35
|
+
|
36
|
+
def match? pn
|
37
|
+
@type_to_posneg.values.each do |typefilters|
|
38
|
+
if (posf = typefilters[:positive]) && !posf.empty?
|
39
|
+
return false unless posf.detect { |fl| fl.match? pn }
|
40
|
+
end
|
41
|
+
|
42
|
+
if (negf = typefilters[:negative]) && !negf.empty?
|
43
|
+
return false if negf.detect { |fl| fl.match? pn }
|
44
|
+
end
|
45
|
+
end
|
46
|
+
true
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,117 @@
|
|
1
|
+
#!/usr/bin/ruby -w
|
2
|
+
#!ruby -w
|
3
|
+
# vim: set filetype=ruby : set sw=2
|
4
|
+
|
5
|
+
module Glark
|
6
|
+
module IO
|
7
|
+
# Lines of input. Handles non-default ("\n") record separator.
|
8
|
+
class Lines
|
9
|
+
def initialize fname
|
10
|
+
@fname = fname
|
11
|
+
@count = nil
|
12
|
+
end
|
13
|
+
|
14
|
+
# Returns the given line for this file. For this method, a line ends with a
|
15
|
+
# CR, as opposed to the "lines" method, which ends with $/.
|
16
|
+
def get_line lnum
|
17
|
+
get_lines[lnum]
|
18
|
+
end
|
19
|
+
|
20
|
+
# this reads the entire file and returns the number of lines
|
21
|
+
def count
|
22
|
+
unless @count
|
23
|
+
@count = ::IO::readlines(@fname).size
|
24
|
+
end
|
25
|
+
@count
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
class LinesCR < Lines
|
30
|
+
def initialize fname, io
|
31
|
+
super fname
|
32
|
+
@lines = Array.new
|
33
|
+
@io = io
|
34
|
+
end
|
35
|
+
|
36
|
+
# Returns the lines for this file, separated by end of line sequences.
|
37
|
+
def get_lines
|
38
|
+
return @lines
|
39
|
+
end
|
40
|
+
|
41
|
+
def each_line &blk
|
42
|
+
while (line = @io.gets) && line.length > 0
|
43
|
+
@lines << line
|
44
|
+
blk.call line
|
45
|
+
end
|
46
|
+
@io.close
|
47
|
+
end
|
48
|
+
|
49
|
+
def get_region rnum
|
50
|
+
# easy case: range is the range number, unless it is out of range.
|
51
|
+
return rnum < @lines.length ? (rnum .. rnum) : nil
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
class LinesNonCR < Lines
|
56
|
+
# cross-platform end of line: DOS UNIX MAC
|
57
|
+
ANY_END_OF_LINE = Regexp.new '(?:\r\n|\n|\r)'
|
58
|
+
|
59
|
+
def initialize fname, io
|
60
|
+
super fname
|
61
|
+
@extracted = nil
|
62
|
+
@regions = nil
|
63
|
+
@lines = ::IO::readlines fname
|
64
|
+
end
|
65
|
+
|
66
|
+
def each_line &blk
|
67
|
+
@lines.each do |line|
|
68
|
+
blk.call line
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
# Returns the lines for this file, separated by end of line sequences.
|
73
|
+
def get_lines
|
74
|
+
@extracted ||= create_extracted
|
75
|
+
end
|
76
|
+
|
77
|
+
# returns the region/range that is represented by the region number
|
78
|
+
def get_region rnum
|
79
|
+
@regions ||= create_regions
|
80
|
+
@regions[rnum]
|
81
|
+
end
|
82
|
+
|
83
|
+
private
|
84
|
+
def create_extracted
|
85
|
+
# This is much easier. Just resplit the whole thing at end of line
|
86
|
+
# sequences.
|
87
|
+
|
88
|
+
eoline = "\n" # should be OS-dependent
|
89
|
+
srclines = @lines
|
90
|
+
reallines = @lines.join("").split ANY_END_OF_LINE
|
91
|
+
|
92
|
+
# "\n" after all but the last line
|
93
|
+
@extracted = (0 ... (reallines.length - 1)).collect { |lnum| reallines[lnum] + eoline }
|
94
|
+
@extracted << reallines[-1]
|
95
|
+
|
96
|
+
@extracted
|
97
|
+
end
|
98
|
+
|
99
|
+
def create_regions
|
100
|
+
@regions = [] # keys = region number; values = range of lines
|
101
|
+
|
102
|
+
lstart = 0
|
103
|
+
@lines.each do |line|
|
104
|
+
lend = lstart
|
105
|
+
line.scan(ANY_END_OF_LINE).each do |cr|
|
106
|
+
lend += 1
|
107
|
+
end
|
108
|
+
|
109
|
+
@regions << ::Range.new(lstart, lend - 1)
|
110
|
+
|
111
|
+
lstart = lend
|
112
|
+
end
|
113
|
+
@regions
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|