Today you’ll learn how to read & write files in Ruby so you can extract the contents, create new files, and find the information you need!
Let’s do this!
How to Read Files In Ruby
You can read a file in Ruby like this:
- Open the file, with the
open
method. - Read the file, the whole file, line by line, or a specific amount of bytes.
- Close the file, with the
close
method.
Here is the process in detail.
Use the File
class to open a file:
file = File.open("users.txt")
As a result you’ll get a File
object, but not the contents of the file yet.
Now:
You can read the contents of the file in three ways.
First, you can read the whole file.
Like this:
file_data = file.read # "user1\nuser2\nuser3\n"
If you’re working with a file that has multiple lines you can either split
the file_data
, or use the readlines
method plus the chomp
method to remove the new line characters.
Example:
file_data = file.readlines.map(&:chomp) # ["user1", "user2", "user3"]
When you’re done working with a file you want to close
it to free up memory & system resources.
Like this:
file.close
As an alternative to having to open & close the file, you can use the File.read
method:
file_data = File.read("user.txt").split # ["user1", "user2", "user3"]
One more tip on reading files.
If you want to process a file one line at a time, you can use the foreach
method.
Example:
File.foreach("users.txt") { |line| puts line }
Instead of reading the whole file into memory you’ll be able to process the file one line at a time, which is useful for big files.
How to Write to a File in Ruby
If you want to write to a file using Ruby:
- Open the file in write mode (“w” flag)
- Use the
write
method to add data to the file - If you didn’t use the block version, remember to
close
Example:
File.open("log.txt", "w") { |f| f.write "#{Time.now} - User logged in\n" }
Important:
This will rewrite the previous file contents!
If you want to add new content to the file, use the “a” (append) flag, instead of the “w” (write) flag.
One shortcut is to use File.write
:
File.write("log.txt", "data...")
To use this method in append mode:
File.write("log.txt", "data...", mode: "a")
That’s the easiest way to write to a file in Ruby in just one line of code 🙂
One more thing…
If you want to write an array to a file you’ll have to convert it into a string first.
Here’s how:
File.write("log.txt", [1,2,3].join("\n"), mode: "a")
This process of converting an object into a string is called serialization.
Ruby File Methods
You can do other things with files, besides reading & writing to them.
For example, you may want to know if a file exists or to get a list of files for the current directory.
You are going to be using methods like:
- rename
- size
- exists?
- extname
- basename
- dirname
- directory?
- file?
Let’s see a few examples:
# Renaming a file File.rename("old-name.txt", "new-name.txt") # File size in bytes File.size("users.txt") # Does this file already exist? File.exists?("log.txt") # Get the file extension, this works even if the file doesn't exists File.extname("users.txt") # => ".txt" # Get the file name without the directory part File.basename("/tmp/ebook.pdf") # => "ebook.pdf" # Get the path for this file, without the file name File.dirname("/tmp/ebook.pdf") # => "/tmp" # Is this actually a file or a directory? File.directory?("cats")
The last example makes more sense if you are looping through the contents of a directory listing.
def find_files_in_current_directory entries = Dir.entries(".") entries.reject { |entry| File.directory?(entry) } end
You can also get stats for a file, like file size, permissions, creation date, etc:
File.stat("/tmp")
Directory Operations
Using Dir.glob you can get a list of all the files that match a certain pattern.
Here are some examples:
# All files in current directory Dir.glob("*") # All files containing "spec" in the name Dir.glob("*spec*") # All ruby files Dir.glob("*.rb")
This one line of code will recursively list all files in Ruby, starting from the current directory:
Dir.glob("**/**")
Use this if you only want to search for directories:
Dir.glob("**/**/")
Using the Dir class it’s also possible to print the current working directory:
Dir.pwd
Check if a directory is empty:
Dir.empty?("/tmp") # false
Check if a directory exists:
Dir.exists?("/home/jesus") # true
Create a new directory:
Dir.mkdir("/tmp/testing")
Create a temporary directory with mktmpdir:
Dir.mktmpdir do |dir| File.write(dir + "/log.txt", "test") end
How to Use The FileUtils Module
There are some extra file handling utilities you can get access to within the FileUtils module.
For example, you can compare files, touch a file (to update the last access & modification time), or copy files & directories with cp_r.
Like this:
require 'fileutils' FileUtils.compare_file("a.txt", "b.txt") FileUtils.touch("/tmp/lock") FileUtils.cp_r("data", "backup")
Btw the “r” in cp_r
stands for “recursive”.
Summary
You have learned how to manage files & folders in Ruby using built-in methods like File.read
& File.write
.
Thanks for reading!