이 글에서는 주로 이 데모의 아바타 업로드 기능에 사용할 수 있는 파일 업로드 및 다운로드를 위한 PHP 기능을 캡슐화하는 방법을 설명합니다. 그런데 여러 파일을 업로드하는 방법도 설명합니다. 파일 업로드에 특히 익숙하다면 이 섹션을 건너뛰어도 됩니다.
여전히 이전과 동일한 인터페이스를 사용하고 있습니다.
addUser.php:
<code><span><!doctype html></span><span><<span>html</span>></span><span><<span>head</span>></span><span><<span>meta</span><span>charset</span>=<span>"utf-8"</span>></span><span><<span>title</span>></span><span></<span>title</span>></span><span></<span>head</span>></span><span><<span>body</span>></span><span><<span>H3</span>></span>添加管理员<span></<span>H3</span>></span><span><<span>FORM</span><span>action</span>=<span>"doAdminAction.php?act=addUser"</span><span>method</span>=<span>"post"</span>></span><span><<span>TABLE</span><span>width</span>=<span>"60%"</span><span>border</span>=<span>"1"</span><span>cellpadding</span>=<span>"5"</span><span>cellspacing</span>=<span>"0"</span><span>bgcolor</span>=<span>"#cccccc"</span>></span><span><<span>tr</span>></span><span><<span>TD</span><span>align</span>=<span>"right"</span>></span>用户名称<span></<span>TD</span>></span><span><<span>TD</span>></span><span><<span>input</span><span>type</span>=<span>"text"</span><span>name</span>=<span>"username"</span><span>placeholder</span>=<span>"请输入用户名称"</span>/></span><span></<span>TD</span>></span><span></<span>tr</span>></span><span><<span>tr</span>></span><span><<span>TD</span><span>align</span>=<span>"right"</span>></span>用户密码<span></<span>TD</span>></span><span><<span>TD</span>></span><span><<span>input</span><span>type</span>=<span>"text"</span><span>name</span>=<span>"password"</span><span>placeholder</span>=<span>"请输入用户名称"</span>/></span><span></<span>TD</span>></span><span></<span>tr</span>></span><span><<span>tr</span>></span><span><<span>TD</span><span>align</span>=<span>"right"</span>></span>用户邮箱<span></<span>TD</span>></span><span><<span>TD</span>></span><span><<span>input</span><span>type</span>=<span>"text"</span><span>name</span>=<span>"email"</span><span>placeholder</span>=<span>"请输入用户名称"</span>/></span><span></<span>TD</span>></span><span></<span>tr</span>></span><span><<span>tr</span>></span><span><<span>td</span><span>align</span>=<span>"right"</span>></span>性别<span></<span>td</span>></span><span><<span>td</span>></span><span><<span>input</span><span>type</span>=<span>"radio"</span><span>name</span>=<span>"sex"</span><span>value</span>=<span>"1"</span><span>checked</span>=<span>"checked"</span>/></span>男 <span><<span>input</span><span>type</span>=<span>"radio"</span><span>name</span>=<span>"sex"</span><span>value</span>=<span>"2"</span> /></span>女 <span><<span>input</span><span>type</span>=<span>"radio"</span><span>name</span>=<span>"sex"</span><span>value</span>=<span>"3"</span> /></span>保密 <span></<span>td</span>></span><span></<span>tr</span>></span><span><<span>tr</span>></span><span><<span>td</span><span>align</span>=<span>"right"</span>></span>头像<span></<span>td</span>></span><span><<span>td</span>></span><span><<span>input</span><span>type</span>=<span>"file"</span><span>name</span>=<span>"face"</span> /></span><span></<span>td</span>></span><span></<span>tr</span>></span><span><<span>tr</span>></span><span><<span>TD</span><span>colspan</span>=<span>"2"</span>></span><span><<span>input</span><span>type</span>=<span>"submit"</span><span>value</span>=<span>"添加用户"</span>/></span><span></<span>TD</span>></span><span></<span>tr</span>></span><span></<span>FORM</span>></span><span></<span>body</span>></span><span></<span>html</span>></span></code>
파일 디렉터리는 다음과 같습니다.
양식 제출을 위해 doAdminAction.php에서 move_uploaded_file($_FILES["face"]["tmp_name"], <code>move_uploaded_file($_FILES["face"]["tmp_name"], <br>
"upload/" . $_FILES["face"]["name"]);
만 추가하면 됩니다.
"upload/" . $_FILES["face"]["name"]);이 코드 줄은 클라이언트가 업로드한 파일을 서버의 해당 위치에 배치할 수 있습니다. 하지만 이러한 코드에는 몇 가지 문제가 있습니다
(1) 관리자에 업로드 폴더가 없으면 파일을 업로드할 수 없습니다.
(2) 업로드된 파일의 종류를 확인하지 않습니다. 바이러스 파일이 나타날 경우 더욱 위험합니다.
(3) 업로드 폴더에 있는 파일과 동일한 이름의 파일이 업로드되면 원본 파일이 교체됩니다.
(4) 파일 크기가 2M를 초과하는 등 파일 업로드 시 발생할 수 있는 일부 오류는 처리되지 않습니다. (php ini 파일에 지정된 기본 업로드 제한 크기는 2M입니다.)
해결책은 다음과 같습니다.
(1) 먼저 업로드된 폴더가 존재하는지 확인합니다. 존재하지 않으면
<code><span>$path</span>=<span>"upload/"</span>; <span>//</span>如果路径不存在就建立的路径上 <span>if</span>(!file_exists(<span>$path</span>)) { mkdir(<span>$path</span>,<span>0777</span>,<span>true</span>); } </code>
을 생성합니다. (2) strtolower(end(explode(“.”, $filename)))를 사용하여 가져옵니다. 파일 확장자 이름
그런 다음 확장명이 필수 파일 형식인지 확인합니다.
(3) md5(uniqid(microtime(true),true));를 사용하여 이전에 얻은 파일 확장자와 연결된 고유 문자열을 업로드된 파일의 파일 이름으로 가져옵니다.
(4) 이제 doAdminAction에 대한 코드 작성을 시작합니다. 네 번째 질문은 코드에서 설명됩니다.
<code><span><span><?php</span><span>require_once</span><span>'../include.php'</span>; <span>//print_r($_FILES["face"]);</span><span>$path</span>=<span>"upload/"</span>; <span>//如果路径不存在就建立的路径上</span><span>if</span>(!file_exists(<span>$path</span>)) { mkdir(<span>$path</span>,<span>0777</span>,<span>true</span>); } <span>//允许的类型</span><span>$allowExt</span>=<span>array</span>(<span>"gif"</span>,<span>"jpeg"</span>,<span>"png"</span>,<span>"jpg"</span>,<span>"wbmp"</span>); <span>$filename</span>=<span>$_FILES</span>[<span>"face"</span>][<span>"name"</span>]; <span>$ext</span>=getExt(<span>$filename</span>); <span>if</span>(!in_array(<span>$ext</span>,<span>$allowExt</span>)){ <span>exit</span>(<span>"非法文件类型"</span>); } <span>//得到了唯一的文件名的文件</span><span>$filename</span>=getUniName().<span>"."</span>.<span>$ext</span>; <span>if</span>(move_uploaded_file(<span>$_FILES</span>[<span>"face"</span>][<span>"tmp_name"</span>], <span>$path</span>.<span>$filename</span>)) { <span>echo</span><span>"文件上传成功"</span>; } <span>else</span> { <span>switch</span>(<span>$_FILES</span>[<span>"face"</span>][<span>'error'</span>]){ <span>case</span><span>1</span>: <span>$mes</span>=<span>"超过了配置文件上传文件的大小"</span>;<span>//UPLOAD_ERR_INI_SIZE</span><span>break</span>; <span>case</span><span>2</span>: <span>$mes</span>=<span>"超过了表单设置上传文件的大小"</span>; <span>//UPLOAD_ERR_FORM_SIZE</span><span>break</span>; <span>case</span><span>3</span>: <span>$mes</span>=<span>"文件部分被上传"</span>;<span>//UPLOAD_ERR_PARTIAL</span><span>break</span>; <span>case</span><span>4</span>: <span>$mes</span>=<span>"没有文件被上传"</span>;<span>//UPLOAD_ERR_NO_FILE</span><span>break</span>; <span>case</span><span>6</span>: <span>$mes</span>=<span>"没有找到临时目录"</span>;<span>//UPLOAD_ERR_NO_TMP_DIR</span><span>break</span>; <span>case</span><span>7</span>: <span>$mes</span>=<span>"文件不可写"</span>;<span>//UPLOAD_ERR_CANT_WRITE;</span><span>break</span>; <span>case</span><span>8</span>: <span>$mes</span>=<span>"由于PHP的扩展程序中断了文件上传"</span>;<span>//UPLOAD_ERR_EXTENSION</span><span>break</span>; } <span>echo</span><span>$mes</span>; } <span>?></span></span></code>
오류가 발생하면 인쇄됩니다. 이제 단일 파일 업로드의 내용을 설명했으므로 이제 위 코드를 함수로 캡슐화합니다.
<code><span><?php</span><span><span>function</span><span>uploadFile</span><span>(<span>$path</span>=<span>"upload/"</span>,<span>$allowExt</span>=array<span>(<span>"gif"</span>,<span>"jpeg"</span>,<span>"png"</span>,<span>"jpg"</span>,<span>"wbmp"</span>)</span>,<span>$imgFlag</span>=true)</span> {</span><span>//如果路径不存在就建立的路径上</span><span>if</span>(!file_exists(<span>$path</span>)) { mkdir(<span>$path</span>,<span>0777</span>,<span>true</span>); } <span>//允许的类型</span><span>$filename</span>=<span>$_FILES</span>[<span>"face"</span>][<span>"name"</span>]; <span>$ext</span>=getExt(<span>$filename</span>); <span>if</span>(!in_array(<span>$ext</span>,<span>$allowExt</span>)){ <span>exit</span>(<span>"非法文件类型"</span>); } <span>if</span>(<span>$imgFlag</span>){ <span>//如何验证图片是否是一个真正的图片类型</span><span>//getimagesize($filename):验证文件是否是图片类型 正确返回数组错误返回false</span><span>$info</span>=getimagesize(<span>$tmp_name</span>); <span>//var_dump($info);exit;</span><span>if</span>(!<span>$info</span>){ <span>exit</span>(<span>"不是真正的图片类型"</span>); } } <span>//得到了唯一的文件名的文件</span><span>$filename</span>=getUniName().<span>"."</span>.<span>$ext</span>; <span>if</span>(move_uploaded_file(<span>$_FILES</span>[<span>"face"</span>][<span>"tmp_name"</span>], <span>$path</span>.<span>$filename</span>)) { <span>echo</span><span>"文件上传成功"</span>; } <span>else</span> { <span>switch</span>(<span>$_FILES</span>[<span>"face"</span>][<span>'error'</span>]){ <span>case</span><span>1</span>: <span>$mes</span>=<span>"超过了配置文件上传文件的大小"</span>;<span>//UPLOAD_ERR_INI_SIZE</span><span>break</span>; <span>case</span><span>2</span>: <span>$mes</span>=<span>"超过了表单设置上传文件的大小"</span>; <span>//UPLOAD_ERR_FORM_SIZE</span><span>break</span>; <span>case</span><span>3</span>: <span>$mes</span>=<span>"文件部分被上传"</span>;<span>//UPLOAD_ERR_PARTIAL</span><span>break</span>; <span>case</span><span>4</span>: <span>$mes</span>=<span>"没有文件被上传"</span>;<span>//UPLOAD_ERR_NO_FILE</span><span>break</span>; <span>case</span><span>6</span>: <span>$mes</span>=<span>"没有找到临时目录"</span>;<span>//UPLOAD_ERR_NO_TMP_DIR</span><span>break</span>; <span>case</span><span>7</span>: <span>$mes</span>=<span>"文件不可写"</span>;<span>//UPLOAD_ERR_CANT_WRITE;</span><span>break</span>; <span>case</span><span>8</span>: <span>$mes</span>=<span>"由于PHP的扩展程序中断了文件上传"</span>;<span>//UPLOAD_ERR_EXTENSION</span><span>break</span>; } <span>echo</span><span>$mes</span>; } }</code>
여러 파일을 업로드하는 경우에는 두 가지 상황이 있습니다.
(1) 여러 단일 파일 업로드
<code><span><!doctype html></span><span><<span>html</span>></span><span><<span>head</span>></span><span><<span>meta</span><span>charset</span>=<span>"utf-8"</span>></span><span><<span>title</span>></span><span></<span>title</span>></span><span></<span>head</span>></span><span><<span>body</span>></span><span><!-- 表单中enctype="multipart/form-data"的意思,是设置表单的MIME编码。默认情况,这个编码格式是application/x-www-form-urlencoded,不能用于文件上传;只有使用了multipart/form-data,才能完整的传递文件数据,进行下面的操作. --></span><span><<span>FORM</span><span>action</span>=<span>"doAction2.php"</span><span>method</span>=<span>"post"</span><span>enctype</span>=<span>"multipart/form-data"</span>></span><span><<span>INPUT</span><span>type</span>=<span>"hidden"</span><span>name</span>=<span>"MAX_FILE_SIZE"</span><span>value</span>=<span>"1048576"</span>/></span> 请选择上传文件:<span><<span>INPUT</span><span>type</span>=<span>"file"</span><span>name</span>=<span>"myFile1"</span>/></span><span><<span>br</span>/></span> 请选择上传文件:<span><<span>INPUT</span><span>type</span>=<span>"file"</span><span>name</span>=<span>"myFile2"</span>/></span><span><<span>br</span>/></span> 请选择上传文件:<span><<span>INPUT</span><span>type</span>=<span>"file"</span><span>name</span>=<span>"myFile3"</span>/></span><span><<span>br</span>/></span><span><<span>input</span><span>type</span>=<span>"submit"</span><span>value</span>=<span>"上传"</span>/></span><span></<span>FORM</span>></span><span></<span>body</span>></span><span></<span>html</span>></span></code>
이 형식은 doAction2.php의 여러 단일 파일 print_r($_FILES)을 업로드하는 것과 같습니다.
<code><span>Array</span> ( [myFile1] => <span>Array</span> ( [name] => touxiang.jpg [type] => image/jpeg [tmp_name] => D:\xampp\tmp\php79E3.tmp [error] => <span>0</span> [size] => <span>28747</span> ) [myFile2] => <span>Array</span> ( [name] => 文章.png [type] => image/png [tmp_name] => D:\xampp\tmp\php7A03.tmp [error] => <span>0</span> [size] => <span>11655</span> ) [myFile3] => <span>Array</span> ( [name] => 增加.png [type] => image/png [tmp_name] => D:\xampp\tmp\php7A04.tmp [error] => <span>0</span> [size] => <span>7439</span> ) )</code>
(2) 다중 파일 업로드
<code><span><!doctype html></span><span><<span>html</span>></span><span><<span>head</span>></span><span><<span>meta</span><span>charset</span>=<span>"utf-8"</span>></span><span><<span>title</span>></span><span></<span>title</span>></span><span></<span>head</span>></span><span><<span>body</span>></span><span><!-- 表单中enctype="multipart/form-data"的意思,是设置表单的MIME编码。默认情况,这个编码格式是application/x-www-form-urlencoded,不能用于文件上传;只有使用了multipart/form-data,才能完整的传递文件数据,进行下面的操作. --></span><span><<span>FORM</span><span>action</span>=<span>"doAction2.php"</span><span>method</span>=<span>"post"</span><span>enctype</span>=<span>"multipart/form-data"</span>></span><span><<span>INPUT</span><span>type</span>=<span>"hidden"</span><span>name</span>=<span>"MAX_FILE_SIZE"</span><span>value</span>=<span>"1048576"</span>/></span> 请选择上传文件:<span><<span>INPUT</span><span>type</span>=<span>"file"</span><span>name</span>=<span>"myFile[]"</span>/></span><span><<span>br</span>/></span> 请选择上传文件:<span><<span>INPUT</span><span>type</span>=<span>"file"</span><span>name</span>=<span>"myFile[]"</span>/></span><span><<span>br</span>/></span> 请选择上传文件:<span><<span>INPUT</span><span>type</span>=<span>"file"</span><span>name</span>=<span>"myFile[]"</span>/></span><span><<span>br</span>/></span><span><<span>input</span><span>type</span>=<span>"submit"</span><span>value</span>=<span>"上传"</span>/></span><span></<span>FORM</span>></span><span></<span>body</span>></span><span></<span>html</span>></span></code>
비슷한 print_r($_files)
<code><span>Array</span> ( [myFile] => <span>Array</span> ( [name] => <span>Array</span> ( [<span>0</span>] => touxiang.jpg [<span>1</span>] => 文章.png [<span>2</span>] => 增加.png ) [type] => <span>Array</span> ( [<span>0</span>] => image/jpeg [<span>1</span>] => image/png [<span>2</span>] => image/png ) [tmp_name] => <span>Array</span> ( [<span>0</span>] => D:\xampp\tmp\php1EC.tmp [<span>1</span>] => D:\xampp\tmp\php1ED.tmp [<span>2</span>] => D:\xampp\tmp\php1EE.tmp ) [error] => <span>Array</span> ( [<span>0</span>] => <span>0</span> [<span>1</span>] => <span>0</span> [<span>2</span>] => <span>0</span> ) [size] => <span>Array</span> ( [<span>0</span>] => <span>28747</span> [<span>1</span>] => <span>11655</span> [<span>2</span>] => <span>7439</span> ) ) ) </code>
두 방법으로 얻은 배열이 매우 다르다는 것을 알 수 있습니다.
첫 번째 경우(파일 배열과 동일)에 대해
<code><span>foreach</span> (<span>$_FILES</span><span>as</span><span>$var</span>) { <span>//对于每一个文件进行了文件上传操作</span><span>$info</span>=uploadFile(<span>$var</span>); <span>echo</span><span>$info</span>; }</code>
두 번째 경우에 표시된 3차원 배열을 첫 번째 경우에 표시된 2차원 배열로 변환할 수 있습니다. .
<code>foreach(<span>$_FILES</span>[myFile][name] as <span>$key</span>=><span>$var</span> ) { <span>$files</span>[<span>$key</span>][name]=<span>$_FILES</span>[myFile][name][<span>$key</span>]; <span>$files</span>[<span>$key</span>][type]=<span>$_FILES</span>[myFile][type][<span>$key</span>]; <span>$files</span>[<span>$key</span>][tmp_name]=<span>$_FILES</span>[myFile][tmp_name][<span>$key</span>]; <span>$files</span>[<span>$key</span>][<span>error</span>]=<span>$_FILES</span>[myFile][<span>error</span>][<span>$key</span>]; <span>$files</span>[<span>$key</span>][<span>size</span>]=<span>$_FILES</span>[myFile][<span>size</span>][<span>$key</span>]; } print_r(<span>$files</span>);</code>
결과
<code><span>Array</span> ( [<span>0</span>] => <span>Array</span> ( [name] => touxiang.jpg [type] => image/jpeg [tmp_name] => D:\xampp\tmp\php3227.tmp [error] => <span>0</span> [size] => <span>28747</span> ) [<span>1</span>] => <span>Array</span> ( [name] => 文章.png [type] => image/png [tmp_name] => D:\xampp\tmp\php3228.tmp [error] => <span>0</span> [size] => <span>11655</span> ) [<span>2</span>] => <span>Array</span> ( [name] => 增加.png [type] => image/png [tmp_name] => D:\xampp\tmp\php3229.tmp [error] => <span>0</span> [size] => <span>7439</span> ) )</code>
이제 파일 업로드 기능을 캡슐화하기 시작합니다. 이 기능은 단일 파일 업로드와 다중 파일 업로드를 모두 처리할 수 있습니다. 그런 다음 배열 처리의 이 부분을 작성하고 upload() 함수를 호출하면 됩니다.
<code><span><?php</span><span>require_once</span><span>"../include.php"</span>; <span>//用于转换数组</span><span><span>function</span><span>buildInfo</span><span>()</span> {</span><span>foreach</span>(<span>$_FILES</span><span>as</span><span>$file</span>) { <span>$i</span>=<span>0</span>; <span>if</span>(is_string(<span>$file</span>[<span>'name'</span>])) { <span>$files</span>[<span>$i</span>]=<span>$file</span>; <span>$i</span>++; } <span>else</span> { <span>foreach</span>(<span>$file</span>[name] <span>as</span><span>$key</span>=><span>$var</span>) { <span>$files</span>[<span>$key</span>][name]=<span>$file</span>[name][<span>$key</span>]; <span>$files</span>[<span>$key</span>][type]=<span>$file</span>[type][<span>$key</span>]; <span>$files</span>[<span>$key</span>][tmp_name]=<span>$file</span>[tmp_name][<span>$key</span>]; <span>$files</span>[<span>$key</span>][error]=<span>$file</span>[error][<span>$key</span>]; <span>$files</span>[<span>$key</span>][size]=<span>$file</span>[size][<span>$key</span>]; } } } <span>return</span><span>$files</span>; } <span>//用于上传</span><span><span>function</span><span>uploadFile</span><span>(<span>$path</span>=<span>"upload/"</span>,<span>$allowExt</span>=array<span>(<span>"gif"</span>,<span>"jpeg"</span>,<span>"png"</span>,<span>"jpg"</span>,<span>"wbmp"</span>)</span>)</span> {</span><span>//如果路径不存在就建立的路径上</span><span>if</span>(!file_exists(<span>$path</span>)) { mkdir(<span>$path</span>,<span>0777</span>,<span>true</span>); } <span>$files</span>=buildInfo(); <span>foreach</span>(<span>$files</span><span>as</span><span>$file</span>) { <span>//允许的类型</span><span>$filename</span>=<span>$file</span>[<span>"name"</span>]; <span>$ext</span>=getExt(<span>$filename</span>); <span>if</span>(!in_array(<span>$ext</span>,<span>$allowExt</span>)){ <span>exit</span>(<span>"非法文件类型"</span>); } <span>//校验是否是一个真正的图片类型</span><span>if</span>(<span>$imgFlag</span>){ <span>if</span>(!getimagesize(<span>$file</span>[<span>'tmp_name'</span>])){ <span>exit</span>(<span>"不是真正的图片类型"</span>); } } <span>//得到了唯一的文件名的文件</span><span>$filename</span>=getUniName().<span>"."</span>.<span>$ext</span>; <span>if</span>(move_uploaded_file(<span>$file</span>[<span>"tmp_name"</span>], <span>$path</span>.<span>$filename</span>)) { <span>echo</span><span>"文件上传成功"</span>; } <span>else</span> { <span>switch</span>(<span>$file</span>[<span>'error'</span>]){ <span>case</span><span>1</span>: <span>$mes</span>=<span>"超过了配置文件上传文件的大小"</span>;<span>//UPLOAD_ERR_INI_SIZE</span><span>break</span>; <span>case</span><span>2</span>: <span>$mes</span>=<span>"超过了表单设置上传文件的大小"</span>; <span>//UPLOAD_ERR_FORM_SIZE</span><span>break</span>; <span>case</span><span>3</span>: <span>$mes</span>=<span>"文件部分被上传"</span>;<span>//UPLOAD_ERR_PARTIAL</span><span>break</span>; <span>case</span><span>4</span>: <span>$mes</span>=<span>"没有文件被上传"</span>;<span>//UPLOAD_ERR_NO_FILE</span><span>break</span>; <span>case</span><span>6</span>: <span>$mes</span>=<span>"没有找到临时目录"</span>;<span>//UPLOAD_ERR_NO_TMP_DIR</span><span>break</span>; <span>case</span><span>7</span>: <span>$mes</span>=<span>"文件不可写"</span>;<span>//UPLOAD_ERR_CANT_WRITE;</span><span>break</span>; <span>case</span><span>8</span>: <span>$mes</span>=<span>"由于PHP的扩展程序中断了文件上传"</span>;<span>//UPLOAD_ERR_EXTENSION</span><span>break</span>; } <span>echo</span><span>$mes</span>; } } }</span></code>
일부 바이러스 파일은 이미지 파일로 위장하기 때문에 이 코드는 업로드된 이미지가 이미지 형식인지 확인하고 이미지 크기를 확인하는 기능도 추가합니다.
위 내용은 PHP를 사용하여 사용자 등록 및 관리를 완료하는 데모(PHP는 단일 파일 및 다중 파일 업로드를 실현함)를 소개하고 관련 내용도 포함되어 있어 PHP 튜토리얼에 관심이 있는 친구들에게 도움이 되기를 바랍니다.