Lua Academy · Lesson

Opening Files with io.open

Open files in read, write, and append modes using io.open.

Lesson 1 of 412 steps

Opening Files with io.open is a free Lua Academy lesson on CoddyKit. This is lesson 1 of 4. Any 3 lessons of this learning path are free to read in full — after that, CoddyKit PRO unlocks every lesson, plus hands-on practice with a built-in code editor and a 24/7 AI tutor. It is part of the Lua Academy learning path, and your progress syncs across the web and the CoddyKit app. The Lua Academy course includes 4 lessons in total.

io.open Syntax

io.open(filename, mode) opens a file and returns a file handle, or nil plus an error message on failure. Mode strings: "r" read (default), "w" write (truncate), "a" append, "r+" read/write, "b" suffix for binary.

local f, err = io.open("test.txt", "w")
if not f then
  print("Error:", err)
  return
end
f:write("Hello, Lua!\n")
f:close()
print("Written successfully")

Read Mode

Open in "r" mode to read an existing file. Always check for nil — if the file doesn't exist, io.open returns nil and an error message. Never assume the file is there.

local f, err = io.open("test.txt", "r")
if not f then
  print("Cannot open:", err)
  return
end
local content = f:read("*a")  -- read all
f:close()
print(content)

Write and Append Modes

"w" creates or truncates the file. "a" creates the file if needed and always appends to the end. Use append mode for log files where you don't want to lose previous content.

-- Write (creates/truncates)
local f = io.open("log.txt", "w")
f:write("Session started\n")
f:close()

-- Append (adds to end)
local g = io.open("log.txt", "a")
g:write("Event: login\n")
g:write("Event: action\n")
g:close()

Binary Mode

Append "b" to any mode for binary reading/writing. On Unix, text and binary modes are identical. On Windows, text mode translates \n to \r\n; binary mode disables this. Always use binary mode for non-text files.

-- Binary read
local f = io.open("image.png", "rb")
if f then
  local header = f:read(8)   -- read 8 bytes
  f:close()
  -- Check PNG magic number: \137PNG\r\n\26\n
  print("Read", #header, "bytes")
end

-- Binary write
local g = io.open("out.bin", "wb")
if g then
  g:write(string.char(0x89, 0x50, 0x4E, 0x47))
  g:close()
end

File Handle Methods

A file handle (returned by io.open) has methods: f:read(...), f:write(...), f:lines(), f:seek(whence, offset), f:flush(), f:close(). Call them with colon syntax on the handle.

local f = io.open("data.txt", "w")
f:write("line 1\n")
f:write("line 2\n")
f:write("line 3\n")
f:flush()   -- force write to disk
f:close()

local g = io.open("data.txt", "r")
for line in g:lines() do
  print(line)
end
g:close()

io.input and io.output

io.input(f) sets the default input file; io.output(f) sets the default output. io.read() reads from the current input; io.write() writes to current output. Default input is stdin; default output is stdout.

-- Read from stdin (default input)
local line = io.read()  -- reads one line
print("You entered:", line)

-- Set default output to a file
io.output("out.txt")
io.write("This goes to out.txt\n")
io.output(io.stdout)  -- restore stdout

Checking File Existence

Lua has no file.exists(), but you can use io.open in read mode — if it fails, the file doesn't exist (or is inaccessible). Alternatively, on POSIX systems use os.execute or the lfs library.

local function fileExists(path)
  local f = io.open(path, "r")
  if f then f:close(); return true end
  return false
end

print(fileExists("test.txt"))     -- true/false
print(fileExists("noexist.txt"))  -- false

Reading with Modes

f:read() accepts format strings: "l" or "*l" reads one line (strips newline); "L" keeps newline; "n" reads a number; "a" or "*a" reads to EOF; a number reads that many bytes.

local f = io.open("data.txt", "r")
if f then
  local line1 = f:read("l")   -- first line, no newline
  local num   = f:read("n")   -- next number in file
  local rest  = f:read("a")   -- rest of file
  f:close()
  print(type(line1), type(num))
end

Temporary Files

io.tmpfile() opens a temporary file in read/write mode. The file is automatically deleted when the program exits or the handle is garbage collected. Use for intermediate processing without managing filenames.

local tmp = io.tmpfile()
tmp:write("temporary data\n")
tmp:write("more data\n")

-- Seek back to start and read
tmp:seek("set", 0)
local content = tmp:read("a")
print(content)
-- File auto-deleted when tmp is collected

Iterating Lines with lines()

f:lines() returns an iterator that reads one line at a time. It automatically closes the file when the iterator is exhausted. This is memory-efficient for large files — it never loads the whole file at once.

local function countLines(path)
  local count = 0
  local f, err = io.open(path, "r")
  if not f then return nil, err end
  for _ in f:lines() do
    count = count + 1
  end
  -- f is closed automatically by lines()
  return count
end

local n, err = countLines("data.txt")
print("Lines:", n)

Quick Check

What does io.open("file.txt", "a") do if the file does not exist?

Recap: io.open

Summary:

  • io.open(path, mode) returns handle or nil+error
  • Modes: r w a r+ b
  • Always check for nil before using the handle
  • Call f:close() when done
  • f:lines() for memory-efficient line iteration
  • io.tmpfile() for auto-deleted temp files
Free to start

Learn Lua with an AI tutor — free

Write and run real code in your browser, get instant help from a 24/7 AI tutor, and pick up where you left off on the web or in the app.

Courses
40
Lessons
159

Frequently Asked Questions

Is the “Opening Files with io.open” lesson free?

Yes — any 3 lessons of the Lua Academy learning path, including “Opening Files with io.open”, are free to read in full here on the web. After that, CoddyKit PRO unlocks every lesson, plus interactive practice with a built-in code editor and a 24/7 AI tutor. The Lua Academy course includes 4 lessons in total.

What will I learn in “Opening Files with io.open”?

Open files in read, write, and append modes using io.open. You practise Lua Academy with hands-on code you run directly in the browser, and a 24/7 AI tutor answers your questions as you work through the lesson.

Do I need any experience to start Lua Academy?

No prior experience is required. Lua Academy on CoddyKit is structured for beginners through advanced learners, so you can start here or from the beginning and move at your own pace. This is lesson 1 of 4.

How long does the “Opening Files with io.open” lesson take?

Most CoddyKit lessons take about 5–10 minutes. Each one is bite-sized and interactive, so you make steady progress and pick up exactly where you left off across the web and the app.

Can I write and run code in this Lua Academy lesson?

Yes. Every Lua Academy lesson includes a built-in code editor, so you write and run real code right in your browser and get instant AI feedback — no local setup required.

All lessons in this course

  1. Opening Files with io.open
  2. Reading File Contents
  3. Writing and Appending to Files
  4. Closing Files and Error Handling
← Back to Lua Academy