C'est drôle, je regardais cette page, mais je négligeais totalement le mot "parent" parce que je les pensais comme des enfants (de gauche à droite).
18
Protip: Dans certaines coquilles, vous pouvez même faire mkdir -p foo/{bar,baz}/zoo/andsoforth. Très utile!
Aaron Copley
1
Personnellement, j'ai également omis de mentionner "parent" dans la page de manuel car, eh bien, je pense que le drapeau devrait être "-r" pour "récursif" - ou tout au moins, il devrait y avoir un pseudonyme, car mkdir6 drapeaux documentés au total. Bon sang, j'ai l'impression que la commande devrait créer des répertoires de manière récursive par défaut, et si vous ne le souhaitez pas, vous devrez le spécifier explicitement.
Ils auraient pu faire -r à la place, comme toute autre commande, il est impossible de se rappeler des paramètres spécifiques pour chaque commande linux
Vedmant
2
Mais ce mkdir -pn'est pas cross-plateforme, ne fonctionne pas dans chaque shell
Роман Коптев
9
@ РоманКоптев, mkdir -pest spécifié dans POSIX , qui est la chose la plus proche d'être totalement portable. Que voulez-vous de mieux dans un script shell?
Wildcard
5
@StephanBijzitter Oui, c'est unix.se, pas unixandwindows.se. :)
EEAA
16
Utilisermkdir -p est un moyen simple pour la plupart des systèmes d’exploitation modernes:
mkdir -p foo/bar/zoo/andsoforth
Cependant, mkdir -pn'est pas recommandé dans de nombreux manuels. Lisez la documentation de GNU makeet autoconfsur les problèmes d'utilisation de mkdir -p:
Les systèmes d’installation et de configuration multiplate-forme ont leurs propres alternativesmkdir -p sûres pour .
CMake à utiliser en ligne de commande shell:
cmake -E make_directory foo/bar/zoo/andsoforth
Autoconf à utiliser dans un script avec prétraitement:
AS_MKDIR_P(foo/bar/zoo/andsoforth)
ou:
AC_PROG_MKDIR_P(foo/bar/zoo/andsoforth)
Mais ces solutions nécessitent cmakeou autoconf( M4) des outils à installer (et un prétraitement possible)
Vous pouvez également utiliser le install-shscript avec l' -doption:
install-sh -d foo/bar/zoo/andsoforth
Ce script est utilisé par autoconfet par automakeprojet. Je pense que ce doit être la solution la plus sûre.
À l'époque, je cherchais une solution multiplateforme pour des applications standard /bin/shsans dépendances, mais je n'en ai pas trouvé. J'ai donc écrit le prochain script qui n'est peut-être pas idéal, mais je pense qu'il est conforme à la plupart des exigences multi-plateformes :
#! /bin/sh
cdirname() # cross platform alternative for 'dirname'
{
# $1 - path
test $# -eq 1 || { echo "Procedure 'cdirname' must have only one parameter. Scripting error."; exit 1; }
echo "$1" | sed -n -e '1p' | sed -e 's#//*#/#g' -e 's#\(.\)/$#\1#' -e 's#^[^/]*$#.#' -e 's#\(.\)/[^/]*$#\1#' -
}
mkd() # cross platform alternative for 'mkdir -p'
{
# $1 - directory to create
test $# -eq 1 || { echo "Function 'mkd' can create only one directory (with it's parent directories)."; exit 1; }
test -d "$1" && return 0
test -d "$(cdirname "$1")" || { mkd "$(cdirname "$1")" || return 1; }
test -d "$1" || { mkdir "$1" || return 1; }
return 0
}
Ce script peut être utilisé pour les anciens systèmes, où l’option -ppour mkdirest absente.
sedUne version multiplateforme basée sur X a dirnameété ajoutée au code. Cela fonctionne avec une méthode similaire à dirname(correct avec chemin /, chemins avec nom de base uniquement, chemins avec fin /, chemins avec et sans fin \n). Cette fonction ne peut pas fonctionner correctement si le chemin contient des nouvelles lignes ou des caractères non valides pour les paramètres régionaux en cours. Il remplace également toute combinaison de /( //, ///) avec un seul/
Ligne modifiée mkdir "$1" || return 1en test -d "$1" || { mkdir "$1" || return 1; }raison de la mkdirfin de l'erreur si le chemin existe et que cette vérification est nécessaire pour les chemins contenant des constructions telles que aaa\.(Si la aaaversion précédente n'existe pas, la création est créée aaa, puis essaye de la recréer).
Cette version de mkd ne génère pas d'erreur si le chemin existe déjà (mais elle a toujours la possibilité de générer une telle erreur lors d'une exécution parallèle) et ne peut pas obtenir plusieurs répertoires en ligne de commande.
"mkdir -p" est défini par posix. Quelles variantes Unix ou Unix-like ne le supporte pas? (et ce ne devrait pas être un shell intégré, bien que je suppose qu'il n'y a aucune raison pour que ce ne soit pas le cas.) pubs.opengroup.org/onlinepubs/9699919799/utilities/mkdir.html
Tim B
5
Certaines des informations contenues dans cette page ont seulement 15 ans. Certains sont plus âgés.
Thomas Dickey
7
Les systèmes qui ne prendraient pas en charge mkdir -pseraient trop anciens (et nous parlons d’au moins deux décennies) pour avoir un printfutilitaire ou une assistance --permettant de marquer la fin des options.
Stéphane Chazelas
2
Votre cdirnameréponse serait incorrecte foo/bar//ou les noms de répertoires contenant des caractères de nouvelle ligne ou des caractères non valides dans les paramètres régionaux en cours.
Stéphane Chazelas
2
printfest sécurisé sur les systèmes POSIX. Prise en charge des systèmes POSIX mkdir -p. mkdir -pPOSIX le spécifie depuis des décennies. --a commencé à se généraliser sur les systèmes AT & T à partir de SysIII au début des années 80. printfest apparu pour la première fois en tant que kshcode intégré et a été spécifié par POSIX plus tard mkdir -p. Certains shells POSIX (comme pdksh ou yash) ne sont toujours pas printfintégrés.
Stéphane Chazelas
0
Option -pde commande mkdirfait p répertoires ARENT au besoin (pas d' erreur si existant):
mkdir -p foo/bar/zoo/andsoforth
Une autre méthode consiste, par exemple, à utiliser &&(erreur si le dossier spécifié existe):
L'opérateur de chaînage &&est utilisé pour chaîner des commandes, de telle sorte que la commande suivante soit exécutée si et seulement si la commande précédente s'est terminée sans erreur.
mkdir -p foo/{bar,baz}/zoo/andsoforth
. Très utile!mkdir
6 drapeaux documentés au total. Bon sang, j'ai l'impression que la commande devrait créer des répertoires de manière récursive par défaut, et si vous ne le souhaitez pas, vous devrez le spécifier explicitement.Réponses:
la source
mkdir -p
n'est pas cross-plateforme, ne fonctionne pas dans chaque shellmkdir -p
est spécifié dans POSIX , qui est la chose la plus proche d'être totalement portable. Que voulez-vous de mieux dans un script shell?Utiliser
mkdir -p
est un moyen simple pour la plupart des systèmes d’exploitation modernes:Cependant,
mkdir -p
n'est pas recommandé dans de nombreux manuels. Lisez la documentation de GNUmake
etautoconf
sur les problèmes d'utilisation demkdir -p
:Les systèmes d’installation et de configuration multiplate-forme ont leurs propres alternatives
mkdir -p
sûres pour .CMake à utiliser en ligne de commande shell:
Autoconf à utiliser dans un script avec prétraitement:
ou:
Mais ces solutions nécessitent
cmake
ouautoconf
(M4
) des outils à installer (et un prétraitement possible)Vous pouvez également utiliser le
install-sh
script avec l'-d
option:Ce script est utilisé par
autoconf
et parautomake
projet. Je pense que ce doit être la solution la plus sûre.À l'époque, je cherchais une solution multiplateforme pour des applications standard
/bin/sh
sans dépendances, mais je n'en ai pas trouvé. J'ai donc écrit le prochain script qui n'est peut-être pas idéal, mais je pense qu'il est conforme à la plupart des exigences multi-plateformes :Ce script peut être utilisé pour les anciens systèmes, où l’option
-p
pourmkdir
est absente.sed
Une version multiplateforme basée sur X adirname
été ajoutée au code. Cela fonctionne avec une méthode similaire àdirname
(correct avec chemin/
, chemins avec nom de base uniquement, chemins avec fin/
, chemins avec et sans fin\n
). Cette fonction ne peut pas fonctionner correctement si le chemin contient des nouvelles lignes ou des caractères non valides pour les paramètres régionaux en cours. Il remplace également toute combinaison de/
(//
,///
) avec un seul/
Ligne modifiée
mkdir "$1" || return 1
entest -d "$1" || { mkdir "$1" || return 1; }
raison de lamkdir
fin de l'erreur si le chemin existe et que cette vérification est nécessaire pour les chemins contenant des constructions telles queaaa\.
(Si laaaa
version précédente n'existe pas, la création est crééeaaa
, puis essaye de la recréer).Cette version de mkd ne génère pas d'erreur si le chemin existe déjà (mais elle a toujours la possibilité de générer une telle erreur lors d'une exécution parallèle) et ne peut pas obtenir plusieurs répertoires en ligne de commande.
la source
mkdir -p
seraient trop anciens (et nous parlons d’au moins deux décennies) pour avoir unprintf
utilitaire ou une assistance--
permettant de marquer la fin des options.cdirname
réponse serait incorrectefoo/bar//
ou les noms de répertoires contenant des caractères de nouvelle ligne ou des caractères non valides dans les paramètres régionaux en cours.printf
est sécurisé sur les systèmes POSIX. Prise en charge des systèmes POSIXmkdir -p
.mkdir -p
POSIX le spécifie depuis des décennies.--
a commencé à se généraliser sur les systèmes AT & T à partir de SysIII au début des années 80.printf
est apparu pour la première fois en tant queksh
code intégré et a été spécifié par POSIX plus tardmkdir -p
. Certains shells POSIX (comme pdksh ou yash) ne sont toujours pasprintf
intégrés.Option
-p
de commandemkdir
fait p répertoires ARENT au besoin (pas d' erreur si existant):Une autre méthode consiste, par exemple, à utiliser
&&
(erreur si le dossier spécifié existe):L'opérateur de chaînage
&&
est utilisé pour chaîner des commandes, de telle sorte que la commande suivante soit exécutée si et seulement si la commande précédente s'est terminée sans erreur.Bien sûr, le premier moyen est meilleur.
la source
Cela devrait le faire.
la source