PurePath.name

Four read-only properties on every path. They look only at the final component and only split at the LAST dot — so archive.tar.gz has the suffix .gz and the stem archive.tar.

pathlib attributePython 3.4+Live demo
Common call
p.stem, p.suffix # 'report', '.pdf'
Returns
strings — '' when there is nothing to return
Replaces
os.path.basename and os.path.splitext
Watch out
'.bashrc' has no suffix; 'a.tar.gz' has stem 'a.tar'
PurePath.name / .stem / .suffix / .suffixes
→ str | list[str]

Demo

Live evaluation
Try names with several dots, a leading dot, a trailing dot, or no name at all.
Try:
Inputs
pathstra path
Code
from pathlib import PurePosixPath
p = PurePosixPath('docs/report.pdf')
(p.name, p.stem, p.suffix, p.suffixes)
Result
('report.pdf', 'report', '.pdf', ['.pdf'])

suffix is the text from the last dot, but only when that dot is neither the first nor the last character of the name: ".bashrc" and "notes." have no suffix. suffixes first strips leading dots, then lists every ".part" — and returns [] for a name ending in a dot. The root "/" has an empty name, so every value is empty.

Common patterns

Group files by extension
Normalise the case of suffix before comparing.
from collections import Counter
from pathlib import Path
Counter(p.suffix.lower() for p in Path('.').iterdir() if p.is_file())
Strip every extension
stem only removes the last one; loop or use suffixes.
from pathlib import PurePosixPath
p = PurePosixPath('site.tar.gz')
base = p.name.removesuffix(''.join(p.suffixes))  # 'site'
Output file next to the input
Combine parent and stem to name a derived file.
from pathlib import Path
src = Path('photos/cat.jpeg')
thumb = src.parent / f'{src.stem}-thumb.webp'

Examples

1. Name of a file
from pathlib import PurePosixPath PurePosixPath('/var/log/syslog.1').name
Returns
'syslog.1'
2. Stem and suffix
from pathlib import PurePosixPath p = PurePosixPath('photos/cat.jpeg') (p.stem, p.suffix)
Returns
('cat', '.jpeg')
3. Double extensions
from pathlib import PurePosixPath p = PurePosixPath('site.tar.gz') (p.stem, p.suffix, p.suffixes)
Returns
('site.tar', '.gz', ['.tar', '.gz'])
4. A dotfile has no suffix
from pathlib import PurePosixPath p = PurePosixPath('.bashrc') (p.stem, p.suffix)
Returns
('.bashrc', '')
5. Folders have names too
from pathlib import PurePosixPath PurePosixPath('/usr/local/').name
Returns
'local'
6. ".." is a name
from pathlib import PurePosixPath PurePosixPath('a/..').name
Returns
'..'
7. Suffix keeps its case
from pathlib import PurePosixPath PurePosixPath('IMG_0042.JPG').suffix
Returns
'.JPG'

Pitfalls

1. Comparing suffixes case-sensitively
suffix is returned exactly as written, so ".JPG" != ".jpg". Lower-case it before comparing.
exact compare
from pathlib import PurePosixPath
PurePosixPath('IMG_0042.JPG').suffix == '.jpg'
False
.lower()
from pathlib import PurePosixPath
PurePosixPath('IMG_0042.JPG').suffix.lower() == '.jpg'
True
2. Using stem to remove all extensions
stem removes only the final suffix.
stem
from pathlib import PurePosixPath
PurePosixPath('data.tar.gz').stem
'data.tar'
split on the first dot
from pathlib import PurePosixPath
PurePosixPath('data.tar.gz').name.split('.', 1)[0]
'data'
3. Expecting a version number to be kept in the stem
Every dot counts: "app-1.2" has the suffix ".2".
version in name
from pathlib import PurePosixPath
PurePosixPath('app-1.2').suffix
'.2'
check against known suffixes
from pathlib import PurePosixPath
p = PurePosixPath('app-1.2')
p.suffix if p.suffix in {'.zip', '.tar', '.gz'} else ''
''

When to use

Use it
  • Getting the file name or extension of any path
  • Filtering files by type (p.suffix == ".csv")
  • Naming derived files (stem + new suffix)
Reach for something else
  • Changing the extension → with_suffix()
  • Detecting the real file type → read the content (e.g. mimetypes.guess_type is still name-based)

Notes

CPython impl
name is PurePath.name (the last parsed part); stem, suffix and suffixes are inherited from PurePathBase in Lib/pathlib/_abc.py
Rule
suffix = name[i:] where i = name.rfind("."), only if 0 < i < len(name) - 1
Changed in 3.14
A single trailing dot counts as a suffix from 3.14 on; in 3.13 and earlier "notes." has no suffix
Empty path
PurePosixPath('') and PurePosixPath('/') have name ''

FAQ

Path(p).stem. It removes only the last extension: Path('a.tar.gz').stem is 'a.tar'.