Path.open
p.open(...) is open(p, ...). Use it in a with block when you need more than one-shot I/O: appending ('a'), reading line by line, exclusive creation ('x'), or binary streaming.
Common call
with p.open('a', encoding='utf-8') as f:
Returns
a file object
Replaces
open(str(p), …)
Watch out
Close it — use with; pass encoding= in text mode
Path.open(modemode — 'r', 'w', 'a', 'x', plus 'b' for binary and '+' for update — as for open().type: str · default: 'r'='r', bufferingbuffering — Buffer policy, as for open().type: int · default: -1=-1, encodingencoding — Text mode only. None = locale encoding.type: str | None · default: None=None, errorserrors — Text mode only: decoding error handler.type: str | None · default: None=None, newlinenewline — Text mode only: newline translation.type: str | None · default: None=None)
→ file object
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| mode | str | no ('r') | 'r', 'w', 'a', 'x', plus 'b' for binary and '+' for update — as for open(). |
| buffering | int | no (-1) | Buffer policy, as for open(). |
| encoding | str | None | no (None) | Text mode only. None = locale encoding. |
| errors | str | None | no (None) | Text mode only: decoding error handler. |
| newline | str | None | no (None) | Text mode only: newline translation. |
Return value
file object — The same object open() returns (TextIOWrapper, BufferedReader, …).
Common patterns
Append to a log
Mode 'a' creates the file if needed and writes at the end.
from pathlib import Path with Path('app.log').open('a', encoding='utf-8') as f: f.write('started\n')
Stream a large file line by line
Memory stays flat regardless of the file size.
from pathlib import Path with Path('access.log').open(encoding='utf-8') as f: errors = sum(1 for line in f if ' 500 ' in line)
CSV with the csv module
The csv module wants newline='' so it can handle line endings itself.
import csv from pathlib import Path with Path('out.csv').open('w', newline='', encoding='utf-8') as f: csv.writer(f).writerows(rows)
Examples
1. Write and read with open()
from pathlib import Path
p = Path('a.txt')
with p.open('w', encoding='utf-8') as f:
f.write('one\ntwo\n')
with p.open(encoding='utf-8') as f:
lines = [line.rstrip('\n') for line in f]
lines
Returns
['one', 'two']2. Append mode
from pathlib import Path
p = Path('log.txt')
for word in ['a', 'b']:
with p.open('a', encoding='utf-8') as f:
f.write(word)
p.read_text(encoding='utf-8')
Returns
'ab'3. Exclusive creation
from pathlib import Path
p = Path('lock')
p.touch()
p.open('x')
Returns
FileExistsError: [Errno 17] File exists: 'lock'4. Binary mode returns bytes
from pathlib import Path
p = Path('b.bin')
p.write_bytes(bytes([1, 2, 3]))
with p.open('rb') as f:
head = f.read(2)
head
Returns
b'\x01\x02'5. Same as the built-in open()
from pathlib import Path
p = Path('c.txt')
p.write_text('x', encoding='utf-8')
with p.open(encoding='utf-8') as f1, open(p, encoding='utf-8') as f2:
same = type(f1) is type(f2)
same
Returns
TruePitfalls
1. Forgetting to close the file
Data written without closing may still be in the buffer. A with block closes the file even on errors.
read before close
from pathlib import Path f = Path('x.txt').open('w', encoding='utf-8') f.write('data') seen = Path('x.txt').read_text(encoding='utf-8') f.close() seen
''
with block
from pathlib import Path with Path('x.txt').open('w', encoding='utf-8') as f: f.write('data') Path('x.txt').read_text(encoding='utf-8')
'data'
2. Opening a missing file for reading
Mode 'r' requires the file to exist; 'a' and 'w' create it.
'r'
from pathlib import Path Path('new.txt').open(encoding='utf-8')
FileNotFoundError: [Errno 2] No such file or directory: 'new.txt'
'a'
from pathlib import Path with Path('new.txt').open('a', encoding='utf-8') as f: pass Path('new.txt').exists()
True
When to use
Use it
- Appending, streaming, or modes x / r+ / binary
- Passing a file object to csv, json.dump, pickle …
Reach for something else
- Whole-file reads and writes → read_text / write_text / read_bytes / write_bytes
Notes
CPython impl
Lib/pathlib/_local.py: io.open(self, mode, buffering, encoding, errors, newline) after io.text_encoding(encoding) in text mode
Built-in
open() accepts a Path directly, so open(p) and p.open() are interchangeable
FAQ
Yes — it calls io.open with the path and the same arguments. Use whichever reads better; open(p) works because paths are os.PathLike.