【问题标题】:How to know if all the user image get uploaded?如何知道是否所有用户图像都已上传?
【发布时间】:2020-12-02 02:28:02
【问题描述】:

我有一个用户可以上传图片的网站。该代码有效,它让用户选择图像(这是单独的代码),下面的代码将其保存在本地存储中。我的问题是,假设用户选择了 10 张图片,其中一张没有上传(尺寸或扩展名不正确等),其余的都上传了。我如何知道哪张图片没有上传到本地存储并向用户显示该错误,以便他们重新上传?

我的代码:

$file_array = reArrayFiles($_FILES['userImages']);
pre_r($file_array);

for($i=0;$i<count($file_array);$i++) {

    $name = $file_array[$i]['name'];
    $tmpName = $file_array[$i]['tmp_name'];
    $size = $file_array[$i]['size'];
    $error = $file_array[$i]['error'];
    $type = $file_array[$i]['type'];

    $fileExtension = explode('.',$name);
    $actualExtension = strtolower(end($fileExtension));

    $extensionAllowed = array('jpg', 'jpeg','png','pdf');
    if(in_array($actualExtension, $extensionAllowed)) {
        if ($error ===0) {
            if (size < 1000000) {
                $newFileName = uniqid('', true).".".$actualExtension;

                $root = $_SERVER["DOCUMENT_ROOT"];
                echo $_SERVER['DOCUMENT_ROOT'];
                session_start();
                $_SESSION['last_id'] = mysqli_insert_id($conn);


                $dir = $root.'/userPos/'.$username.'/'.$_SESSION['last_id'].'/';
                $_SESSION['dir_name'] = $dir;

                if(!file_exists($dir) ) {
                    mkdir($dir, 0755, true);
                }
                $fileDestionation = $dir.'/'.$newFileName;
                move_uploaded_file($tmpName, $fileDestionation);


                header("Location: ../profile.php?dirname=".$_SESSION['dir_name']);
            } else {
                echo "Your file is too big";
            } 
        }else {
            echo "There was an error uoloading your file";
        } 
    } else {
        echo "You cannot upload files of this type";
    }
}

【问题讨论】:

  • 你知道,我实际上在你的 earlier question 的 cmets 中解释了这个要点。对于每个文件,您都在检查$error = $file_array[$i]['error'];。因此,您知道该特定文件是否存在错误。现在,您所要做的就是拥有一个数组,将您发现失败的任何文件的详细信息放入其中,至少包括文件名和错误消息。一旦你有了这些信息,你就可以很容易地向用户展示它。
  • 是的,我知道。但是我做不到,所以我在这里问:(
  • 嗯,“不能”是什么意思?你从我写的内容中没有明白什么,究竟是什么?您尝试了什么,出了什么问题?您知道如何创建一个数组并填充它,我可以从您的代码中看到这一点。那么具体是什么问题呢?请展示您实现这个(相当简单)逻辑的尝试并解释您遇到的问题。
  • 这就是我所做的move_uploaded_file($tmpName, $fileDestionation); if ($error) { header("Location: ../index.php?"); } else { header("Location: ../profile.php?dirname=".$_SESSION['dir_name']); } 即使其中一张图片没有上传,它仍然将其发送给我的个人资料页面。
  • @ADyson 另外,我不明白它是如何进入if(error===0) 循环的,即使有一个错误(因为一张图片没有上传。

标签: php mysql image upload local-storage


【解决方案1】:

以下内容未经测试,但基于我使用了几年的代码。我运行了一个版本进行测试,它似乎工作正常,但它是否满足两个问题中提出的目标尚不清楚......但您可能可以在代码中使用一些东西。

<?php
    error_reporting( E_ALL );
    session_start();
    

    
    if( $_SERVER['REQUEST_METHOD']=='POST' ){
        
        
        
        $fieldname='userImages';    # the name of the file field in the form.
        $username='geronimo';       # test
        #$username = $username = $_SESSION['userUsername'].$_SESSION['userId'];
        
        
        
        function uploaderror( $error ){
            /* utility function to return info about upload errors */
            switch( $error ) {
                case UPLOAD_ERR_INI_SIZE: return "The uploaded file exceeds the upload_max_filesize directive in php.ini"; 
                case UPLOAD_ERR_FORM_SIZE: return "The uploaded file exceeds the MAX_FILE_SIZE directive that was specified in the HTML form"; 
                case UPLOAD_ERR_PARTIAL: return "The uploaded file was only partially uploaded"; 
                case UPLOAD_ERR_NO_FILE: return "No file was uploaded"; 
                case UPLOAD_ERR_NO_TMP_DIR: return "Missing a temporary folder"; 
                case UPLOAD_ERR_CANT_WRITE: return "Failed to write file to disk"; 
                case UPLOAD_ERR_EXTENSION: return "File upload stopped by extension"; 
                default: return "Unknown upload error";
            }
        }
    
        if( isset(
            $_FILES[ $fieldname ],
            $_POST['_name'],
            $_POST['_desc'],
            $username
        )){
            /* do not have this... is it the db conn? */
            #require '../testing.php';
            
            # pertinent to my dev system
            chdir('../../dbo');
            require 'db-conn-details.php';
            require 'mysqli-conn.php';
            
            
            $extns  = array( 'jpg', 'jpeg','png','pdf' );
            $maxfs  = pow( 1024, 2 ) * 1; # 1Mb ~ MAX File Size
            $root   = $_SERVER['DOCUMENT_ROOT'];
            $log    = array();
            $errors = array();
            
            
            
            # If images should be deleted if SQL insert fails
            # you can use a `transaction` based approach.
            $conn->begin_transaction();
            $conn->autocommit( false );
            
            
            
            /*
                seems peculiar having both table and column named `_desc`?
                create the `prepared statement` & bind placeholders.
                Execute stmt and find number of rows inserted.. should be 1
            */
            $sql='insert into `_desc` ( `username`, `_name`, `_desc` ) values ( ?, ?, ? )';
            $stmt=$conn->prepare( $sql );
            if( !$stmt ){
                /* 
                    this should never be reached in production code... 
                    if it is there is a problem with the table schema
                */
                exit('Failed to prepare SQL statement. Check the table design and verify SQL statement is correct.');
            }
            $stmt->bind_param( 'sss', $username, $_POST['_name'], $_POST['_desc'] );
            $stmt->execute();
            
            
            $rows=$stmt->affected_rows;
            $lid=$stmt->insert_id ?: false;
            

            
            
            /*
                If one row was inserted then proceed to process
                all files uploaded. If there is no valid $lid
                variable ( Last Insert ID ) do not proceed as
                it is used to generate folder structure for the
                user.
            */
            if( $rows > 0 && $lid ){
                
                $files=(object)$_FILES[ $fieldname ];
                
                foreach( $files->name as $i => $void ){
                    /* get properties for upload item */
                    $name = $files->name[$i];
                    $size = $files->size[$i];
                    $type = $files->type[$i];
                    $tmp  = $files->tmp_name[$i];
                    $error= $files->error[$i];
                    
                    /* find attributes for file */
                    $ext  = pathinfo( $name, PATHINFO_EXTENSION );
                    list( $width, $height, $type, $attr ) = getimagesize( $tmp );
                    
                    /* Some tests */
                    if( !$width or !$height )$errors[]=sprintf( 'The file "%s" does not appear to be a valid image.',$name );
                    if( !in_array( $ext, $extns ) )$errors[]=sprintf( 'Invalid file extension "%s" for file "%s"', $ext, $name );
                    if( $size > $maxfs )$errors[]=sprintf( 'File "%s" is too large! Size:"%s", Max:"%s"', $name, $size, $maxfs );
                    if( $error!==UPLOAD_ERR_OK )$errors[]=sprintf( 'Error:The file "%s" encountered problems. "%s"', $name, uploaderror( $error ) );
                    if( !is_uploaded_file( $tmp ) )$errors[]=sprintf( 'Warning: The file "%s" might be part of an attack', $name );
                    
                    
                    
                    /*
                        At this stage if there are no errors the file
                        should be moved to it's final location.
                    */
                    if( empty( $errors ) ){
                    
                        $dir = sprintf( '%s/userPos/%s/%s', $root, $username, $lid );
                        if( !file_exists( $dir ) )mkdir( $dir, 0777, true );
                        clearstatcache();
                        
                        $filename=sprintf( '%s.%s', uniqid( '', true ), $ext );
                        $target=sprintf( '%s/%s', $dir, $filename );
                        
                        $status=move_uploaded_file( $tmp, $target );
                        if( !$status ) $errors[]=sprintf('There was a problem saving "%s" as "%s"', $name, $filename );
                        else{
                            $log[]=array(
                                'name'      =>  $name,
                                'size'      =>  $size,
                                'width'     =>  $width,
                                'height'    =>  $height,
                                'filename'  =>  $filename,
                                'folder'    =>  $dir,
                                'status'    =>  $status,
                                'details'   =>  sprintf('"%s" renamed "%s", moved to "%s"', $name, $filename, $dir )
                            );
                        }
                    }
                }
            }else{
                $errors[]='SQL query failed.';
            }
            
            
            if( empty( $errors ) )$conn->commit();
            
            $stmt->free_result();
            $stmt->close();
            
            
            $_SESSION['uploadinfo']=array(
                'errors'    =>  $errors,
                'log'       =>  $log
            );
            exit( header( sprintf( 'Location: ?dirname=%s', $dir ) ) );
            
            
        }else{
            echo 'Error: initial criteria for processing have not been met';
        }
    }
?>
<!DOCTYPE html>
<html lang='en'>
    <head>
        <title>PHP: Multiple file uploads</title>
        <meta charset='utf-8' />
        <style>
            fieldset{border:none;}
            label{width:80%;display:block;padding:1rem;}
            label > input{float:right;width:80%;}
            .errors{color:red}
            .info{color:green}
        </style>
    </head>
    <body>
        <form method='post' enctype='multipart/form-data'>
            <fieldset>
                <label>Name: <input type='text' name='_name' /></label>
                <label>Description: <input type='text' name='_desc' /></label>
                <label>Images:<input type='file' name='userImages[]' multiple /></label>
            </fieldset>
            
            <input type='submit' />
            
            <?php
                if( !empty( $_SESSION['uploadinfo'] ) ){
                
                    if( !empty( $_SESSION['uploadinfo']['errors'] ) ){
                        printf('
                            <h1>Errors</h1>
                            <pre class="errors">%s</pre>',
                            print_r($_SESSION['uploadinfo']['errors'],true)
                        );
                    }
                    
                    if( !empty( $_SESSION['uploadinfo']['log'] ) ){
                        printf('
                            <h1>Status</h1>
                            <pre class="info">%s</pre>',
                            print_r($_SESSION['uploadinfo']['log'],true)
                        );
                    }
                    
                    unset( $_SESSION['uploadinfo'] );
                }
            ?>
        </form>
    </body>
</html>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-08-01
    • 1970-01-01
    • 1970-01-01
    • 2011-12-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-04-17
    相关资源
    最近更新 更多