trenni 1.4.4 → 1.4.5

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 216efe70504b121ea181eb3de5e24978db147f7e
4
- data.tar.gz: fe495f4698096e743427e8b1860cf214ba8d5ce8
3
+ metadata.gz: 35f057654b1e83a57d1fe72969c9ee72eaf376de
4
+ data.tar.gz: a96c7a44b65be07ed3dc69e20ddbb25d92ee300a
5
5
  SHA512:
6
- metadata.gz: f18a0a7bc9a13a81289d6f14188812759e645a5cdea3f9d4a8ecaa6dcfad2da6f71679f032482b176b8ff494396e0914b8b84326f470daa1aebefe91160de918
7
- data.tar.gz: dc5079d20186b3800de81560c6932a6a0ff23b5f084e0ea0d2f3e958742859390fa040be47560521e3cbbf0f0d3648833914929a4c61b0b5323cdb86c9bdf0bb
6
+ metadata.gz: cef23ac0aa45af2f913cdd6b864a5beeacb78e0b3bc1c621db0565de40a34f030df816f048341a8c582f79628b75c334e33de3580c869956c7b0884856a48e21
7
+ data.tar.gz: e6a318ab7acaa6a04c5857b51caecb019936b07dcdcdd50581d0cb7879a2260ac8b1c399fdd28660cfd4cd87fa247649d89a3da54205b7bee15ede9a7e890bd4
data/.travis.yml CHANGED
@@ -1,5 +1,13 @@
1
1
  language: ruby
2
+ sudo: false
2
3
  rvm:
3
- - "2.0"
4
- - "2.1"
4
+ - 2.0.0
5
+ - 2.1.8
6
+ - 2.2.4
7
+ - 2.3.0
8
+ - ruby-head
9
+ - rbx-2
5
10
  env: COVERAGE=true
11
+ matrix:
12
+ allow_failures:
13
+ - rvm: "rbx-2"
data/lib/trenni/parser.rb CHANGED
@@ -26,49 +26,81 @@ module Trenni
26
26
  OPENED_TAG = :opened
27
27
  CLOSED_TAG = :closed
28
28
 
29
- def self.line_at_offset(input, input_offset)
30
- line_number = 1
31
- line_offset = offset = 0
32
-
33
- input.each_line do |line|
34
- line_offset = offset
35
- offset += line.size
36
-
37
- if offset >= input_offset
38
- return {
39
- # The line that contains the input_offset:
40
- :line_number => line_number,
41
- # The offset to the start of that line:
42
- :line_offset => line_offset,
43
- # The number of characters from the start of the line to the input_offset:
44
- :character_offset => input_offset - line_offset,
45
- # The line of text itself:
46
- :text => line.chomp
47
- }
29
+ class Location
30
+ def initialize(input, offset)
31
+ raise ArgumentError.new("Offset #{index} is past end of input #{input.bytesize}") if offset > input.bytesize
32
+
33
+ @offset = offset
34
+ @line_index = 0
35
+ line_offset = next_line_offset = 0
36
+
37
+ input.each_line do |line|
38
+ line_offset = next_line_offset
39
+ next_line_offset += line.bytesize
40
+
41
+ # Is our input offset within this line?
42
+ if next_line_offset >= offset
43
+ @line_text = line.chomp
44
+ @line_range = line_offset...next_line_offset
45
+ break
46
+ else
47
+ @line_index += 1
48
+ end
48
49
  end
49
-
50
- line_number += 1
51
50
  end
52
51
 
53
- return nil
52
+ def to_i
53
+ @offset
54
+ end
55
+
56
+ def to_s
57
+ "[#{self.line_number}:#{self.line_range}]"
58
+ end
59
+
60
+ # The line that contains the @offset (base 0 indexing).
61
+ attr :line_index
62
+
63
+ # The line index, but base-1.
64
+ def line_number
65
+ @line_index + 1
66
+ end
67
+
68
+ # The byte offset to the start of that line.
69
+ attr :line_range
70
+
71
+ # The number of bytes from the start of the line to the given offset in the input.
72
+ def line_offset
73
+ @offset - @line_range.min
74
+ end
75
+
76
+ attr :line_text
77
+
78
+ def to_hash
79
+ {
80
+ :line_number => self.line_number,
81
+ :line_offset => self.line_range.min,
82
+ :character_offset => self.line_offset,
83
+ :text => self.line_text.chomp
84
+ }
85
+ end
86
+ end
87
+
88
+ def self.line_at_offset(input, input_offset)
89
+ warn "#{self.class}::line_at_offset is deprecated, use Location.new(input, input_offset) directly!"
90
+
91
+ Location.new(input, input_offset).to_hash rescue nil
54
92
  end
55
93
 
56
94
  class ParseError < StandardError
57
95
  def initialize(message, scanner)
58
96
  @message = message
59
-
60
- @position = scanner.pos
61
- @line = Parser.line_at_offset(scanner.string, @position)
97
+ @location = Location.new(scanner.string, scanner.pos)
62
98
  end
63
-
64
- attr :offset
99
+
100
+ attr :location
65
101
 
66
102
  def to_s
67
- if @offset
68
- "Parse Error: #{@message} @ [#{@line[0]}:#{@line[2]}]: #{@line[4]}"
69
- else
70
- "Parse Error [#{@position}]: #{@message}"
71
- end
103
+ "#{@message} at #{@location}"
72
104
  end
73
105
  end
74
106
 
@@ -19,5 +19,5 @@
19
19
  # THE SOFTWARE.
20
20
 
21
21
  module Trenni
22
- VERSION = "1.4.4"
22
+ VERSION = "1.4.5"
23
23
  end
@@ -90,13 +90,24 @@ module Trenni::ParserSpec
90
90
  it "should know about line numbers" do
91
91
  data = %Q{Hello\nWorld\nFoo\nBar!}
92
92
 
93
- line = Trenni::Parser.line_at_offset(data, 7)
93
+ location = Trenni::Parser::Location.new(data, 7)
94
94
 
95
- expect(line[:text]).to be == "World"
95
+ expect(location.line_text).to be == "World"
96
96
 
97
- expect(line[:line_number]).to be == 2
98
- expect(line[:line_offset]).to be == 6
99
- expect(line[:character_offset]).to be == 1
97
+ expect(location.line_number).to be == 2
98
+ expect(location.line_range.min).to be == 6
99
+ expect(location.line_offset).to be == 1
100
+ end
101
+
102
+ it "should know about line numbers when input contains multi-byte characters" do
103
+ delegate = ParserDelegate.new
104
+ scanner = Trenni::Parser.new(delegate)
105
+
106
+ data = %Q{<p>\nこんにちは\nWorld\n<p}
107
+ error = scanner.parse(data) rescue $!
108
+
109
+ expect(error).to be_kind_of Trenni::Parser::ParseError
110
+ expect(error.location.line_number).to be == 4
100
111
  end
101
112
  end
102
113
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: trenni
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.4
4
+ version: 1.4.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Samuel Williams
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-01-10 00:00:00.000000000 Z
11
+ date: 2016-01-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler