Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

A more intuitive fs.mkdtemp() #6142

Closed
sholladay opened this issue Apr 11, 2016 · 4 comments
Closed

A more intuitive fs.mkdtemp() #6142

sholladay opened this issue Apr 11, 2016 · 4 comments
Labels
doc Issues and PRs related to the documentations. feature request Issues that request new features to be added to Node.js. fs Issues and PRs related to the fs subsystem / file system.

Comments

@sholladay
Copy link
Contributor

sholladay commented Apr 11, 2016

  • Version: 5.10.1
  • Platform: Darwin 15.3.0
  • Subsystem: fs

I am happy that the Node team decided to implement fs.mkdtemp() - the security concerns around this behavior make me glad to see it in core.

However, the API feels awkward to me because:

  • The randomness it provides is hard coded to 6 characters, which is just enough that it's probably fine, but not enough that I don't want to add more.

  • Using the prefix argument sounds like a good way to add random characters, but doing half the work is strange if you read code that actually does this. Additionally, if I'm going to implement my own name pattern, I don't really want to also have to keep in mind the one Node is using. For example, should I have to re-implement the entire mkdtemp just to get valid UUIDv4 directory names? That is genuinely useful for unit tests and also for being able to easily mv the temporary directory to a cache-proof URL on my server without "renaming" it ... lest I have to undo the suffix every time or teach my client code about it.

  • Using prefix as a directory path is messy, What would you expect this code to do?

    'use strict';
    
    const os = require('os');
    const fs = require('fs');
    
    fs.mkdtemp(os.tmpdir(), (err, dir) => {
        if (err) {
            throw err;
        }
        console.log('Created directory:', dir);
    });

    If os.tmpdir() returns /tmp for you, that will actually create a directory at the very root of your filesystem, rather than inside of /tmp. And it will end up being named something like tmp-e0ew3m. To "fix" this you have to use path.join(os.tmpdir(), '/').

I would like to propose making the API more intuitive and useful for its intended purpose: unique, convenient, secure creation of temporary directories.

  1. Have an explicit cwd argument, which is internally path.join()'d with the name. This is so that the name can be computed in isolation. And to prevent accidentally creating directories out in the open, where they won't actually be cleaned up.
  2. Replace prefix with (or just add) a name option, which is used as-is when provided. Possibly increase the default randomness for the case where one is not provided. This makes it easy to opt-out of the pattern that Node happens to use currently, which is not exposed via any kind of constant (and I don't think that would provide much value, anyway).

I think these changes are best done as a breaking change, mainly to make the API less surprising. But compatibility could probably be maintained by only enabling these semantics on the options object.

@bnoordhuis
Copy link
Member

The randomness it provides is hard coded to 6 characters, which is just enough that it's probably fine, but not enough that I don't want to add more.

That's a limitation of libc's mkdtemp(3) implementation, which fs.mkdtemp() is a fairly thin binding to.

It's possible to implement it from scratch but then we miss out on platform-specific tweaks (which might be good for consistency but could be bad for security or interoperability.)

@bnoordhuis bnoordhuis added fs Issues and PRs related to the fs subsystem / file system. feature request Issues that request new features to be added to Node.js. labels Apr 11, 2016
@benjamingr
Copy link
Member

ping @ralt

@jasnell
Copy link
Member

jasnell commented Apr 22, 2016

I'm not sure if there's much more we should do other than improve the documentation to make this clearer. Providing a separate tmpdir argument would be inconsistent with the other fs methods and as @bnoordhuis points out there's little we can do as far as the randomness of the prefix. A PR that expands the documentation would be quite helpful!

@nodejs/documentation

@sholladay
Copy link
Contributor Author

... would be inconsistent with the other fs methods

I am not aware of any other fs methods that have this prefix argument / behavior. I am actually trying to propose something that is more consistent. Namely, I believe that passing os.tempdir() as the first argument should do something reasonable, as the other methods do (see my third bullet point).

Better API ideas aside, I found the current behavior awkward as a library author. I am willing to put up with my paths being misunderstood by the path module, but not by fs. It gets to walk to the filesystem, it needs to behave the same with or without a trailing slash.

jasnell added a commit to jasnell/node that referenced this issue May 17, 2016
Per: nodejs#6142

Clarify the prefix argument.

Fixes: nodejs#6142
Fishrock123 pushed a commit that referenced this issue May 23, 2016
Per: #6142

Clarify the prefix argument.

Fixes: #6142
PR-URL: #6800
Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl>
Reviewed-By: Roman Klauke <romaaan.git@gmail.com>
rvagg pushed a commit that referenced this issue Jun 2, 2016
Per: #6142

Clarify the prefix argument.

Fixes: #6142
PR-URL: #6800
Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl>
Reviewed-By: Roman Klauke <romaaan.git@gmail.com>
@sam-github sam-github added doc Issues and PRs related to the documentations. and removed doc Issues and PRs related to the documentations. labels Dec 1, 2016
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
doc Issues and PRs related to the documentations. feature request Issues that request new features to be added to Node.js. fs Issues and PRs related to the fs subsystem / file system.
Projects
None yet
Development

No branches or pull requests

5 participants