Portada | Monotemáticos | Secciones | Desarrolladores | Comunidad | Servicios | Servicios profesionales | RSS
Desde 0 | HTML | CSS | ASP | PHP | AJAX | Javascript | Promoción de webs | Rentabilidad de webs
Directorio | Manuales | Scripts | FAQs | Programas | Artículos Copyleft | Actualidad | La Cosecha | Colabora
Registrarse | Vuestras páginas | Foros del web | Lista de correo | Boletín de novedades
Generador METAs | Compras | Busca cursos
Alojamiento | Dominios.es | Micropagos SMS | Buscadores | Patentes, marcas | Creación web | Multimedia | Videos
Desarrollo Freelance | Buscar proyectos | Buscar profesionales | Solicitar desarrollo

Upload de archivos con PHP


Realizamos unas páginas PHP que reciben un archivo del discoduro del visitante y lo suben al servidor remoto.


09/11/03 - En PHP tenemos muchas funcionalidades desarrolladas desde el principio y sin necesidad de instalar ningún añadido en nuestro servidor. Es el caso de subir archivos a un servidor web por HTTP y a través de una página con un formulario, donde se permite seleccionar el archivo que queremos cargar de nuestro disco duro.

El ejemplo se encuentra bien documentado en un montón de páginas para desarrolladores, sin ir más lejos en la página de la propia tecnología: http://www.php.net/manual/es/features.file-upload.php. Nosotros en este caso vamos a intentar ir un poco más allá, realizando un par de comprobaciones al subir el fichero y combinando en el mismo formulario campos de tipo file y tipo text.

El formulario para subir seleccionar los archivos

Es un formulario cualquiera, pero tiene una serie de particularidades y campos file, que no solemos utilizar habitualmente.

<form action="subearchivo.php" method="post" enctype="multipart/form-data">
    <b>Campo de tipo texto:</b>
    <br>
    <input type="text" name="cadenatexto" size="20" maxlength="100">
    <input type="hidden" name="MAX_FILE_SIZE" value="100000">
    <br>
    <br>
    <b>Enviar un nuevo archivo: </b>
    <br>
    <input name="userfile" type="file">
    <br>
    <input type="submit" value="Enviar">
</form>


Para empezar vemos que se ha colocado un nuevo atributo en el formulario: enctype="multipart/form-data", necesario para subir en un mismo formulario datos y archivos.

También tenemos el campo hidden MAX_FILE_SIZE, que sirve para indicar el tamaño en bytes de los archivos a subir. Este campo algunos navegadores no tienen porqué entenderlo o hacerle caso. Además, es fácil saltarse esa protección, por lo que deberemos en las propias páginas PHP comprobar que el archivo tenga el tamaño que deseamos.

Por último, tenemos el campo tipo file, donde se seleccionará el archivo a subir. También hemos colocado un campo de tipo text, para subir datos por POST de tipo texto acompañados a los datos binarios del archivo.

Página que sube los archivos

Esta página debe hacer las comprobaciones necesarias para saber si las características del archivo a subir son las que deseamos y realizar la copia del archivo en un directorio del servidor.

Para hacer las comprobaciones, PHP nos crea una serie de variables que podemos acceder con la información del archivo enviado.

$HTTP_POST_FILES['userfile']['name']
El nombre original del fichero en la máquina cliente.

$HTTP_POST_FILES['userfile']['type']
El tipo mime del fichero (si el navegador lo proporciona). Un ejemplo podría ser "image/gif".

$HTTP_POST_FILES['userfile']['size']
El tamaño en bytes del fichero recibido.

$HTTP_POST_FILES['userfile']['tmp_name']
El nombre del fichero temporal que se utiliza para almacenar en el servidor el archivo recibido.

<?
//tomo el valor de un elemento de tipo texto del formulario
$cadenatexto = $_POST["cadenatexto"];
echo "Escribió en el campo de texto: " . $cadenatexto . "<br><br>";

//datos del arhivo
$nombre_archivo = $HTTP_POST_FILES['userfile']['name'];
$tipo_archivo = $HTTP_POST_FILES['userfile']['type'];
$tamano_archivo = $HTTP_POST_FILES['userfile']['size'];
//compruebo si las características del archivo son las que deseo
if (!((strpos($tipo_archivo, "gif") || strpos($tipo_archivo, "jpeg")) && ($tamano_archivo < 100000))) {
    echo "La extensión o el tamaño de los archivos no es correcta. <br><br><table><tr><td><li>Se permiten archivos .gif o .jpg<br><li>se permiten archivos de 100 Kb máximo.</td></tr></table>";
}else{
    if (move_uploaded_file($HTTP_POST_FILES['userfile']['tmp_name'], $nombre_archivo)){
       echo "El archivo ha sido cargado correctamente.";
    }else{
       echo "Ocurrió algún error al subir el fichero. No pudo guardarse.";
    }
}
?>


Para empezar, recogemos el campo de texto enviado por POST, de la forma habitual. Aunque esto no tenga nada que ver con subir archivos, es muy normal que en el mismo formulario deseemos mezclar varios tipos de información.

Luego se recogen los datos necesarios del archivo, como su nombre, extensión y tamaño para, en el siguiente if, comprobar que la extensión sea .gif o .jpg y que el tamaño menor que 100000 bytes.

Si el archivo tenía las características deseadas, se puede subir al servidor. Para ello se utiliza la función move_uploaded_file(), que recibe el nombre del archivo temporal que se desea subir y el nombre del archivo que se desea dar.

Cuando se sube el archivo, el servidor lo copia en una localización temporal para que seamos nosotros los que elijamos la posición definitiva donde queremos que se almacene. Si no lo copiamos a ningún sitio, después de la ejecución de la página, se borra de su localización temporal.

La función move_uploaded_file() se utiliza para mover el archivo a la posición definitiva. Recibe por un lado el nombre temporal del fichero y por otro el nombre que deseamos colocarle definitivamente y, si se desea, la ruta para llegar al directorio donde queremos guardarlo. En el caso del ejemplo sólo se indica el nombre del archivo, por ello el fichero se subirá al mismo directorio donde están las páginas PHP que hacen el upload. Esta función devuelve un boleano que indica si hubo o no éxito al subir el archivo.

Nota: Es importante señalar que el upload de archivos es un proceso crítico que puede dar lugar a errores y agujeros de seguridad. Por ejemplo, si los directorios destino están protejidos contra escritura, nos dará un error. Podemos ver los errores comunes relatados en la página de PHP.

Recomendamos una vez más ampliar esta información en la página de PHP: http://www.php.net/manual/es/features.file-upload.php

Se pueden descargar los códigos del ejemplo en este enlace.

 Seguir navegando a partir aquí:
+ 1 manual relacionado
+ 1 categoria relacionada
+ 20 comentarios (Añadir)
+ 13 comentarios no revisados

 Autoría, licencia y acciones sobre este artículo

Informe de Miguel Angel Alvarez*
Director de DesarrolloWeb.com

Atención: Contenido exclusivo de DesarrolloWeb.com. No reproducir. Copyright.

* Para consultas técnicas utilizar la lista de correo.

Versión imprimible Versión imprimible del artículo
Enviar artículo por e-mail Enviar artículo por e-mail
Añadir un comentario al artículo Publicar un comentario del artículo

Manuales relacionados con este artículo
Dentro de Gestión de archivos en PHP

Categorias relacionadas
A través de las categorías de nuestro directorio se pueden encontrar otro tipo de recursos relacionados con este artículo:
+ Entrar en Scripts en PHP


 Comentarios de los visitantes
Los comentarios de los visitantes son para ampliar la información del artículo. Cualquiera puede participar.
Se muestran 20 comentarios revisados

 Comentario de Ducados
16/1/04 
¿Algun usuario se ha topado con este estupendo error al probar este ejemplo?

Valor del Campo de Texto: archivo

Warning: Unable to create '016.jpg': Permiso denegado in /var/www/html/subir.php on line 55

Warning: Unable to move '/var/www/html/tmp/php8Y90P3' to '016.jpg' in /var/www/html/subir.php on line 55
Ocurrió algún error al subir el fichero. No pudo guardarse.

Lo dicho, si alguien sabe como solucionar esto, que postee aqui o me mande un email.

Gracias por Anticipado

 Comentario de Nehos
25/1/04 
El problema esta en los permisos del directorio donde se van a mover los archivos, en modo consola haz un chmod 777 nombreDirectorio, o implementa un pequeño script con php que te lo haga si no tienes accesso en modo consola

 Comentario de speack
30/1/04 
los errores que muestras parece ser que es porque en el directorio donde pusiste los scripts no le diste el permiso chmod, colocate arriba del directorio y con el menu contextual te aparecera un a opcion de chmod ponle 777...
bye

 Comentario de Ducados
24/2/04 
No es por problema de permisos, haciendole un "ls" al directorio en cuestión sale esto:
[root@ServidorWEB directorio]# ls -al /directorio/en/cuestion
total 80
drwxrwxrwx 2 usuario usuario 4096 feb 24 20:33 .
Dios mio, no siento las piernas... ¿será problema de la RedHat 9.0, del php.ini, de bush?
Saludos y Gracias

 Comentario de FASAT
04/3/04 
efectivamente, son los permisos en los directorios los que influyen en el envio de los archivos, no obstante, aconsejo crear una carpeta y en esa colocar el form y el php, ya que en ella, también quedan los archivos enviados.
FASAT
SANTIAGO, CHILE

 Comentario de david
07/5/04 
El campo MAX_FILE_SIZE = 100000, en que se mide exactamente, en bits o bytes? Lo que quiere decir en este ejemplo es que no se pueden subir ficheros de más de 100 Kb o 100 KB.

Es verdad que sólo se pueden subir ficheros de hasta 2 MB.
Si la unidad de medida es en bits, entonces para poder subir como mucho ficheros de un 1MB el valor de MAX_FILE_SIZE será 1024 KB que es 1024 * 1000 * B = 1024 * 1000 * 8 bits, no?
Espero que alguien lo entienda Saludos, david

 Comentario de José A. Rivas G.
01/10/04 
He utilizado este ejemplo para construir un upload de logotipos para un directorio que tengo en mi web, el comentario va por lo siguiente: Ya se establecen es el ejemplo como limitar el tipo de archivo y tamaño del mismo, pero necesito bloquear las dimensiones del mismo, realice distintas pruebas con getimagesize() y efectivamente me muestra las dimensiones de la imagen pero solo despues de que la misma se subió, hay alguna variable de tipo $HTTP_POST_FILES que deuelva el alto y ancho de un archivo de imagen. Gracias...

 Comentario de Elias
10/3/05 
funciona perfecto el upload, salvo con los archivos de extension "rar", le añadi el codiogo qeu realiza la comprobacion pero no me funciona, no asi con los zip u otras extensiones con las que no tengo problemas

 Comentario de Victor
01/4/05 
Genial el artículo. Me gustaría saber si es posible incluir en el archivo alguna sentencia para enviar por email desde el servidor el documento subido para tener una copia al momento de los archivos subidos desde el formulario. Gracias

 Comentario de cesar sepulveda
14/4/05 
Encuentro espectacular su ayuda. Estube tratando de aplicar este codigo al formulario de envio y no me adjunta el archivo y no lo envia al correo. Quisiera saber como se hace, serian tan amables de enviarme alguna ayuda.
Concretamente quisiera saber como adjuntar un archivo a un formulario y enviar los datos de este con el archivo al correo de destino.
gracias.

 Comentario de cesar sepulveda
26/4/05 
Exelente demostración de upload en php. Los felicito de verdad. Les cuento que me resulto perfectamente. El unico inconveniente es que no se a donde envia el archivo. Hay alguna de enviarlo a un correo electronico?. Ojala me contesten gracias por todo y los felicito!!!!

 Comentario de oriol soriano
26/7/05 
El script del ejemplo, sube el archivo al directorio pre-definido por defecto en php.ini para uploads, lo que hace la función move_uploaded_file() es moverlo de este directorio temporal al que tu decidas de la siguiente manera move_uploaded_file(directorio_temporal,directorio_nuevo) en el ejemplo solo pone nombre del archivo, con lo que se queda en el mismo directorio temporal definido en php.ini

 Comentario de Dario Cortes Martinez
17/11/05 
amigos
encontre la manera de guardar los archivos en carpetas designadas aqui les envio el codigo

<?
$path="\wwwarchivos/";

$nombre_archivo = $_FILES['userfile']['name'];
$tipo_archivo = $_FILES['userfile']['type'];
$tamano_archivo = $_FILES['userfile']['size'];

if (!((strpos($tipo_archivo, "doc") || strpos($tipo_archivo, "zip") || strpos($tipo_archivo,"jpg")) && ($tamano_archivo < 2000000000))) {
echo "La extensión o el tamaño de los archivos no es correcta. <br><br><table><tr><td><li>Se permiten archivos *.doc, *.zip o *.jpg<br><li>se permiten archivos de ?? máximo.</td></tr></table><br>";
echo "<a href='index.php'>Click aquí</a> para corregir los campos.";
}else{
if (move_uploaded_file($HTTP_POST_FILES['userfile']['tmp_name'], $path.$_FILES['userfile']['name'])){
echo "El archivo ha sido cargado correctamente.";
}else{
echo "Ocurrió algún error al subir el fichero. No pudo guardarse.";
}
}
?>

si se dan cuenta ocupe una variable path para darle la direccion
en mi caso trabajo con una carpeta archivos dentro de la raiz
localhostwwwarchivos

espero que les sirva
10.4

 Comentario de Rodrigo Mazzo
28/1/06 
Para los que tengan problemas con las extensiones rar o pptsimilares, para efectos de este script hay cosas que cambian. Por ejmplo, un archivo doc es msword, y uno ppt debe escribirse como vnd.ms-powerpoint. Para averiguar la extensión de una extensión particular, yo usé un "echo $HTTP_POST_FILES['userfile']['type']; "
Espero le sirva a alguien.. saludos,
Rodrigo

 Comentario de Fabian
15/8/06 
Me encanto el articulo pero tengo una duda muy pequeña estoy apenas aprendiendo php, y me gustaria saber o que me explicaran un poco mas donde se descarga el archivo que se subio ?

 Comentario de Edgardo
07/9/06 
el archivo se guarda en el directorio en donde se encuentra la pagina.php

 Comentario de JEJE
24/12/06 
imponente, explica muchas cosas que no sabia, muchas gracias, hace como 3 dias que buscaba algo que me explicara asi de claro, gracias

 Comentario de César Santos
03/1/07 
Muchas Gracias por esta demostración ordenada, correcta y muy bien definida, con tu aporte será suficiente para actulizar mi página web muchas gracias...

PorFavor no dejes de escribir Articulos para los iniciantes en PHP. Otra vez Gracias...

 Comentario de Germán
30/6/07 
Hola aquí les envio un script modificado que si funciona:tu página se llamrá:subir_archivo.php
<body>
Hola, estoy probando el codigo
<?php
echo $_POST['cadenatexto']." Nombres<br>";
if ($_POST['cadenatexto']!='')
{
$path="./archivos_php/";
$nombre_archivo = $_FILES['userfile']['name'];
$tipo_archivo = $_FILES['userfile']['type'];
$tamano_archivo = $_FILES['userfile']['size'];
if (!((strpos($nombre_archivo, "doc") || strpos($nombre_archivo, "gif") || strpos($nombre_archivo,"jpg"))))
{
echo "La extensión o el tamaño de los archivos no es correcta";
}
else
{
if (move_uploaded_file($HTTP_POST_FILES['userfile']['tmp_name'], $path.$_FILES['userfile']['name']))
{
echo "El archivo ha sido cargado correctamente.";
}
else
{
echo "Ocurrió algún error al subir el fichero. No pudo guardarse.";
}
}
}
?>
<form action="subir_archivo.php" method="post" enctype="multipart/form-data">
<b>Campo de tipo texto:</b>
<br>
<input type="text" name="cadenatexto" size="20" maxlength="100">
<input type="hidden" name="MAX_FILE_SIZE" value="100000000">
<br>
<br>
<b>Enviar un nuevo archivo: </b>
<br>
<input name="userfile" type="file">
<br>
<input type="submit" value="Enviar">
</form>
</body>

 Comentario de iim.vxk
07/9/07 
a los que tengan éstas 2 Advertencias - rutas son un ejemplo real - ::

-
move_uploaded_file(/uploads/images/sample.png) [function.move-uploaded-file]: failed to open stream: No such file or directory in /scripts/php/system/upload-file.php on line X
-

y

-
move_uploaded_file() [function.move-uploaded-file]: Unable to move '/tmp/somefilename' to '/uploads/images/sample.png' in /scripts/php/system/upload-file.php on line X
-

probablemente la ruta '/uploads/images/sample.png' esté incompleta, en mi caso la ruta completa es "/home/x-user/public_html/uploads/images/sample.png"

para saber el directorio actual de trabajo pueden usar getcwd(), de seguro se chingan al error.

XD

:)

Añadir un comentario al artículo Añadir un comentario del artículo
 Comentarios sin revisar
Entre los comentarios no revisados puede haber algunos interesantes que se hayan enviado recientemente.
 Se han encontrado 13 comentarios sin revisar

Ver el comentario no revisadoVer los comentarios no revisados
Añadir un comentario al artículo Añadir un comentario del artículo



Enlaces:
Maestrosdelweb
  Ir arriba

Manuales relacionados
+Gestión de archivos en PHP
Categorías
+Scripts en PHP

Tienda DesarrolloWeb

DesarrolloWeb.com | Copyright | Anunciese | Acerca de | Datos legales | Contacta | Por GuiarteMultimedia