How to Check if a File Exists in Python

What you’ll build or solve

You’ll check whether a file exists before you read, write, or delete it.

When this approach works best

Checking if a file exists works well when you:

  • Validate an input file before reading it, like data.json or a CSV export.
  • Skip work when an output file already exists, like a cached API response or a generated report.
  • Clean up files safely, like deleting old logs only if they’re there.

Skip this approach if you can rely on error handling instead. Catching FileNotFoundError can be simpler than checking first, especially in code that runs in parallel.

Prerequisites

  • Python 3 installed
  • You can run a Python script
  • You know what a file path is, relative vs absolute

Step-by-step instructions

1) Check a path with pathlib

pathlib is the most readable way to work with paths. Use .exists() to see if a path exists at all.

frompathlibimportPath

path=Path("data.json")

ifpath.exists():
print("Path exists")
else:
print("Path is missing")

What to look for: .exists() returns True for both files and folders. Step 2 shows how to check for a file specifically.


2) Confirm it’s a file, not a folder

If you need a real file, use .is_file().

frompathlibimportPath

path=Path("data.json")

ifpath.is_file():
print("File exists")
else:
print("Missing file, or path is a folder")

If you expect a folder instead, use .is_dir():

frompathlibimportPath

path=Path("logs")

ifpath.is_dir():
print("Folder exists")

What to look for: .is_file() returns False if the path doesn’t exist, so you usually don’t need a separate .exists() call.


3) Handle missing files without checking first

Sometimes you don’t need an existence check at all. Open the file and handle the error in one place.

Option A: Catch FileNotFoundError

try:
withopen("data.json","r",encoding="utf-8")asf:
text=f.read()
exceptFileNotFoundError:
text=None

Option B: Test first, then open

Useful when you want branching logic.

frompathlibimportPath

path=Path("data.json")

ifpath.is_file():
text=path.read_text(encoding="utf-8")
else:
text=None

What to look for: Error handling avoids a check-then-use gap, which matters if another process can delete the file between your check and your open.


Examples you can copy

Example 1: Read a file only if it exists

frompathlibimportPath

path=Path("notes.txt")

ifpath.is_file():
content=path.read_text(encoding="utf-8")
else:
content=""

Example 2: Create a file only if it’s missing

frompathlibimportPath

path=Path("config.json")

ifnotpath.exists():
path.write_text('{\n  "debug": false\n}\n',encoding="utf-8")

Example 3: Pick a fallback file if the main one is missing

frompathlibimportPath

primary=Path("data.json")
fallback=Path("data.sample.json")

path=primaryifprimary.is_file()elsefallback

data_text=path.read_text(encoding="utf-8")

Example 4: Check a file in the script’s folder

This helps when your working folder changes depending on how you run the script.

frompathlibimportPath

base=Path(__file__).parent
path=base/"data.json"

print(path.is_file())

Example 5: Check with os.path.exists() as an alternative

Some codebases use os.path instead of pathlib.

importos

ifos.path.exists("data.json"):
print("Exists")

If you need file-only behavior:

importos

ifos.path.isfile("data.json"):
print("File exists")

Common mistakes and how to fix them

Mistake 1: Using .exists() when you need a file

What you might do:

frompathlibimportPath

ifPath("logs").exists():
print("Ready to read logs")

Why it breaks: .exists() returns True for folders too, so your code may treat a directory like a file.

Correct approach:

frompathlibimportPath

ifPath("logs").is_file():
print("This is a file")
else:
print("Not a file")

Mistake 2: Checking first, then opening, and still crashing

What you might do:

frompathlibimportPath

path=Path("data.json")

ifpath.is_file():
text=path.read_text(encoding="utf-8")

Why it breaks: Another process can delete the file after the check. This is a race condition because the file’s state can change between check and use.

Correct approach:

frompathlibimportPath

path=Path("data.json")

try:
text=path.read_text(encoding="utf-8")
exceptFileNotFoundError:
text=None

Troubleshooting

If you see FileNotFoundError even after checking, wrap the read or open in try/except because files can disappear between steps.

If .is_file() returns False but the file exists, print the resolved path to confirm you’re checking the right location:

frompathlibimportPath
print(Path("data.json").resolve())

If your script behaves differently in an IDE vs terminal, anchor the path to the script folder with Path(__file__).parent.

If you see PermissionError, you may not have access to the folder, or the file may be locked by another app.


Quick recap

  • Use Path(...).exists() to check if a path exists at all.
  • Use Path(...).is_file() when you specifically need a file.
  • Use Path(...).is_dir() when you specifically need a folder.
  • Prefer try/except FileNotFoundError when the file might disappear between check and use.
  • Print Path(...).resolve() if you suspect you’re checking the wrong location.