quinta-feira, 3 de janeiro de 2013

Upload de arquivos com AJAX e PHP

Simples tutorial de upload de arquivos com AJAX e PHP
O conceito
- Criar um formulário HTML simples para upload de arquivos
- Definir o target para um iFrame invisível que está na página. (logo veremos sobre e porque disso)
- Chamar uma função JavaSript para exibir uma animação enquanto o PHP rola nos bastidores.
- Após o PHP terminar o upload, esconder a animação
Criando o arquivo HTML
O arquivo HTML que usaremos neste artigo é bem simples. Ele tem apenas um formulário  com um campo do tipo FILE e um botão SUBMIT. No entanto, não podemos esquecer de definirmos o parâmetro enctype. Na verdade, além do que mencionei, precisamos adicionar um pouco mais de código nesse HTML do que um simples formulário. Primeiro precisamos de um bloco onde nós vamos mostrar a animação que ilustrará o progresso do upload. Precisamos também de um outro bloco onde informamos ao visitante se o upload foi sucesso ou não. Além disso, precisamos adicionar um iFrame oculto para a página que é utilizada como target do  formulário. Também adicionaremos um evento 'onsubmit' no formulário.
Enfim, o 'body' de nosso arquivo HTML ficará assim:
pegue o arquivo loader.gif aqui
<body>
    <p id="upload_process">Loading...<br/><img src="loader.gif" /></p>
    <p id="result"></p>
    <form action="upload.php" method="post" enctype="multipart/form-data" target="upload_target" onsubmit="startUpload();" >
        File: <input name="myfile" type="file" />
        <input type="submit" name="submitBtn" value="Upload" />
    </form>
    <iframe id="upload_target" name="upload_target" src="#" style="width:0;height:0;border:0px solid #fff;"></iframe>
</body>
Por padrão, o conteúdo do bloco da animação de progresso do upload estará oculto. Precisaremos de uma função JavaScript que faz com que este bloco fique visível caso o botão submit for pressionado. É um código muito simples, que apenas alterará o parâmetro de visibilidade.
function startUpload(){
     document.getElementById('upload_process').style.visibility = 'visible';
    return true;
}
E tem mais. Precisaremos de uma outra função, onde à chamaremos ao final do processo de upload. A finalidade desta função será imprimir uma mensagem de resultado que dependendo do valor de um devido parâmetro, esconderá o bloco da animação ilustrativa de progresso do upload novamente.
function stopUpload(success){
     var result = '';
     if (success == 1){
        document.getElementById('result').innerHTML ='<span>O upload do arquivo foi executado com sucesso!<\/span><br/><br/>';
    }
    else{
        document.getElementById('result').innerHTML = '<span>Ocorreu um erro durante o upload do arquivo!<\/span><br/><br/>';
    }
     document.getElementById('upload_process').style.visibility = 'hidden';
    return true;
 }
Bom, antes de criarmos o código PHP, vamos criar um style CSS para caracterizar visualmente o bloco de progresso do upload. O estilo para usarmos no formulário é muito simples, mas o estilo do bloco de progresso e upload iremos definir o z-index e o parâmetro de visibilidade também.
#upload_process{
    z-index:100;
    position:absolute;
    visibility:hidden;
    text-align:center;
    width:400px;
    margin:0px;
    padding:0px;
    background-color:#fff;
    border:1px solid #ccc;
}
form{
    text-align:center;
    width:390px;
    margin:0px;
    padding:5px;
    background-color:#fff;
    border:1px solid #ccc;
}


Agora podemos focalizar no lado servidor e no responsável pela mágica do upload.
O código do lado servidor é escrito em PHP e é muito curto e simples. Primeiro precisamos definir
o caminho de destino do arquivo. Neste caso, vamos utilizar o diretório que já estamos trabalhando. 
Depois introduzimos uma variável que mostrará se houve um erro ou não durante o processo de upload
Em seguida, movemos o arquivo carregado no diretório tmp para o diretório que mencionei um pouco antes.
Continuando...
Definimos uma variável para lidar com o resultado do upload, ou seja,  se foi sucesso ou falha e ao final
do código inserimos um comando 'sleep()' para fazer a animação demorar um pouco mais no caso de uploads 
muito rápidos.
Enfim, o código PHP completo fica assim
<?php
$destination_path = getcwd().DIRECTORY_SEPARATOR;
$result = 0;
$target_path = $destination_path . basename( $_FILES['myfile']['name']);
if (@move_uploaded_file($_FILES['myfile']['tmp_name'], $target_path))
{
    $result = 1;
}
sleep(1);
?>
Para concluir vamos dar uma olhada naquele iFrame que falamos no início:
A saída do código PHP será exibido/executado dentro do iFrame. Como você se lembra, o iFrame não estará visível, no entanto, podemos chamar uma função JavaScript nele. Na verdade é exatamente esse o ponto em que podemos chamar a função JavaScriptdefinida no código HTML para esconder a animação de progresso e exibir o resultado de upload de arquivos na página principal.
Nós podemos fazê-lo com o seguinte código JavaScript:
<script language="javascript" type="text/javascript">
window.top.window.stopUpload(<?php echo $result; ?>);
</script>


É isso aí. Qualquer dúvida fala aí nos comentários.
Bons estudos.






Um comentário:

  1. Otimo tutorial, mas fiquei com dúvida em relação ao php... Teria como detalhar um pouco mais? Grato

    ResponderExcluir