{"id":13902517,"url":"https://github.com/epogrebnyak/justpath","last_synced_at":"2025-04-04T13:12:00.328Z","repository":{"id":219413240,"uuid":"748975972","full_name":"epogrebnyak/justpath","owner":"epogrebnyak","description":"Inspect and refine PATH environment variable on Windows, Linux and MacOS.","archived":false,"fork":false,"pushed_at":"2024-06-06T10:24:40.000Z","size":181,"stargazers_count":346,"open_issues_count":11,"forks_count":11,"subscribers_count":3,"default_branch":"main","last_synced_at":"2025-03-28T12:09:08.216Z","etag":null,"topics":["command-line","environment-variables","environments","filesystem","path","python"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"gpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/epogrebnyak.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-01-27T07:54:35.000Z","updated_at":"2025-03-25T00:43:23.000Z","dependencies_parsed_at":"2024-01-27T11:50:06.932Z","dependency_job_id":"db681810-a4a6-4232-992b-c9414d6b88a9","html_url":"https://github.com/epogrebnyak/justpath","commit_stats":null,"previous_names":["epogrebnyak/what-the-path"],"tags_count":4,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/epogrebnyak%2Fjustpath","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/epogrebnyak%2Fjustpath/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/epogrebnyak%2Fjustpath/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/epogrebnyak%2Fjustpath/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/epogrebnyak","download_url":"https://codeload.github.com/epogrebnyak/justpath/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247182401,"owners_count":20897381,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["command-line","environment-variables","environments","filesystem","path","python"],"created_at":"2024-08-06T22:01:11.076Z","updated_at":"2025-04-04T13:12:00.309Z","avatar_url":"https://github.com/epogrebnyak.png","language":"Python","funding_links":[],"categories":["Python"],"sub_categories":[],"readme":"# justpath\n\n[![CI](https://github.com/epogrebnyak/justpath/actions/workflows/python-package.yml/badge.svg)](https://github.com/epogrebnyak/justpath/actions/workflows/python-package.yml)\n[![PyPI - Version](https://img.shields.io/pypi/v/justpath)](https://pypi.org/project/justpath/)\n[![Reddit][reddit_shield]](https://www.reddit.com/r/Python/comments/1aehs4i/clean_path_of_nonexistent_directories_with/)\n[![Hacker News][hn_logo]](https://news.ycombinator.com/item?id=39493363)\n[![Python Bytes](https://img.shields.io/badge/Python_Bytes-377-D7F9FF?logo=applepodcasts\u0026labelColor=blue)](https://www.youtube.com/watch?v=eWnYlxOREu4\u0026t=125s)\n\n[reddit_shield]: https://img.shields.io/badge/Reddit-%23FF4500.svg?style=flat\u0026logo=Reddit\u0026logoColor=white\n[hn_logo]: https://img.shields.io/badge/HackerNews-F0652F?logo=ycombinator\u0026logoColor=white\n\nJust a simple utility to explore `PATH` environment variable on Windows, Linux and MacOS.\n\n## Workflow\n\n`justpath` shows your `PATH` environment variable line by line with numbering, comments and highlighing and helps detecting invalid or duplicate directories on your `PATH`.\n\nYou can also create a modified version of `PATH` string and use it in your shell startup script or through an environment manager.\nNote that `justpath` itself cannot change your shell `PATH`.\n\n## Try quickly\n\nInstall (with pip or [pipx](#stable-version)):\n\n```console\npip install justpath\n```\n\nTry the following:\n\n```console\njustpath --raw\njustpath\njustpath --count\njustpath --invalid\njustpath --duplicates\njustpath --duplicates --follow-symlinks\njustpath --correct --string\n```\n\n## Screencast\n\n[![asciicast](https://asciinema.org/a/RjfqfUhcI4iJKNw55sSkuioU5.svg)](https://asciinema.org/a/RjfqfUhcI4iJKNw55sSkuioU5)\n\n## Basic usage\n\nWhat is the raw content of `PATH` string?\n\n```console\njustpath --raw\n```\n\nList directories in `PATH` line by line.\n\n```console\njustpath\n```\n\nSame as above, but no line numbers, no comments, no color, just bare text.\n\n```console\njustpath --bare\n```\n\nShow directories from PATH in alphabetic order[^1]:\n\n```console\njustpath --sort\n```\n\n[^1]: Sorting helps to view and analyze `PATH`. Do not put a sorted `PATH` back on your system as you will loose useful information about path resolution order.\n\nWhat are the paths that contain `bin` string?\n\n```console\njustpath --includes bin\n```\n\nWhat are the paths that do not contain `windows` string?\n\n```console\njustpath --excludes windows\n```\n\nAre there any directories in `PATH` that do not exist?\n\n```console\njustpath --invalid\n```\n\nAre there any duplicate directories in `PATH`?\n\n```console\njustpath --duplicates\n```\n\nSame, but resolving symbolic links:\n\n```console\njustpath --duplicates --follow-symlinks\n```\n\nWhat is the `PATH` without invalid paths and duplicates?\n\n```console\njustpath --purge-invalid --purge-duplicates\n```\n\nSame as above, but more concise:\n\n```console\njustpath --correct\n```\n\nA clean `PATH` string in OS-native format:\n\n```console\njustpath --correct --string\n```\n\nOne-line alternatives for `justpath` commands where they exist:\n\n```console\njustpath --shell-equivalents\n```\n\n## Useful cases\n\n### 1. Filter directory names\n\n`justpath` allows to filter paths that must or must not include a certain string.\nFiltering is case insensitive, `--includes windows` and `--includes Windows` will\nproduce the same result. `--excludes` flag will filter out the directories containing provided string.\n\n```console\nλ justpath --sort --includes windows --excludes system32\n39 C:\\Users\\Евгений\\AppData\\Local\\Microsoft\\WindowsApps\n24 C:\\WINDOWS\n14 C:\\Windows\n46 C:\\tools\\Cmder\\vendor\\git-for-windows\\cmd\n47 C:\\tools\\Cmder\\vendor\\git-for-windows\\mingw64\\bin\n12 C:\\tools\\Cmder\\vendor\\git-for-windows\\usr\\bin\n```\n\n### 2. Directory does not exist or not a directory\n\n`justpath` will indicate if path does not exist or path is not a directory.\n\nBelow is an example from Github Codespaces, for some reason\n`/usr/local/sdkman/candidates/ant/current/bin` does not exist,\nbut included in `PATH`.\n\n```console\nλ justpath --sort --includes sdkman\n19 /usr/local/sdkman/bin\n23 /usr/local/sdkman/candidates/ant/current/bin (directory does not exist)\n21 /usr/local/sdkman/candidates/gradle/current/bin\n20 /usr/local/sdkman/candidates/java/current/bin\n22 /usr/local/sdkman/candidates/maven/current/bin\n```\n\nAdded file `touch d:\\quarto\\this_is_a_file` for example below.\n\n```console\nλ justpath --includes quarto\n33 C:\\Program Files\\Quarto\\bin\n41 D:\\Quarto\\bin\n50 x:\\quarto\\does_not_exist (directory does not exist)\n51 d:\\quarto\\this_is_a_file (not a directory)\n```\n\nUse `--invalid` flag to explore what parts of PATH do not exist or not a directory.\n\n```console\nλ justpath --includes quarto --invalid\n50 x:\\quarto\\does_not_exist (directory does not exist)\n51 d:\\quarto\\this_is_a_file (not a directory)\n```\n\n### 3. Purge incorrect paths\n\n`--correct` flag will drop invalid paths from listing.\n\n```console\nλ justpath --includes quarto --correct\n33 C:\\Program Files\\Quarto\\bin\n41 D:\\Quarto\\bin\n```\n\n`--correct` flag is the same as applying both `--purge-invalid` and `--purge-duplicates`\nflag. The duplicates are purged from the end of a string.\n\nYou may also add `--follow-symlinks` flag in order to resolve symbolic links\nwhen counting and purging duplicate directories.\n\n### 4. Dump `PATH` as JSON\n\n`justpath` can dump a list of paths from `PATH` to JSON.\nYou may add `--correct` flag to list only correct paths.\n\n```\njustpath --correct --json\n```\n\n### 5. Create new content string for `PATH`\n\nWith `justpath` you can create new `PATH` contents and use it in your shell startup script.\nAs any child process `justpath` itself cannot modify PATH in your current environment.\n\nYou can get a valid string for your PATH in a format native to your operating system\nusing `--string` ouput flag.\n\n```console\nλ justpath --correct --string\nC:\\tools\\Cmder\\bin;C:\\tools\\Cmder\\vendor\\bin;C:\\Windows\\system32;C:\\Windows;...\n```\n\n### 6. Count directories in `PATH`\n\n```console\nλ justpath --count\n52 directories in your PATH\n1 does not exist\n16 duplicates\n```\n\n```\nλ justpath --count --json\n{\"total\": 52, \"invalid\": 1, \"duplicates\": 16}\n```\n\n### 7. Follow symlinks when looking for duplicates\n\nOften times symbolic links are added to `PATH` to point to a particular version\nof a package. You can discover more duplicate directories with `--follow-symlinks` flag.\n\n```console\n$ justpath --duplicates --follow-symlinks --includes dotnet\n 6 /home/codespace/.dotnet (resolves to /usr/local/dotnet/7.0.306, duplicates: 2)\n32 /usr/local/dotnet/current (resolves to /usr/local/dotnet/7.0.306, duplicates: 2)\n\n$ justpath --duplicates --follow-symlinks --includes java\n10 /home/codespace/java/current/bin (resolves to /usr/local/sdkman/candidates/java/21.0.1-ms/bin, duplicates: 2)\n19 /usr/local/sdkman/candidates/java/current/bin (resolves to /usr/local/sdkman/candidates/java/21.0.1-ms/bin, duplicates: 2)\n```\n\n## Installation\n\n### Stable version\n\n```console\npip install justpath\n```\n\nor with [pipx](https://github.com/pypa/pipx)\n\n```console\npipx install justpath\n```\n\n### Development version\n\n```console\ngit clone https://github.com/epogrebnyak/justpath.git\ncd justpath\npip install -e .\n```\n\nor shorter:\n\n```console\npip install git+https://github.com/epogrebnyak/justpath.git\n```\n\n### Other package managers \n\nInstallation via conda or homebrew not yet supported.\n\n## CLI tool\n\nAfter installation you can try the command line script:\n\n```\njustpath --help\n```\n\n## Motivation\n\nI think [this quote][quote] about `PATH` is quite right:\n\n\u003e I always get the feeling that nobody knows what a PATH is and at this point they are too afraid to ask.\n\n[quote]: https://www.reddit.com/r/linuxquestions/comments/pgv7hm/comment/hbf3bno/\n\n`PATH` environment variable syntax on Windows and on Linux are different,\nso I wrote this utility to be able to explore `PATH` more easily.\n\nMy own use case for `justpath` was exploring and sanitizing the `PATH` on Windows together with Rapid Environment Editor.\nI also find it useful to inspect `PATH` on a remote enviroment like Codespaces to detect invalid paths.\n\n## Feedback\n\nSome of positive feedback I got about the `justpath` package:\n\n\u003e I like it! I do the steps involved in this occasionally, manually.\n\u003e It's not hard but this makes it nice.\n\u003e Not sure I'll use it since it is one more thing to install and remember,\n\u003e but the author had an itch and scratched it. Well done.\n\n\u003e It's handy to see your path entries in a list.\n\u003e Checking whether each entry is a valid location is neat, too.\n\u003e But even better, from my perspective, you published the code and got feedback from people,\n\u003e including related implementations. That’s worth it, in my book.\n\u003e Edit: I like the includes part, too.\n\n\u003e I think this is a cool package.\n\u003e Some of my first scripts in several languages have just been messing with file system abstractions.\n\u003e Files and file paths are much more complex than most people think.\n\n\n## Development notes\n\n### More about `PATH`\n\nSee [links.md](docs/links.md) for more information about `PATH`.\n\n### Making of command line interfaces (CLIs)\n\nFew good links about CLI applications in general:\n\n- [docopt](http://docopt.org/) is a great package to develop intuition about command line interfaces.\n- [clig](https://clig.dev/) - ton of useful suggestions about CLIs including expected standard flags (`--silent`, `--json`, etc).\n- [12 factor CLI app](https://panlw.github.io/15394417631263.html) - cited by `clig`.\n\n## Alternatives\n\n### Linux scripting\n\nOn Linux you can run `echo $PATH | tr \";\" \"\\n\"` to view your path line by line and\ncombine it with `grep`, `sort`, `uniq` and `wc -l` for the similar effect\nas `justpath` commands.\n\nThe benefit of a script is that you do not need to install any extra dependency.\nThe drawback is that not everyone is good at writing bash scripts.\nScripting would also be a bit more problematic on Windows.\n\nCheck out the discussion at [Hacker News](https://news.ycombinator.com/item?id=39493363)\nabout bash and zsh scripts and `justpath` scenarios.\n\n\u003e [!TIP]\n\u003e `justpath --shell-equivalents` provides a reference about one line commands for several shells that do similar jobs as `justpath` itself.\n\n### Other utilities\n\nEven better tools than `justpath` may exist.\n\n- [Rapid Environment Editor](https://www.rapidee.com/en/path-variable) for Windows\n  is a gem (no affiliation).\n- Maybe some smart command-line utility in Rust will emerge for PATH specifically,\n  but [not there yet](https://gist.github.com/sts10/daadbc2f403bdffad1b6d33aff016c0a).\n- There is [pathdebug](https://github.com/d-led/pathdebug) written in Go\n  that goes a step futher and attempts to trace where your PATH is defined.\n- There is a family of tools to manage environment paths\n  like [dotenv](https://github.com/motdotla/dotenv) or its Python port, and a newer tool called [envio](https://github.com/envio-cli/envio) written in Rust.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fepogrebnyak%2Fjustpath","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fepogrebnyak%2Fjustpath","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fepogrebnyak%2Fjustpath/lists"}