python: get directory two levels up

PythonPathOperating SystemDirectory

Python Problem Overview


Ok...I dont know where module x is, but I know that I need to get the path to the directory two levels up.

So, is there a more elegant way to do:

import os
two_up = os.path.dirname(os.path.dirname(__file__))

Solutions for both Python 2 and 3 are welcome!

Python Solutions


Solution 1 - Python

You can use pathlib. Unfortunately this is only available in the stdlib for Python 3.4. If you have an older version you'll have to install a copy from PyPI here. This should be easy to do using pip.

from pathlib import Path

p = Path(__file__).parents[1]

print(p)
# /absolute/path/to/two/levels/up

This uses the parents sequence which provides access to the parent directories and chooses the 2nd one up.

Note that p in this case will be some form of Path object, with their own methods. If you need the paths as string then you can call str on them.

Solution 2 - Python

Very easy:

Here is what you want:

import os.path as path

two_up =  path.abspath(path.join(__file__ ,"../.."))

Solution 3 - Python

I was going to add this just to be silly, but also because it shows newcomers the potential usefulness of aliasing functions and/or imports.

Having written it, I think this code is more readable (i.e. lower time to grasp intention) than the other answers to date, and readability is (usually) king.

from os.path import dirname as up

two_up = up(up(__file__))

Note: you only want to do this kind of thing if your module is very small, or contextually cohesive.

Solution 4 - Python

The best solution (for python >= 3.4) when executing from any directory is:

from pathlib import Path
two_up = Path(__file__).resolve().parents[1]

Solution 5 - Python

For getting the directory 2 levels up:

 import os.path as path
 curr_dir=Path(os.path.dirname(os.path.abspath(__file__)))
 two_dir_up_=os.fspath(Path(curr_dir.parent.parent).resolve())

I have done the following to go up two and drill down on other dir

 default_config_dir=os.fspath(Path(curr_dir.parent.parent,
                                   'data/config').resolve()) 

Solution 6 - Python

Personally, I find that using the os module is the easiest method as outlined below. If you are only going up one level, replace ('../..') with ('..').

    import os
    os.chdir('../..')
    
--Check:
    os.getcwd()

Solution 7 - Python

More cross-platform implementation will be:

import pathlib
two_up = (pathlib.Path(__file__) / ".." / "..").resolve()

Using parent is not supported on Windows. Also need to add .resolve(), to:

>Make the path absolute, resolving all symlinks on the way and also normalizing it (for example turning slashes into backslashes under Windows)

Solution 8 - Python

(pathlib.Path('../../') ).resolve()

Solution 9 - Python

I have found that the following works well in 2.7.x

import os
two_up = os.path.normpath(os.path.join(__file__,'../'))

Solution 10 - Python

You can use this as a generic solution:

import os

def getParentDir(path, level=1):
  return os.path.normpath( os.path.join(path, *([".."] * level)) )

Solution 11 - Python

Assuming you want to access folder named xzy two folders up your python file. This works for me and platform independent.

".././xyz"

Solution 12 - Python

There is already an accepted answer, but for two levels up I think a chaining approach is arguably more readable:

pathlib.Path(__file__).parent.parent.resolve()

Solution 13 - Python

100% working answer:

os.path.abspath(os.path.join(os.getcwd() ,"../.."))

Solution 14 - Python

Surprisingly it seems no one has yet explored this nice one-liner option:

import os
two_up = os.path.normpath(__file__).rsplit(os.sep, maxsplit=2)[0]

rsplit is interesting since the maxsplit parameter directly represents how many parent folders to move up and it always returns a result in just one pass through the path.

Solution 15 - Python

With Pathlib (recommended after Python 3.5, the/a general solution that works not only in file.py files, but also in Jupyter (or other kind of) notebook and Python shell is:

p = Path.cwd().resolve().parents[1]

You only need to substitute (__file__) for cwd() (current working directory).

Indeed it would even work just with:

p = Path().resolve().parents[1]

(and of course with .parent.parent instead of parents[1])

Solution 16 - Python

I don't yet see a viable answer for 2.7 which doesn't require installing additional dependencies and also starts from the file's directory. It's not nice as a single-line solution, but there's nothing wrong with using the standard utilities.

import os

grandparent_dir = os.path.abspath(  # Convert into absolute path string
    os.path.join(  # Current file's grandparent directory
        os.path.join(  # Current file's parent directory
            os.path.dirname(  # Current file's directory
                os.path.abspath(__file__)  # Current file path
            ),
            os.pardir
        ),
        os.pardir
    )
)

print grandparent_dir

And to prove it works, here I start out in ~/Documents/notes just so that I show the current directory doesn't influence outcome. I put the file grandpa.py with that script in a folder called "scripts". It crawls up to the Documents dir and then to the user dir on a Mac.

(testing)AlanSE-OSX:notes AlanSE$ echo ~/Documents/scripts/grandpa.py 
/Users/alancoding/Documents/scripts/grandpa.py
(testing)AlanSE-OSX:notes AlanSE$ python2.7 ~/Documents/scripts/grandpa.py 
/Users/alancoding

This is the obvious extrapolation of the answer for the parent dir. Better to use a general solution than a less-good solution in fewer lines.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionjrammView Question on Stackoverflow
Solution 1 - PythonFfisegyddView Answer on Stackoverflow
Solution 2 - PythonSebi2020View Answer on Stackoverflow
Solution 3 - PythonandyhasitView Answer on Stackoverflow
Solution 4 - PythonpythinkerView Answer on Stackoverflow
Solution 5 - PythonzerocogView Answer on Stackoverflow
Solution 6 - Pythonuser4816510View Answer on Stackoverflow
Solution 7 - PythonzhukovgreenView Answer on Stackoverflow
Solution 8 - PythonAlexisView Answer on Stackoverflow
Solution 9 - PythonLucidiousView Answer on Stackoverflow
Solution 10 - PythonAxel HeiderView Answer on Stackoverflow
Solution 11 - Pythonuser11770816View Answer on Stackoverflow
Solution 12 - PythontekView Answer on Stackoverflow
Solution 13 - PythonJason AkonView Answer on Stackoverflow
Solution 14 - PythonglopesView Answer on Stackoverflow
Solution 15 - PythonMartinView Answer on Stackoverflow
Solution 16 - PythonAlanSEView Answer on Stackoverflow