Read binary file as string in Ruby

RubyStringFile Io

Ruby Problem Overview


I need an easy way to take a tar file and convert it into a string (and vice versa). Is there a way to do this in Ruby? My best attempt was this:

file = File.open("path-to-file.tar.gz")
contents = ""
file.each {|line|
  contents << line
}

I thought that would be enough to convert it to a string, but then when I try to write it back out like this...

newFile = File.open("test.tar.gz", "w")
newFile.write(contents)

It isn't the same file. Doing ls -l shows the files are of different sizes, although they are pretty close (and opening the file reveals most of the contents intact). Is there a small mistake I'm making or an entirely different (but workable) way to accomplish this?

Ruby Solutions


Solution 1 - Ruby

First, you should open the file as a binary file. Then you can read the entire file in, in one command.

file = File.open("path-to-file.tar.gz", "rb")
contents = file.read

That will get you the entire file in a string.

After that, you probably want to file.close. If you don’t do that, file won’t be closed until it is garbage-collected, so it would be a slight waste of system resources while it is open.

Solution 2 - Ruby

If you need binary mode, you'll need to do it the hard way:

s = File.open(filename, 'rb') { |f| f.read }

If not, shorter and sweeter is:

s = IO.read(filename)

Solution 3 - Ruby

To avoid leaving the file open, it is best to pass a block to File.open. This way, the file will be closed after the block executes.

contents = File.open('path-to-file.tar.gz', 'rb') { |f| f.read }

Solution 4 - Ruby

how about some open/close safety.

string = File.open('file.txt', 'rb') { |file| file.read }

Solution 5 - Ruby

on os x these are the same for me... could this maybe be extra "\r" in windows?

in any case you may be better of with:

contents = File.read("e.tgz")
newFile = File.open("ee.tgz", "w")
newFile.write(contents)

Solution 6 - Ruby

Ruby have binary reading

data = IO.binread(path/filaname)

or if less than Ruby 1.9.2

data = IO.read(path/file)

Solution 7 - Ruby

You can probably encode the tar file in Base64. Base 64 will give you a pure ASCII representation of the file that you can store in a plain text file. Then you can retrieve the tar file by decoding the text back.

You do something like:

require 'base64'

file_contents = Base64.encode64(tar_file_data)

Have look at the Base64 Rubydocs to get a better idea.

Solution 8 - Ruby

Ruby 1.9+ has IO.binread (see @bardzo's answer) and also supports passing the encoding as an option to IO.read:

  • Ruby 1.9

    data = File.read(name, {:encoding => 'BINARY'})
    
  • Ruby 2+

    data = File.read(name, encoding: 'BINARY')
    

(Note in both cases that 'BINARY' is an alias for 'ASCII-8BIT'.)

Solution 9 - Ruby

If you can encode the tar file by Base64 (and storing it in a plain text file) you can use

File.open("my_tar.txt").each {|line| puts line}

or

File.new("name_file.txt", "r").each {|line| puts line}

to print each (text) line in the cmd.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionChris BunchView Question on Stackoverflow
Solution 1 - RubyDavid NehmeView Answer on Stackoverflow
Solution 2 - RubyCurt SampsonView Answer on Stackoverflow
Solution 3 - RubyAaron HinniView Answer on Stackoverflow
Solution 4 - RubyAlexView Answer on Stackoverflow
Solution 5 - RubyPurfideasView Answer on Stackoverflow
Solution 6 - RubybardzoView Answer on Stackoverflow
Solution 7 - Rubycomctrl6View Answer on Stackoverflow
Solution 8 - RubyDavid MolesView Answer on Stackoverflow
Solution 9 - RubyBorisView Answer on Stackoverflow