Skip to content

Commit d2ecd94

Browse files
schneemsandyywz
andcommitted
Fix missing line break due to puts logic
In #225 it was reported that the output looks incorrect: ``` $ cat /tmp/4a71c7e417cc9eac0971e3a2519b295c/scratch.rb def x.y.z end $ ruby /tmp/4a71c7e417cc9eac0971e3a2519b295c/scratch.rb /tmp/4a71c7e417cc9eac0971e3a2519b295c/scratch.rb: --> /tmp/4a71c7e417cc9eac0971e3a2519b295c/scratch.rb expected a delimiter to close the parametersunexpected '.', ignoring it > 1 def x.y.z > 2 end ``` Specifically: ``` expected a delimiter to close the parametersunexpected '.', ignoring it ``` However this does not show up when executing the debug executable: ``` $ bin/bundle exec exe/syntax_suggest /tmp/4a71c7e417cc9eac0971e3a2519b295c/scratch.rb --> /tmp/4a71c7e417cc9eac0971e3a2519b295c/scratch.rb expected a delimiter to close the parameters unexpected '.', ignoring it > 1 def x.y.z > 2 end ``` This is because `exe/syntax_suggest` uses STDOUT.puts while calling `ruby` with the filename uses a fake IO object represented by MiniStringIO. This class was incorrectly not adding a newline to the end of the print. The fix was to move the class to it's own file where it can be tested and then fix the behavior. close #225 Co-authored-by: Andy Yong <[email protected]>
1 parent eb4f254 commit d2ecd94

File tree

5 files changed

+52
-18
lines changed

5 files changed

+52
-18
lines changed

CHANGELOG.md

+2
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
## HEAD (unreleased)
22

3+
- Fix: Separate multiple parser errors by newline. (https://github.com/ruby/syntax_suggest/pull/232)
4+
35
## 2.0.1
46

57
- Fix CLI failure when shipped with default gems. (https://github.com/ruby/syntax_suggest/pull/226 and https://github.com/ruby/syntax_suggest/pull/227)

lib/syntax_suggest/api.rb

+1
Original file line numberDiff line numberDiff line change
@@ -227,6 +227,7 @@ def self.valid?(source)
227227
require_relative "code_line"
228228
require_relative "code_block"
229229
require_relative "block_expand"
230+
require_relative "mini_stringio"
230231
require_relative "priority_queue"
231232
require_relative "unvisited_lines"
232233
require_relative "around_block_scan"

lib/syntax_suggest/core_ext.rb

-18
Original file line numberDiff line numberDiff line change
@@ -3,24 +3,6 @@
33
# Ruby 3.2+ has a cleaner way to hook into Ruby that doesn't use `require`
44
if SyntaxError.method_defined?(:detailed_message)
55
module SyntaxSuggest
6-
# Mini String IO [Private]
7-
#
8-
# Acts like a StringIO with reduced API, but without having to require that
9-
# class.
10-
class MiniStringIO
11-
def initialize(isatty: $stderr.isatty)
12-
@string = +""
13-
@isatty = isatty
14-
end
15-
16-
attr_reader :isatty
17-
def puts(value = $/, **)
18-
@string << value
19-
end
20-
21-
attr_reader :string
22-
end
23-
246
# SyntaxSuggest.module_for_detailed_message [Private]
257
#
268
# Used to monkeypatch SyntaxError via Module.prepend

lib/syntax_suggest/mini_stringio.rb

+24
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
module SyntaxSuggest
2+
# Mini String IO [Private]
3+
#
4+
# Acts like a StringIO with reduced API, but without having to require that
5+
# class.
6+
class MiniStringIO
7+
EMPTY_ARG = Object.new
8+
9+
def initialize(isatty: $stderr.isatty)
10+
@string = +""
11+
@isatty = isatty
12+
end
13+
14+
attr_reader :isatty
15+
def puts(value = EMPTY_ARG, **)
16+
if !value.equal?(EMPTY_ARG)
17+
@string << value
18+
end
19+
@string << $/
20+
end
21+
22+
attr_reader :string
23+
end
24+
end

spec/unit/mini_stringio_spec.rb

+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
# frozen_string_literal: true
2+
3+
require_relative "../spec_helper"
4+
5+
module SyntaxSuggest
6+
RSpec.describe "MiniStringIO" do
7+
it "#puts with no inputs" do
8+
io = MiniStringIO.new
9+
io.puts
10+
expect(io.string).to eq($/)
11+
end
12+
13+
it "#puts with an input" do
14+
io = MiniStringIO.new
15+
io.puts "Hello"
16+
expect(io.string).to eq(["Hello", $/].join)
17+
end
18+
19+
it "#puts with an input with a newline" do
20+
io = MiniStringIO.new
21+
io.puts "Hello\n"
22+
expect(io.string).to eq(["Hello\n", $/].join)
23+
end
24+
end
25+
end

0 commit comments

Comments
 (0)