wp_mkdir_p()WP 2.0.1

Recursive directory creation based on full path.

Will attempt to set permissions on folders.

1 time — 0.0002389 sec (fast) | 50000 times — 0.16 sec (very fast) | PHP 7.3.3, WP 5.2.3

No Hooks.

Return

true|false. Whether the path was created. True if path already exists.

Usage

wp_mkdir_p( $target );
$target(string) (required)
Full path to attempt to create.

Examples

0

#1 Directory Creation Demo

Suppose we need to create a nested directories:

if ( wp_mkdir_p( 'a/really/deep/sub/directory' ) ){
  echo 'Directory created!';
}
0

#2 Creating a directory inside /uploads

This example shows how to create a new folder in the /uploads directory, while activating the plugin.

It can be useful when the plugin has file import functions or the ability to upload files and you want to save all files to a specific folder.

function myplugin_activate() {

	$upload = wp_upload_dir();
	$upload_dir = $upload['basedir'] . '/mypluginfiles';

	if ( ! wp_mkdir_p( $upload_dir ) ){
		echo "Failed to create mypluginfiles directory";
	}
}

register_activation_hook( __FILE__, 'myplugin_activate' );

Changelog

Since 2.0.1 Introduced.

wp_mkdir_p() code WP 6.5.2

function wp_mkdir_p( $target ) {
	$wrapper = null;

	// Strip the protocol.
	if ( wp_is_stream( $target ) ) {
		list( $wrapper, $target ) = explode( '://', $target, 2 );
	}

	// From php.net/mkdir user contributed notes.
	$target = str_replace( '//', '/', $target );

	// Put the wrapper back on the target.
	if ( null !== $wrapper ) {
		$target = $wrapper . '://' . $target;
	}

	/*
	 * Safe mode fails with a trailing slash under certain PHP versions.
	 * Use rtrim() instead of untrailingslashit to avoid formatting.php dependency.
	 */
	$target = rtrim( $target, '/' );
	if ( empty( $target ) ) {
		$target = '/';
	}

	if ( file_exists( $target ) ) {
		return @is_dir( $target );
	}

	// Do not allow path traversals.
	if ( str_contains( $target, '../' ) || str_contains( $target, '..' . DIRECTORY_SEPARATOR ) ) {
		return false;
	}

	// We need to find the permissions of the parent folder that exists and inherit that.
	$target_parent = dirname( $target );
	while ( '.' !== $target_parent && ! is_dir( $target_parent ) && dirname( $target_parent ) !== $target_parent ) {
		$target_parent = dirname( $target_parent );
	}

	// Get the permission bits.
	$stat = @stat( $target_parent );
	if ( $stat ) {
		$dir_perms = $stat['mode'] & 0007777;
	} else {
		$dir_perms = 0777;
	}

	if ( @mkdir( $target, $dir_perms, true ) ) {

		/*
		 * If a umask is set that modifies $dir_perms, we'll have to re-set
		 * the $dir_perms correctly with chmod()
		 */
		if ( ( $dir_perms & ~umask() ) !== $dir_perms ) {
			$folder_parts = explode( '/', substr( $target, strlen( $target_parent ) + 1 ) );
			for ( $i = 1, $c = count( $folder_parts ); $i <= $c; $i++ ) {
				chmod( $target_parent . '/' . implode( '/', array_slice( $folder_parts, 0, $i ) ), $dir_perms );
			}
		}

		return true;
	}

	return false;
}