코딩 스쿨 PHP

언어선택 : HTMLCSSJAVAJAVASCRIPTMYSQLSQL PHP

PHP Directory

PHP 디렉토리 참조: 디렉토리 관리 및 조작


PHP 디렉토리 참조는 파일 시스템 내에서 디렉토리를 생성, 읽기, 수정, 삭제하는 데 사용되는 다양한 내장 함수들을 포괄합니다. PHP를 사용하면 웹 애플리케이션에서 디렉토리 구조를 동적으로 관리하고, 파일을 효율적으로 처리할 수 있습니다. 이 가이드는 PHP에서 디렉토리를 다루는 방법과 관련 함수들을 상세히 설명하며, 실용적인 예제를 통해 효과적인 디렉토리 관리를 도와드립니다.


1. PHP 디렉토리 함수 개요

PHP는 디렉토리를 효과적으로 관리하기 위해 다양한 내장 함수를 제공합니다. 이러한 함수들은 디렉토리의 생성, 삭제, 읽기, 수정 등을 가능하게 합니다. 주요 디렉토리 관련 함수들은 다음과 같습니다:

  • opendir(): 디렉토리를 열고 디렉토리 핸들을 반환합니다.
  • readdir(): 열린 디렉토리 핸들에서 다음 항목을 읽습니다.
  • closedir(): 열린 디렉토리를 닫습니다.
  • mkdir(): 새 디렉토리를 생성합니다.
  • rmdir(): 비어 있는 디렉토리를 삭제합니다.
  • scandir(): 디렉토리의 파일과 폴더 목록을 배열로 반환합니다.
  • glob(): 특정 패턴과 일치하는 파일 경로 목록을 반환합니다.
  • is_dir(), file_exists(), is_readable(), is_writable(): 디렉토리의 존재 여부와 속성을 확인합니다.
  • chmod(), chown(), chgrp(): 디렉토리의 권한과 소유권을 변경합니다.

이 함수들을 활용하면 디렉토리와 파일을 효율적으로 관리할 수 있으며, 웹 애플리케이션의 파일 구조를 동적으로 조작할 수 있습니다.


2. 디렉토리 열기 및 닫기

디렉토리를 열고, 디렉토리 내의 파일과 폴더를 읽고, 디렉토리를 닫는 과정은 다음과 같은 함수들을 통해 이루어집니다.

2.1 opendir()

opendir() 함수는 지정된 경로의 디렉토리를 열고 디렉토리 핸들을 반환합니다. 디렉토리를 열 때는 해당 디렉토리가 존재하고 읽기 가능한지 확인해야 합니다.

예시: 디렉토리 열기

<?php
$dirPath = "/path/to/directory";

if (is_dir($dirPath)) {
    if ($dh = opendir($dirPath)) {
        echo "디렉토리를 성공적으로 열었습니다.<br>";
        closedir($dh);
    } else {
        echo "디렉토리를 여는 데 실패했습니다.";
    }
} else {
    echo "디렉토리가 존재하지 않습니다.";
}
?>

2.2 readdir()

readdir() 함수는 열린 디렉토리 핸들에서 다음 항목을 읽습니다. 이 함수는 디렉토리의 파일과 폴더를 순차적으로 읽어들일 때 사용됩니다.

예시: 디렉토리 내용 읽기

<?php
$dirPath = "/path/to/directory";

if (is_dir($dirPath)) {
    if ($dh = opendir($dirPath)) {
        echo "디렉토리 목록:<br>";
        while (($file = readdir($dh)) !== false) {
            echo "파일명: $file<br>";
        }
        closedir($dh);
    } else {
        echo "디렉토리를 여는 데 실패했습니다.";
    }
} else {
    echo "디렉토리가 존재하지 않습니다.";
}
?>

2.3 closedir()

closedir() 함수는 열린 디렉토리를 닫습니다. 디렉토리 작업이 끝난 후에는 반드시 디렉토리를 닫아야 합니다.

예시: 디렉토리 닫기

<?php
$dirPath = "/path/to/directory";

if (is_dir($dirPath)) {
    if ($dh = opendir($dirPath)) {
        // 디렉토리 작업 수행
        closedir($dh);
        echo "디렉토리를 성공적으로 닫았습니다.";
    } else {
        echo "디렉토리를 여는 데 실패했습니다.";
    }
} else {
    echo "디렉토리가 존재하지 않습니다.";
}
?>


3. 디렉토리 생성 및 삭제

웹 애플리케이션에서 동적으로 디렉토리를 생성하거나 삭제하는 것은 매우 일반적인 작업입니다. PHP는 이를 위한 간단한 함수들을 제공합니다.

3.1 mkdir()

mkdir() 함수는 새 디렉토리를 생성합니다. 이 함수는 디렉토리 경로와 선택적으로 권한을 인수로 받습니다. 기본적으로 생성된 디렉토리의 권한은 시스템의 기본 설정을 따릅니다.

예시: 디렉토리 생성

<?php
$dirPath = "/path/to/new_directory";
$permissions = 0755; // 디렉토리 권한 설정 (읽기, 쓰기, 실행 권한)

if (!is_dir($dirPath)) {
    if (mkdir($dirPath, $permissions, true)) { // true는 중첩 디렉토리 생성 허용
        echo "디렉토리를 성공적으로 생성했습니다.";
    } else {
        echo "디렉토리 생성에 실패했습니다.";
    }
} else {
    echo "디렉토리가 이미 존재합니다.";
}
?>

3.2 rmdir()

rmdir() 함수는 비어 있는 디렉토리를 삭제합니다. 디렉토리가 비어 있지 않다면 삭제할 수 없습니다. 비어 있지 않은 디렉토리를 삭제하려면 먼저 디렉토리 내의 모든 파일과 서브디렉토리를 삭제해야 합니다.

예시: 비어 있는 디렉토리 삭제

<?php
$dirPath = "/path/to/empty_directory";

if (is_dir($dirPath)) {
    if (rmdir($dirPath)) {
        echo "디렉토리를 성공적으로 삭제했습니다.";
    } else {
        echo "디렉토리 삭제에 실패했습니다. 디렉토리가 비어 있지 않거나 권한이 부족할 수 있습니다.";
    }
} else {
    echo "디렉토리가 존재하지 않습니다.";
}
?>

비어 있지 않은 디렉토리 삭제:

비어 있지 않은 디렉토리를 삭제하려면, 먼저 모든 파일과 서브디렉토리를 재귀적으로 삭제해야 합니다.

예시: 비어 있지 않은 디렉토리 삭제

<?php
function deleteDirectory($dir) {
    if (!file_exists($dir)) {
        return true;
    }

    if (!is_dir($dir)) {
        return unlink($dir);
    }

    foreach (scandir($dir) as $item) {
        if ($item == '.' || $item == '..') {
            continue;
        }

        if (!deleteDirectory($dir . DIRECTORY_SEPARATOR . $item)) {
            return false;
        }
    }

    return rmdir($dir);
}

$dirPath = "/path/to/non_empty_directory";

if (deleteDirectory($dirPath)) {
    echo "디렉토리를 성공적으로 삭제했습니다.";
} else {
    echo "디렉토리 삭제에 실패했습니다.";
}
?>


4. 디렉토리 내용 읽기

디렉토리 내의 파일과 폴더 목록을 읽어들이는 것은 파일 관리 작업에서 중요한 부분입니다. PHP는 이를 위해 여러 함수를 제공합니다.

4.1 scandir()

scandir() 함수는 지정된 디렉토리의 파일과 폴더 목록을 배열로 반환합니다. 이 함수는 간단하게 디렉토리의 모든 항목을 가져올 수 있어 매우 유용합니다.

예시: 디렉토리 목록 가져오기

<?php
$dirPath = "/path/to/directory";

if (is_dir($dirPath)) {
    $files = scandir($dirPath);
    foreach ($files as $file) {
        if ($file != '.' && $file != '..') {
            echo "파일/폴더명: $file<br>";
        }
    }
} else {
    echo "디렉토리가 존재하지 않습니다.";
}
?>

4.2 glob()

glob() 함수는 특정 패턴과 일치하는 파일 경로 목록을 배열로 반환합니다. 이 함수는 파일 필터링에 유용하며, 와일드카드를 사용하여 원하는 파일만 선택할 수 있습니다.

예시: 특정 확장자의 파일 목록 가져오기

<?php
$dirPath = "/path/to/directory";
$pattern = "*.txt"; // .txt 확장자를 가진 파일들

$files = glob($dirPath . DIRECTORY_SEPARATOR . $pattern);

foreach ($files as $file) {
    echo "텍스트 파일: " . basename($file) . "<br>";
}
?>

예시: 특정 패턴의 파일들 가져오기

<?php
$dirPath = "/path/to/directory";
$pattern = "file_*_backup.php";

$files = glob($dirPath . DIRECTORY_SEPARATOR . $pattern);

foreach ($files as $file) {
    echo "매칭된 파일: " . basename($file) . "<br>";
}
?>


5. 디렉토리 존재 확인 및 속성 확인

디렉토리의 존재 여부와 속성을 확인하는 것은 파일 시스템 작업에서 필수적입니다. PHP는 이를 위해 여러 함수를 제공합니다.

5.1 is_dir()

is_dir() 함수는 지정된 경로가 디렉토리인지 확인합니다. 이 함수는 디렉토리 존재 여부를 확인할 때 유용합니다.

예시: 디렉토리 존재 확인

<?php
$dirPath = "/path/to/directory";

if (is_dir($dirPath)) {
    echo "디렉토리가 존재합니다.";
} else {
    echo "디렉토리가 존재하지 않습니다.";
}
?>

5.2 file_exists()

file_exists() 함수는 지정된 경로에 파일이나 디렉토리가 존재하는지 확인합니다. 이 함수는 파일과 디렉토리 모두에 대해 사용할 수 있습니다.

예시: 파일 또는 디렉토리 존재 확인

<?php
$path = "/path/to/file_or_directory";

if (file_exists($path)) {
    echo "파일 또는 디렉토리가 존재합니다.";
} else {
    echo "파일 또는 디렉토리가 존재하지 않습니다.";
}
?>

5.3 is_readable()

is_readable() 함수는 지정된 경로의 파일이나 디렉토리가 읽기 가능한지 확인합니다. 이 함수는 파일을 읽기 전에 권한을 확인할 때 유용합니다.

예시: 파일 읽기 가능 여부 확인

<?php
$filePath = "/path/to/file.txt";

if (is_readable($filePath)) {
    echo "파일을 읽을 수 있습니다.";
} else {
    echo "파일을 읽을 수 없습니다.";
}
?>

5.4 is_writable()

is_writable() 함수는 지정된 경로의 파일이나 디렉토리가 쓰기 가능한지 확인합니다. 이 함수는 파일을 쓰기 전에 권한을 확인할 때 유용합니다.

예시: 파일 쓰기 가능 여부 확인

<?php
$filePath = "/path/to/file.txt";

if (is_writable($filePath)) {
    echo "파일에 쓸 수 있습니다.";
} else {
    echo "파일에 쓸 수 없습니다.";
}
?>


6. 디렉토리 권한 설정

디렉토리의 권한을 설정하고 변경하는 것은 파일 시스템 보안에서 중요한 부분입니다. PHP는 이를 위해 다양한 함수를 제공합니다.

6.1 chmod()

chmod() 함수는 파일이나 디렉토리의 권한을 변경합니다. 이 함수는 Unix 기반 시스템에서 주로 사용되며, Windows에서는 제한적으로 작동할 수 있습니다.

예시: 디렉토리 권한 변경

<?php
$dirPath = "/path/to/directory";
$newPermissions = 0755; // 권한 설정 (읽기, 쓰기, 실행)

if (chmod($dirPath, $newPermissions)) {
    echo "디렉토리 권한을 성공적으로 변경했습니다.";
} else {
    echo "디렉토리 권한 변경에 실패했습니다.";
}
?>

6.2 chown()

chown() 함수는 파일이나 디렉토리의 소유자를 변경합니다. 이 함수는 서버 관리 권한이 필요하며, 대부분의 경우 웹 서버 사용자로 제한됩니다.

예시: 디렉토리 소유자 변경

<?php
$dirPath = "/path/to/directory";
$newOwner = "www-data"; // 예: Apache의 기본 사용자

if (chown($dirPath, $newOwner)) {
    echo "디렉토리 소유자를 성공적으로 변경했습니다.";
} else {
    echo "디렉토리 소유자 변경에 실패했습니다.";
}
?>

6.3 chgrp()

chgrp() 함수는 파일이나 디렉토리의 그룹을 변경합니다. 이 함수 역시 서버 관리 권한이 필요합니다.

예시: 디렉토리 그룹 변경

<?php
$dirPath = "/path/to/directory";
$newGroup = "www-data"; // 예: Apache의 기본 그룹

if (chgrp($dirPath, $newGroup)) {
    echo "디렉토리 그룹을 성공적으로 변경했습니다.";
} else {
    echo "디렉토리 그룹 변경에 실패했습니다.";
}
?>


7. 디렉토리 내 파일 및 서브디렉토리 작업

디렉토리 내의 파일과 서브디렉토리에 대한 다양한 작업을 수행할 수 있습니다. PHP는 파일 복사, 이동, 삭제 등을 위한 함수들을 제공합니다.

7.1 파일 복사

copy() 함수는 파일을 복사합니다. 이 함수는 소스 파일과 대상 파일 경로를 인수로 받습니다.

예시: 파일 복사

<?php
$source = "/path/to/source/file.txt";
$destination = "/path/to/destination/file_copy.txt";

if (copy($source, $destination)) {
    echo "파일을 성공적으로 복사했습니다.";
} else {
    echo "파일 복사에 실패했습니다.";
}
?>

7.2 파일 이동

rename() 함수는 파일을 이동하거나 이름을 변경합니다. 이 함수는 소스 파일과 대상 파일 경로를 인수로 받습니다.

예시: 파일 이동

<?php
$source = "/path/to/source/file.txt";
$destination = "/path/to/destination/file.txt";

if (rename($source, $destination)) {
    echo "파일을 성공적으로 이동했습니다.";
} else {
    echo "파일 이동에 실패했습니다.";
}
?>

7.3 파일 삭제

unlink() 함수는 파일을 삭제합니다. 이 함수는 파일 경로를 인수로 받습니다.

예시: 파일 삭제

<?php
$filePath = "/path/to/file.txt";

if (unlink($filePath)) {
    echo "파일을 성공적으로 삭제했습니다.";
} else {
    echo "파일 삭제에 실패했습니다.";
}
?>

주의사항:

  • 파일을 삭제하기 전에 반드시 백업을 해두거나, 중요한 파일이 삭제되지 않도록 확인 절차를 거쳐야 합니다.
  • unlink() 함수는 디렉토리를 삭제하지 않으며, 디렉토리를 삭제하려면 rmdir() 함수를 사용해야 합니다.

8. 보안 고려사항

디렉토리와 파일을 다룰 때는 보안에 대한 철저한 고려가 필요합니다. PHP는 강력한 기능을 제공하지만, 올바르게 사용하지 않으면 보안 취약점이 발생할 수 있습니다.

8.1 입력 데이터 검증

사용자로부터 입력받은 디렉토리 경로는 반드시 검증해야 합니다. 디렉토리 트래버설 공격(Directory Traversal)을 방지하기 위해, 사용자의 입력을 직접적으로 파일 시스템 함수에 사용하지 말고, 안전하게 처리해야 합니다.

예시: 디렉토리 경로 검증

<?php
function sanitizePath($path) {
    // 기본 경로를 설정하고, 상대 경로를 허용하지 않도록 합니다.
    $baseDir = realpath("/path/to/base/directory");
    $fullPath = realpath($baseDir . DIRECTORY_SEPARATOR . $path);

    if ($fullPath && strpos($fullPath, $baseDir) === 0) {
        return $fullPath;
    } else {
        return false;
    }
}

$userInput = $_POST['dir'];

$sanitizedPath = sanitizePath($userInput);

if ($sanitizedPath) {
    // 안전하게 디렉토리 작업 수행
    if (is_dir($sanitizedPath)) {
        echo "디렉토리가 존재합니다.";
    } else {
        echo "디렉토리가 존재하지 않습니다.";
    }
} else {
    echo "유효하지 않은 디렉토리 경로입니다.";
}
?>

8.2 권한 관리

디렉토리와 파일의 권한을 적절히 설정하여, 불필요한 접근을 제한해야 합니다. chmod(), chown(), chgrp() 함수를 사용하여 필요한 최소 권한만 부여합니다.

예시: 파일 권한 설정

<?php
$filePath = "/path/to/file.txt";
$newPermissions = 0644; // 소유자에게는 읽기 및 쓰기 권한, 그룹 및 기타 사용자에게는 읽기 권한만 부여

if (chmod($filePath, $newPermissions)) {
    echo "파일 권한을 성공적으로 변경했습니다.";
} else {
    echo "파일 권한 변경에 실패했습니다.";
}
?>

8.3 에러 메시지 관리

디렉토리와 파일 작업 중 발생하는 에러 메시지는 사용자에게 시스템 정보를 노출하지 않도록 주의해야 합니다. 에러 로그는 서버의 로그 파일에 기록하고, 사용자에게는 일반적인 에러 메시지만 표시합니다.

예시: 에러 메시지 처리

<?php
$dirPath = "/path/to/directory";

if (!is_dir($dirPath)) {
    // 사용자에게는 일반적인 메시지 표시
    echo "디렉토리가 존재하지 않습니다.";
    // 상세 에러는 로그에 기록
    error_log("디렉토리 존재하지 않음: " . $dirPath);
    exit;
}

if (!is_readable($dirPath)) {
    echo "디렉토리를 읽을 수 없습니다.";
    error_log("디렉토리 읽기 불가: " . $dirPath);
    exit;
}

// 디렉토리 작업 수행
?>

8.4 보안 모드 및 설정

PHP의 open_basedir 설정을 사용하여 PHP 스크립트가 접근할 수 있는 디렉토리를 제한할 수 있습니다. 이를 통해 디렉토리 트래버설 공격을 방지하고, 시스템의 민감한 파일에 대한 접근을 차단할 수 있습니다.

예시: php.ini 설정

; PHP 스크립트가 접근할 수 있는 디렉토리 경로 설정
open_basedir = /path/to/base/directory:/another/path


9. 실용적인 예제

PHP를 사용하여 디렉토리를 관리하는 다양한 실용적인 예제를 소개합니다. 이러한 예제들은 실제 웹 애플리케이션 개발에서 유용하게 활용될 수 있습니다.

9.1 디렉토리 목록 출력

웹 페이지에 특정 디렉토리의 파일과 폴더 목록을 출력하는 스크립트입니다.

예시: 디렉토리 목록 출력

<?php
$dirPath = "/path/to/directory";

if (is_dir($dirPath)) {
    if ($dh = opendir($dirPath)) {
        echo "<h3>디렉토리 목록:</h3><ul>";
        while (($file = readdir($dh)) !== false) {
            if ($file != '.' && $file != '..') {
                echo "<li>$file</li>";
            }
        }
        echo "</ul>";
        closedir($dh);
    } else {
        echo "디렉토리를 여는 데 실패했습니다.";
    }
} else {
    echo "디렉토리가 존재하지 않습니다.";
}
?>

9.2 디렉토리 생성 및 파일 업로드

사용자가 웹 폼을 통해 파일을 업로드하면, PHP 스크립트가 업로드된 파일을 특정 디렉토리에 저장하는 예제입니다.

HTML 폼: 파일 업로드

<!DOCTYPE html>
<html>
<head>
    <title>파일 업로드</title>
</head>
<body>
    <h2>파일 업로드</h2>
    <form action="upload.php" method="post" enctype="multipart/form-data">
        업로드할 파일 선택:
        <input type="file" name="uploadedFile"><br><br>
        <input type="submit" value="업로드">
    </form>
</body>
</html>

PHP 스크립트: upload.php

<?php
$targetDir = "/path/to/upload/directory/";
$targetFile = $targetDir . basename($_FILES["uploadedFile"]["name"]);
$uploadOk = 1;

// 파일이 실제로 업로드되었는지 확인
if(isset($_POST["submit"])) {
    if ($_FILES["uploadedFile"]["error"] == UPLOAD_ERR_OK) {
        $uploadOk = 1;
    } else {
        echo "파일 업로드 중 오류가 발생했습니다.";
        $uploadOk = 0;
    }
}

// 파일이 존재하는지 확인
if (file_exists($targetFile)) {
    echo "이미 존재하는 파일입니다.";
    $uploadOk = 0;
}

// 파일 크기 제한 (예: 5MB)
if ($_FILES["uploadedFile"]["size"] > 5000000) {
    echo "파일 크기가 너무 큽니다.";
    $uploadOk = 0;
}

// 허용된 파일 형식 확인 (예: JPG, PNG, GIF)
$imageFileType = strtolower(pathinfo($targetFile, PATHINFO_EXTENSION));
$allowedTypes = array("jpg", "jpeg", "png", "gif");

if(!in_array($imageFileType, $allowedTypes)) {
    echo "허용되지 않은 파일 형식입니다.";
    $uploadOk = 0;
}

// 업로드 가능 여부 확인
if ($uploadOk == 0) {
    echo "파일이 업로드되지 않았습니다.";
} else {
    if (move_uploaded_file($_FILES["uploadedFile"]["tmp_name"], $targetFile)) {
        echo "파일 ". htmlspecialchars(basename($_FILES["uploadedFile"]["name"])). " 이(가) 성공적으로 업로드되었습니다.";
    } else {
        echo "파일 업로드 중 오류가 발생했습니다.";
    }
}
?>

9.3 디렉토리 삭제 스크립트

특정 디렉토리를 삭제하는 PHP 스크립트입니다. 이 스크립트는 디렉토리가 비어 있는지 확인한 후 삭제를 수행합니다.

예시: 디렉토리 삭제

<?php
$dirPath = "/path/to/directory";

function deleteDirectory($dir) {
    if (!file_exists($dir)) {
        return true;
    }

    if (!is_dir($dir)) {
        return unlink($dir);
    }

    foreach (scandir($dir) as $item) {
        if ($item == '.' || $item == '..') {
            continue;
        }

        if (!deleteDirectory($dir . DIRECTORY_SEPARATOR . $item)) {
            return false;
        }
    }

    return rmdir($dir);
}

if (deleteDirectory($dirPath)) {
    echo "디렉토리를 성공적으로 삭제했습니다.";
} else {
    echo "디렉토리 삭제에 실패했습니다.";
}
?>

주의사항:

  • 이 스크립트는 지정된 디렉토리와 그 안의 모든 파일 및 서브디렉토리를 삭제합니다. 중요한 데이터가 삭제되지 않도록 주의해야 합니다.
  • 디렉토리 삭제 기능을 구현할 때는 사용자 인증과 권한 확인을 철저히 해야 합니다.

10. 참고 자료


요약

PHP 디렉토리 참조는 파일 시스템 내에서 디렉토리를 효과적으로 관리하고 조작할 수 있는 다양한 함수들을 제공합니다. 디렉토리 열기, 읽기, 생성, 삭제, 권한 설정 등 여러 작업을 PHP 스크립트를 통해 손쉽게 수행할 수 있습니다. 이러한 기능들은 웹 애플리케이션에서 파일 업로드, 사용자 데이터 관리, 로그 파일 처리 등 다양한 용도로 활용됩니다.

보안을 고려하여 디렉토리와 파일을 다룰 때는 입력 데이터의 철저한 검증, 권한 관리, 에러 메시지의 적절한 처리 등을 신경 써야 합니다. 또한, 디렉토리 작업을 자동화할 때는 실수로 중요한 데이터를 삭제하지 않도록 주의해야 합니다.

PHP의 디렉토리 관련 기능을 잘 활용하면, 웹 애플리케이션의 파일 관리가 더욱 효율적이고 안전하게 이루어질 수 있습니다. 다양한 예제를 통해 실습해 보고, 공식 문서를 참고하여 깊이 있는 이해를 쌓는 것이 중요합니다.


copyright ⓒ 스타트코딩 all rights reserved.
이메일 : startcodingim@gamil.com