Computer Programming 1 (JavaScript) • Data I/O & JSON

Basic File I/O — I can read/write simple text or data in a supported environment (Node fs or browser download) at my level.

Learn how JavaScript programs save and retrieve data using Node.js file system operations and browser downloads.

A JavaScript data file with code brackets and a laptop.
Inside this lesson 10 sections 5 questions 7 figures

SECTION 1

Historical Context & Motivation

Every useful program eventually needs to remember something. Whether it is a high score in a game, a list of contacts, or a journal entry, data has to be stored somewhere that survives after the program closes. This is the fundamental problem of persistence — keeping information around even when the power goes off or the browser tab closes. Without file I/O (short for Input/Output), programs would lose every piece of data the moment they stopped running.

The history of file I/O is tightly linked to the evolution of storage media and the languages that talk to them. Early computers used punch cards and magnetic tape; modern systems use solid-state drives and cloud storage. JavaScript, originally a browser-only language, had no built-in way to read or write files on a user's computer for security reasons. That changed dramatically when Node.js brought JavaScript to the server side, giving developers direct access to the file system through the fs module.

1956 • First Hard Disk Drive

IBM ships the RAMAC 305, the first computer with a hard disk. Programs can now read and write persistent files instead of relying solely on punch cards and tape.

1972 • C Language & stdio.h

The C programming language introduces standardized file I/O functions like fopen() and fwrite(), establishing patterns still used today.

1995 • JavaScript Is Born

Brendan Eich creates JavaScript for the Netscape browser. For security, it intentionally cannot access the user's file system.

2009 • Node.js Released

Ryan Dahl releases Node.js, bringing JavaScript to the server. The built-in fs module lets JavaScript read and write files for the first time.

2020s • Browser File APIs Mature

Modern browsers introduce the File System Access API and Blob-based downloads, allowing controlled file creation from client-side JavaScript.

This lesson answers a straightforward question: How do I get my JavaScript program to save data to a file and read it back later? We will explore two environments — Node.js on the server and the browser on the client — so you can choose the one that matches your current setup.

SECTION 2

Core Principles & Definitions

Before writing any code, it helps to understand the building blocks of file I/O. Regardless of the programming language, every file operation boils down to a small set of ideas. Once you learn these principles in JavaScript, they transfer directly to Python, Java, or any other language you study in the future.

1

File Path

The address of a file on disk, like ./data/notes.txt. Paths can be relative (starting from the current folder) or absolute (starting from the root of the drive).
2

Encoding

Files store bytes, not characters. An encoding (such as utf-8) is the rule that converts between bytes and human-readable text.
3

Read (Input)

Loading data from a file into your program's memory. In Node.js, this is done with fs.readFileSync() or fs.readFile().
4

Write (Output)

Saving data from your program's memory to a file. Use fs.writeFileSync() to create or overwrite a file, or fs.appendFileSync() to add to the end.
5

Synchronous vs. Asynchronous

Synchronous operations block the program until the file is done. Asynchronous operations let the program keep running while the file loads in the background. For beginners, synchronous is simpler.
✦

KEY TAKEAWAY

Think of file I/O like a notebook on your desk. Reading is opening the notebook and looking at what is written. Writing is picking up a pen and adding new text. The file path is the label on the notebook's spine that tells you which one to grab, and the encoding is the language the notebook is written in.

SECTION 3

Visual Explanation — The File I/O Flow

File I/O Data Flow in Node.jsYour Program(JavaScript / Node.js)Variables in RAMFile on Disknotes.txtPersistent bytesfs.writeFileSync(path, data)fs.readFileSync(path, 'utf-8')Step-by-Step: Writing Then Reading1Create datain a variable2CallwriteFileSync3File savedto disk ✓4CallreadFileSync5Data backin a variableThe data round-trips: variable → file → variable
The diagram shows the two main operations: writing sends data from your program to a file on disk, and reading brings it back. The bottom row shows the five-step round-trip that most file I/O programs follow.

In the diagram above, notice the clear separation between your program's memory (left box) and the file on disk (right box). When you call fs.writeFileSync(), Node.js converts the string in your variable into bytes and stores them on the hard drive. When you later call fs.readFileSync() with the 'utf-8' encoding, those bytes are decoded back into a JavaScript string you can use. This round-trip is the heart of basic file I/O.

SECTION 4

How It Works — The fs Module in Detail

Node.js includes a built-in module called fs (short for "file system"). You do not need to install anything — just require it at the top of your script. The module provides dozens of functions, but for beginning file I/O you only need three: readFileSync, writeFileSync, and appendFileSync. Each of these is a synchronous function, meaning your program pauses until the file operation finishes.

Importing the Module

At the very top of your JavaScript file, add: const fs = require('fs'); — this loads the file system module and stores it in a variable called fs. From that point on, you can call any method on the fs object.

Function Signatures

WRITE A FILE

fs.writeFileSync(filePath,dataString)fs.writeFileSync( filePath, dataString )

filePath — a string like 'output.txt' that names the file to create or overwrite. dataString — the text content to save.

READ A FILE

fs.readFileSync(filePath,′utf−8′)→stringfs.readFileSync( filePath, 'utf-8' ) → string

Returns the entire file content as a JavaScript string. The 'utf-8' argument tells Node how to decode the bytes into characters.

APPEND TO A FILE

fs.appendFileSync(filePath,newData)fs.appendFileSync( filePath, newData )

Adds newData to the end of the existing file instead of erasing it. Useful for log files and running totals.

⚠

Security Note

The browser intentionally prevents JavaScript from accessing your hard drive without permission. That is why fs only works in Node.js. In the browser, you can create a downloadable file using the Blob object and a temporary link — we cover that in Section 5.

SECTION 5

Node.js vs. Browser — Two Ways to Do File I/O

Because JavaScript runs in two very different environments, the technique you use to save a file depends on where your code executes. In Node.js, your script has direct access to the operating system's file system. In the browser, you cannot touch the file system directly, but you can generate a file in memory and prompt the user to download it. Both approaches produce real files; the difference is the amount of user interaction required.

Two Environments for JavaScript File I/ONode.js (Server)const fs = require('fs');fs.writeFileSync('hi.txt','Hello World');let data = fs.readFileSync('hi.txt', 'utf-8');✓ Direct disk access✓ No user interaction needed✓ Can read any file in pathBest for: scripts, servers,data processing, automationBrowser (Client)const blob = new Blob(['Hello World'], {type:'text/plain'});const url =URL.createObjectURL(blob);const a = document.createElement('a'); a.href=url; a.click();✗ No direct disk access✓ User downloads the file✓ Works in any browserBest for: web apps, exportingreports, saving user data
Node.js (left, green border) uses the fs module for direct disk access. The browser (right, amber border) creates a Blob and triggers a download link. Choose the approach that matches where your code runs.

Browser Download — Step by Step

When you are writing front-end code and want the user to save a file, you follow a three-step recipe. First, wrap your string data in a Blob (Binary Large Object) — this is JavaScript's way of representing a file in memory. Second, create a temporary URL that points to the Blob using URL.createObjectURL(blob). Third, create an invisible <a> link, set its href to that URL, give it a download attribute with a filename, and programmatically click it. The browser then downloads the file just as if the user had clicked a download button on a webpage.

SECTION 6

Worked Example — A Simple Note Saver

Let's build a tiny Node.js script that saves a note to a text file, reads it back, and appends a second line. This example uses only the synchronous versions of fs functions so the flow is easy to follow line by line.

Note Saver — Node.js

  1. 1

    Step 1 — Import the fs module

    At the top of a file called notes.js, write: const fs = require('fs');. This gives you access to all file system functions. No installation is needed because fs ships with Node.js.
  2. 2

    Step 2 — Write a file

    Create a variable with a message, then save it: const msg = 'Today I learned file I/O!'; followed by fs.writeFileSync('myNote.txt', msg);. After this line runs, a new file called myNote.txt appears in the same folder as your script.
    File myNote.txt created with content: "Today I learned file I/O!"
  3. 3

    Step 3 — Read the file back

    Now read the file into a new variable: const contents = fs.readFileSync('myNote.txt', 'utf-8'); The second argument 'utf-8' tells Node to return a readable string instead of raw bytes. Print it to confirm: console.log(contents);
    Console output: Today I learned file I/O!
  4. 4

    Step 4 — Append a second line

    Instead of overwriting, add to the end: fs.appendFileSync('myNote.txt', '\nIt was actually pretty easy.'); The \n inserts a newline character so the second note appears on its own line.
    File now contains two lines: "Today I learned file I/O!" and "It was actually pretty easy."
  5. 5

    Step 5 — Run the script

    Open a terminal, navigate to the folder with notes.js, and run node notes.js. Afterward, open myNote.txt in any text editor to see both lines.
    ✓ Script runs, file is created and updated on disk.

SECTION 7

Strengths, Limitations & Common Pitfalls

File I/O is powerful, but it comes with trade-offs. Understanding these will save you from frustrating bugs and help you pick the right tool for each situation.

AspectStrengthsLimitations / Pitfalls
SimplicityThree functions cover most basic needs. Very little setup required.Synchronous versions block the program. Not ideal for large files or web servers.
PersistenceData survives program restarts, computer reboots, and power outages.Files can be accidentally deleted or overwritten. No undo button.
PortabilityText files can be opened by any editor on any operating system.File paths differ between Windows (backslash) and Mac/Linux (forward slash).
Error HandlingNode throws clear error messages if a file is not found.Forgetting to wrap in try/catch can crash your entire program.
Data FormatWorks with plain text, CSV, JSON — any format that can be expressed as a string.Not suitable for binary files (images, audio) without extra handling.

Key strengths and limitations of basic file I/O in JavaScript

⚠

COMMON MISTAKE

The number-one beginner mistake is using writeFileSync when you meant appendFileSync. Writing overwrites the entire file — like erasing a whiteboard before writing something new. Appending adds to the bottom — like writing the next line in a journal. Always double-check which behavior you need before running your code.

SECTION 8

Connection to Advanced Topics

Basic file I/O is the foundation for many more advanced concepts you will encounter as you continue learning programming. Understanding how to read and write simple text files prepares you for working with structured data formats, databases, and network communication.

Basic File I/O (This Lesson)Advanced Concept (Future)
Reading/writing plain text with readFileSync / writeFileSyncAsynchronous I/O with fs.promises and async/await
Saving data as a raw stringStructured data with JSON.stringify() and JSON.parse()
One file at a time, manual pathReading directories, globbing patterns, and file watchers
Local text file storageDatabases (SQLite, MongoDB) for structured, queryable storage
Browser Blob downloadFetch API for reading/writing data over the network

How basic file I/O connects to advanced topics

The very next skill to learn after this lesson is JSON file I/O. Instead of saving a raw string, you will learn to convert JavaScript objects and arrays into JSON text with JSON.stringify(), save that text to a file, and later parse it back into a usable object with JSON.parse(). This pattern is used in almost every real-world application.

SECTION 9

Practice Problems

Question 1: CONCEPTUAL

Explain in your own words why a browser-based JavaScript program cannot use fs.writeFileSync() to save a file. What security problem would it cause if browsers allowed this?
Show answer
Browsers run JavaScript code from any website you visit. If that code could write directly to your hard drive, a malicious website could overwrite important system files, plant viruses, or steal data by reading files. The fs module is available only in Node.js because Node runs code that you choose to execute on your own computer, so you are in control. In the browser, you must use the Blob/download approach, which requires the user to explicitly approve each download.

Question 2: BASIC CALCULATION

Write a Node.js script that creates a file called greeting.txt containing the text "Hello, [your name]!". Then read the file back and print its contents to the console. Write out the exact lines of code you would use.
Show answer
The script requires three lines of functional code: const fs = require('fs'); to import the module, fs.writeFileSync('greeting.txt', 'Hello, Alex!'); to create the file, and console.log(fs.readFileSync('greeting.txt', 'utf-8')); to read it and print it. When run with node script.js, the console will display "Hello, Alex!" and a file named greeting.txt will exist in the current directory.

Question 3: INTERMEDIATE

You have a Node.js program that logs timestamps every time it runs. Write code that appends the current date and time as a new line to a file called log.txt each time the script executes. After running the script three times, what would the file contain?
Show answer
Use const fs = require('fs'); followed by fs.appendFileSync('log.txt', new Date().toISOString() + '\n');. The key choice here is appendFileSync instead of writeFileSync — append adds to the end, while write would erase the previous timestamps. After three runs, the file would contain three lines, each with an ISO timestamp like 2025-01-15T14:30:00.000Z. The '\n' ensures each timestamp is on its own line.

Question 4: APPLIED

A teacher wants a browser-based web page where students can type a short essay into a text area and click a button to download it as a .txt file. Describe the JavaScript steps (using Blob) that the button's click handler should perform. You do not need to write HTML, just the JavaScript logic.
Show answer
The click handler should: (1) get the essay text from the textarea using document.getElementById('essay').value; (2) create a Blob: const blob = new Blob([essayText], { type: 'text/plain' });; (3) generate a URL: const url = URL.createObjectURL(blob);; (4) create a temporary anchor element, set its href to the URL, set download = 'essay.txt', and call a.click(); (5) clean up with URL.revokeObjectURL(url). The browser will prompt the student to save the file.

Question 5: CRITICAL THINKING

Imagine you build a to-do list app in Node.js that stores tasks in a file called todos.txt. Each task is on a separate line. A user wants to delete the second task without affecting the others. Outline a strategy using only readFileSync and writeFileSync. What are the limitations of this approach compared to using a database?
Show answer
Strategy: (1) Read the entire file with readFileSync. (2) Split the string into an array of lines using .split('\n'). (3) Use .splice(1, 1) to remove the second element (index 1). (4) Join the array back with .join('\n') and write it back with writeFileSync. The limitation is that you must read and rewrite the entire file for every small change, which is slow for large files. A database can update a single record without touching the rest. Additionally, if the program crashes mid-write, the file could become corrupted, whereas databases use transactions to prevent data loss.

SUMMARY

Lesson Summary

Summary

In this lesson you learned how to perform basic file I/O in JavaScript across two environments. In Node.js, the built-in fs module provides writeFileSync to save data, readFileSync to load data (always with 'utf-8' encoding for text), and appendFileSync to add new content without erasing old content.

In the browser, direct file system access is blocked for security, so you create a Blob from your data and trigger a download. The core idea in both environments is the same: data moves from program memory to a persistent file and back again. Mastering this round-trip prepares you for JSON serialization, database operations, and network data transfer in future lessons.

Varsity Tutors • Computer Programming 1 (JavaScript) • Basic File I/O