Make directory path: Difference between revisions

From Rosetta Code
Content added Content deleted
(→‎{{header|Ruby}}: Added Ruby entry.)
(=={{header|Racket}}== implementation added)
Line 68: Line 68:
</lang>
</lang>


=={{header|Racket}}==

Uses `make-directory*` (NB the star -- that causes the intermediate directories to be produced).

Canonical documentation at http://docs.racket-lang.org/reference/Filesystem.html#%28def._%28%28lib._racket%2Ffile..rkt%29._make-directory*%29%29
<blockquote>Creates directory specified by _path_, creating intermediate
directories as necessary, and never failing if _path_ exists already.
</blockquote>

<lang racket>#lang racket
(define path-str "/tmp/woo/yay")
(define path/..-str "/tmp/woo")

;; clean up from a previous run
(when (directory-exists? path-str)
(delete-directory path-str)
(delete-directory path/..-str))
;; delete-directory/files could also be used -- but that requires goggles and rubber
;; gloves to handle safely!

(define (report-path-exists)
(printf "~s exists (as a directory?):~a~%~s exists (as a directory?):~a~%~%"
path/..-str (directory-exists? path/..-str)
path-str (directory-exists? path-str)))

(report-path-exists)

;; Really ... this is the only bit that matters!
(make-directory* path-str)

(report-path-exists)</lang>

{{out}}
<pre>"/tmp/woo" exists (as a directory?):#f
"/tmp/woo/yay" exists (as a directory?):#f

"/tmp/woo" exists (as a directory?):#t
"/tmp/woo/yay" exists (as a directory?):#t

</pre>


=={{header|JavaScript}}==
=={{header|JavaScript}}==

Revision as of 08:35, 12 August 2014

Task
Make directory path
You are encouraged to solve this task according to the task description, using any language you may know.

Create a directory and any missing parents.

This task is named after the posix mkdir -p command, and several libraries which implement the same behavior.

Please implement a function of a single path string (for example ./path/to/dir) which has the above side-effect. If the directory already exists, return successfully. Ideally implementations will work equally well cross-platform (on windows, linux, and OS X).

It's likely that your language implements such a function as part of its standard library. If so, please also show how such a function would be implemented.


Go

The standard packages include os.MkdirAll which does exactly this (and its source is also available via that link). <lang go> os.MkdirAll("/tmp/some/path/to/dir", 0770)</lang>

Perl 6

There is a builtin function with the same name and it creates subdirectories by default.

<lang perl6>mkdir 'path/to/dir'</lang>

Python

<lang Python> from errno import EEXIST from os import mkdir, curdir from os.path import split, exists

def mkdirp(path, mode=0777):

   head, tail = split(path)
   if not tail:
       head, tail = split(head)
   if head and tail and not exists(head):
       try:
           mkdirp(head, mode)
       except OSError as e:
           # be happy if someone already created the path
           if e.errno != EEXIST:
               raise
       if tail == curdir:  # xxx/newdir/. exists if xxx/newdir exists
           return
   try:
       mkdir(path, mode)
   except OSError as e:
       # be happy if someone already created the path
       if e.errno != EEXIST:
           raise

</lang>

Above is a modified version of the standard library's os.makedirs, for pedagogical purposes. In practice, you would be more likely to use the standard library call:

<lang Python> def mkdirp(path):

   try:
       os.makedirs(path)
   except OSError as exc: # Python >2.5
       if exc.errno == errno.EEXIST and os.path.isdir(path):
           pass
       else: raise

</lang>

In Python3 this becomes even simpler:

<lang Python> def mkdirp(path):

   os.makedirs(path, exist_ok=True)

</lang>

Racket

Uses `make-directory*` (NB the star -- that causes the intermediate directories to be produced).

Canonical documentation at http://docs.racket-lang.org/reference/Filesystem.html#%28def._%28%28lib._racket%2Ffile..rkt%29._make-directory*%29%29

Creates directory specified by _path_, creating intermediate

directories as necessary, and never failing if _path_ exists already.

<lang racket>#lang racket (define path-str "/tmp/woo/yay") (define path/..-str "/tmp/woo")

clean up from a previous run

(when (directory-exists? path-str)

 (delete-directory path-str)
 (delete-directory path/..-str))
delete-directory/files could also be used -- but that requires goggles and rubber
gloves to handle safely!

(define (report-path-exists)

 (printf "~s exists (as a directory?):~a~%~s exists (as a directory?):~a~%~%"
         path/..-str (directory-exists? path/..-str)
         path-str (directory-exists? path-str)))

(report-path-exists)

Really ... this is the only bit that matters!

(make-directory* path-str)

(report-path-exists)</lang>

Output:
"/tmp/woo" exists (as a directory?):#f
"/tmp/woo/yay" exists (as a directory?):#f

"/tmp/woo" exists (as a directory?):#t
"/tmp/woo/yay" exists (as a directory?):#t

JavaScript

Works with: Node.js

Simplified version of the popular mkdirp library:

<lang Javascript>var path = require('path'); var fs = require('fs');

function mkdirp (p, cb) {

   cb = cb || function () {};
   p = path.resolve(p);
   fs.mkdir(p, function (er) {
       if (!er) {
           return cb(null);
       }
       switch (er.code) {
           case 'ENOENT':
               // The directory doesn't exist. Make its parent and try again.
               mkdirp(path.dirname(p), function (er) {
                   if (er) cb(er);
                   else mkdirp(p, cb);
               });
               break;
               // In the case of any other error, something is borked.
           default:
               cb(er);
               break;
       }
   });

}</lang>

Ruby

<lang ruby>require 'fileutils' FileUtils.mkdir_p("path/to/dir") </lang> mkdir_p also takes an array of pathnames instead of a single pathname as an argument.

REXX

The following works with any modern (Microsoft) Windows ® and/or DOS.


Operating system note:   all versions of Microsoft ® DOS require the use of a blackslash   [\]   instead of a forward slash   [/].

Usage note:   without the error messages being suppressed, the   MKDIR   command will issue an error message if the subdirectory (or its path) already exists. <lang rexx>/*REXX program creates a directory and all its parent paths as necessary*/ trace off /*suppress possible warning msgs.*/ dPath = 'path\to\dir' 'MKDIR' dPath "2>nul" /*alias could be used: MD Dpath */

                                      /*stick a fork in it, we're done.*/</lang>


UNIX Shell

Works with: Bourne Again SHell

<lang bash>function mkdirp() { mkdir -p "$1"; }</lang>

zkl

This is for Unix as zkl doesn't have a built in mkdir method. <lang zkl>System.cmd("mkdir -p ../foo/bar")</lang> The system error code is returned (0 in this case). <lang zkl>fcn mkdir(path) { System.cmd("mkdir -p "+path) }</lang>

Output:
zkl: mkdir("../foo/bar")
0
zkl: mkdir("/foo/bar")
mkdir: cannot create directory ‘/foo’: Permission denied
256