7

I have this code

File.open(file_name, 'r') { |file| file.read }

but Rubocop is warning:

Offenses:

Style/SymbolProc: Pass &:read as argument to open instead of a block.

How do you do this?

Stefan
  • 109,145
  • 14
  • 143
  • 218
Obromios
  • 15,408
  • 15
  • 72
  • 127

3 Answers3

9

I just created a file named "t.txt" that contains "Hello, World\n". We can read that as follows.

File.open('t.txt', 'r', &:read)
  #=> "Hello, World\n"

Incidentally, as the default of the second argument is 'r', it suffices to write:

File.open('t.txt', &:read)

Here's another example:

"This is A Test".gsub('i', &:upcase)
  #=> "ThIs Is A Test" 

In other words, include the proc (e.g., &:read) as the last argument.

Stefan
  • 109,145
  • 14
  • 143
  • 218
Cary Swoveland
  • 106,649
  • 6
  • 63
  • 100
3

File.open(file_name, 'r', &:read)

Rubocop wants you to use the 'symbol to proc' feature in Ruby instead of defining a complete block. This is purely stylistic, and doesn't affect the code execution. You can find it in the Rubocop style guide.

Tom
  • 1,311
  • 10
  • 18
1

You can look up the offense in RuboCop's docs, e.g. Style/SymbolProc – it usually shows a "bad" and a "good" example:

# bad
something.map { |s| s.upcase }

# good
something.map(&:upcase)

If this doesn't help, you can have RuboCop auto-correct the offense (for cops supporting auto-correction like this one).

Given a file test.rb:

# frozen_string_literal: true

File.open(file_name, 'r') { |file| file.read }

Run rubocop -a: (the actual output depends on your config)

$ rubocop -a test.rb
Inspecting 1 file
C

Offenses:

test.rb:3:27: C: [Corrected] Style/SymbolProc: Pass &:read as an argument to open instead of a block.
File.open(file_name, 'r') { |file| file.read }
                          ^^^^^^^^^^^^^^^^^^^^

1 file inspected, 1 offense detected, 1 offense corrected

And test.rb will become:

# frozen_string_literal: true

File.open(file_name, 'r', &:read)
Stefan
  • 109,145
  • 14
  • 143
  • 218