PHP 이미지와 GIF를 안전하게 업로드하는 방법

Aug 20 2020

저는 소셜 네트워크를 만들고 있는데 이것이 사진 / gif 및 비디오를 업로드하는 안전한 방법인지 알고 싶습니다.

if(isset($_POST['post'])) { $uploadOk = 1;
    $imageName = $_FILES['postToUpload']['name'];
    $errorMessage = ""; $picdate = date('Y-m-d_H-i-s');

    if($imageName != "") { $targetDir = "assets/images/posts/";
        $imageName = $targetDir . uniqid() . basename($imageName); $imageFileType = pathinfo($imageName, PATHINFO_EXTENSION); if($_FILES['postToUpload']['size'] > 10971520) {
            $errorMessage = "Your file is to large"; $uploadOk = 0;
        }

        if (strtolower($imageFileType) != "jpeg" && strtolower($imageFileType) != "png" &&
            strtolower($imageFileType) != "jpg" && strtolower($imageFileType) != "gif"
            && strtolower($imageFileType) != "mp4"&& strtolower($imageFileType) != "Ogg"
            && strtolower($imageFileType) != "WebM"){ $errorMessage = "File type not allowed.";
            $uploadOk = 0; } if($uploadOk){
            if(move_uploaded_file($_FILES['postToUpload']['tmp_name'], $imageName)) {
                // image uploaded

            } else{
                // image did not upload
                $uploadOk = 0; } } } if($uploadOk) {

    $post = new Post($con, $userLoggedIn); $post->submitPost(trim(strip_tags(filter_var($_POST['post_text'], FILTER_SANITIZE_STRING))), 'none', $imageName);

    } else {

        echo "<div class='alert alert-danger'>
                $errorMessage
            </div>";
    }
}

답변

2 Victor Sep 11 2020 at 20:56

다음과 같은 이유로 코드가 안전하지 않습니다.

  • 파일 확장자에만 의존하므로 공격자는 모든 백도어를 업로드 할 수 있습니다.
  • 변수 $_FILES['postToUpload']['name']가 정의되어 있는지 확인하지 않고 접근 하므로 전체 경로 공개로 이어질 수 있습니다.
  • uniqid()인자없이 함수 를 사용 하기 때문에 고유성이 보장되지 않고 동시에 업로드되고 동일한 파일명을 가진 파일은 덮어 쓰기됩니다.
  • 잠재적으로 위험한 문자를 제거하지 않고 사용자가 제공 한 파일 이름을 저장하므로 예기치 않은 결과가 발생할 수 있습니다.

코드 개선을위한 몇 가지 권장 사항 :

  • $uploadOk변수를 제거 하십시오. 이미 $errorMessage변수를 가지고 있고 처리하고 있으며 파일이 성공적으로 업로드되었는지 확인하기에 충분합니다.
  • 각 확장 $imageFileType을 호출하는 대신 소문자로 정의해야합니다 strtolower().
  • (귀하의 경우 당신은 그렇지 않으면 사용자가 할 수없는 일부 파일을 업로드하는 것, 소문자 모든 이용 가능한 파일 확장자를 정의해야 WebM하고 Ogg있기 때문에, strtolower($imageFileType) != "Ogg"그리고 strtolower($imageFileType) != "WebM"항상있을 것입니다 FALSE).