haskell / haskell/directory

add a createDirectoryUnder

Open
#106 3 comments 0 reactions 0 assignees View on GitHub
type: (3) feature request
Dominant language
Haskell
Stars
65
Forks
52
PR merge metrics
No merged PRs in 30d

Description

createDirectoryIfMissing True is a larger hammer than called for under many circumstances, but by being the only one in this module, it is in my experience very easy to reach for it without much thought. I suggest adding an alternative such as:

createDirectoryUnder
:: FilePath --^ a top directory, which must already exist
-> FilePath --^ create this directory, and any missing intermediate directories before the top
-> IO ()

Here are some use cases for createDirectoryUnder:

* On Linux, it's common for removable drives to be mounted at eg, /media/user/foo. If a program that uses createDirectoryIfMissing True has been passed a directory under there, and is operating on it, when the removable drive gets disconnected, it will be unmounted, and the mount point removed. But, /media/user often remains, and is owned by the non-root user. So, the program may recreate /media/user/foo, and proceed with IO that was supposed to go to the removable drive. Data loss can result, things written there can prevent a later re-mount of the drive, etc.

* A program that has generated a temporary directory in a secure manner (eg mode 700) is writing to paths under /tmp/foo.pid/. If the user or some automated process decides to clean up /tmp while the program is still running, a later call to createDirectoryIfMissing True "/tmp/foo.pid/bar/baz" will re-create /tmp/foo.pid/, but in doing so it has opened a security hole; the directory's mode is no longer secure and an attacker can read files that the program writes there. (Other security holes are also possible.)

I have an implementation of createDirectoryUnder in git-annex, but relies on some other code from it, and probably gets some of the race conditions wrong that createDirectoryIfMissing deals with, so would be at best a hint at an implementation suitable for directory.

While implementing it, I found it made sense for it to throw an exception if the top directory does not exist, but not to create the top directory. It also makes sense for it to fail if the directory to be created is not actually located under the top directory. And, either or both directories can be relative (to the current directory, not one-another!), which complicates the implementation.

Contributor guide

Open the contributing guide

Research direction

Start by examining the module's existing createDirectoryIfMissing implementation and the git-annex createDirectoryUnder implementation mentioned in the issue. Done means adding an operation that creates missing directories below an existing top directory, rejects a missing top or a destination outside it, and handles relative paths and race conditions safely.

Written by the indexing model from the issue text.

Assessment

Tech stack
haskell
Domain
operating-systems
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
32/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.