The sed command in Linux

sed (stream editor) transforms text as it flows through: its overwhelmingly common use is find-and-replace with the s command — sed 's/old/new/g'. Applied with -i it edits files in place, which makes it the standard tool for scripted config changes across servers. For anything more elaborate than substitution and line filtering, awk usually reads better.

How sed works

sed is a machine with a one-line buffer. For each input line: copy it into the pattern space, run every command of your script over that space in order, then (unless -n) print whatever the space holds and move on. All the commands — s for substitute, d for delete, p for print, plus line and regex addresses that gate them — operate on that single evolving line. One pass, no random access: a stream editor in the literal sense.

There is a second register, the hold space, that survives across lines — the mechanism behind the famous multi-line one-liners — but the everyday subtlety is elsewhere: -i does not edit "in place". sed writes a temporary file and renames it over the original, which means the file gets a new inode; hard links to it detach and, without care, permissions can shift. It is atomic and safe, but "in place" is a rename in disguise.

Syntax

sed [OPTIONS] 'COMMAND' [FILE...]

Common options

OptionWhat it does
s/old/new/Substitute the first match on each line.
s/old/new/gSubstitute every match on each line (g = global).
-iEdit the file in place instead of printing.
-i.bakIn-place, but keep a backup with the given extension first.
-n + pPrint only selected lines: sed -n "5,10p" shows lines 5–10.
/pattern/dDelete matching lines.
-EExtended regular expressions.

How to use sed: examples

$ sed 's/http:/https:/g' links.txt

Replace every http: with https: and print the result (file untouched).

$ sed -i 's/DEBUG=true/DEBUG=false/' .env

Edit a config file in place — the scripted-deployment staple.

$ sed -i.bak 's/localhost/db.internal/g' config.yml

Same, but keep config.yml.bak as a safety net.

$ sed -n '20,40p' app.log

Print only lines 20 through 40 of a file.

$ sed '/^#/d; /^$/d' nginx.conf

Strip comments and blank lines to read the effective configuration.

$ echo 'user_name' | sed -E 's/_(.)/\U\1/g'

Regex groups and case conversion: snake_case → camelCase (GNU sed).

Real-world use cases for sed

Config surgery across a fleet

Changing a setting on twenty servers: ssh each and run sed -i.bak "s/^worker_processes.*/worker_processes 8;/" /etc/nginx/nginx.conf. Anchored to the line start, in-place with backup — scripted config management before (and beneath) Ansible.

Mass-updating source code

A domain migration: grep -rl "old-cdn.example.com" src/ | xargs sed -i "s/old-cdn/new-cdn/g" rewrites every affected file in one pipeline. grep selects, xargs distributes, sed edits — a pattern worth keeping in your notes verbatim.

Pro tips and common mistakes

Frequently asked questions about sed

How do I replace text in a file with sed?

sed -i 's/old/new/g' file — s substitutes, g applies to all matches per line, -i writes the file in place. Test without -i first to preview the result.

How do I use a / inside the pattern?

Pick a different delimiter — sed accepts any character after s: sed "s|/var/www|/srv/web|g" avoids escaping every slash.

Why does sed -i behave differently on macOS?

BSD sed (macOS) requires an argument to -i, even empty: sed -i '' 's/a/b/' file. GNU sed (Linux) takes -i alone. Scripts meant for both should use -i.bak.

Related commands

grep

Find lines matching a pattern in files or piped input — the workhorse of text search.

awk

Pull columns out of any output, filter rows, and compute sums — the shell's spreadsheet.

cut

Slice fields or character ranges out of each line — quick column extraction for delimited data.

Want to build real fluency? The interactive course takes you through sed and every other essential command with guided, checked exercises.