...was asked for some php file upload code, so I thought I would post some stripped down, barebones code that I use in admin/dashboard pages to add/change images associated with products.

Please see attached image for folder setup.

The code uses the jQuery Form plugin by Mike Alsup.

index.php has two forms; one for the image uploads and the other to show where you would have your "product add/update" form. Files are immediately uploaded to a tmp directory whenever you select an image. If you change your mind a few times you can end up with lots of images in your tmp folder, so there is a small routine to empty the tmp folder whenevery index.php is called.

//remove old tmp files
$tmpImageFolder = $_SERVER['DOCUMENT_ROOT'].'/assets/images/tmp';
$files = glob($tmpImageFolder.'/*.*');
if ($files){
    foreach($files as $filename){
<!DOCTYPE html>
    <title>Upload File Demo</title>
    /* hide the browse button */
    #input-file {
    <p><img id="display-image" src="/assets/images/placeholder.jpg"></p>
    <form id="upload" action="/ajax/uploadfile.php" method="post" enctype="multipart/form-data">
        <input id="input-file" name="file" type="file" value="" />
    <p><button id="choose-photo" type="button">Choose Photo</button></p>

    <!-- the product form handler can be ajax or standard post -->
    <form id="product-update">
        <!-- use a hidden field to send over new filename. hidden field is updated via the js uploadFile() function -->
        <input id="product-newfilename" type="hidden" value="">
        <!-- Your actual product form data goes here -->

    <script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
    <script src="/assets/js/jquery.form.min.js"></script>
    <script src="/assets/js/uploadform.js"></script>

CSS is used to remove the ugly "browse" input type="file" control and then jQuery is used to trigger the control when "Choose Photo" button (which can be nicely styled) is clicked. When an image is selected the jQuery Form is triggered and uploads the file to the forms action url.


    var reg=/(.jpg|.gif|.png)$/;
    if (!reg.test($("#input-file").val())) {
        alert('Invalid File Type');
        return false;


function uploadFile()
        dataType: 'json',
        success: function(data, statusText, xhr, wrapper){
            //update relevent product form fields here

uploadfile.php is a standard upload file handler which renames the uploaded and displays the new name.

Edited by JorgeM: moved the style element to the correct location in the code.


$tmpImageFolder = $_SERVER['DOCUMENT_ROOT'].'/assets/images/tmp';

//$actualFileName = $_FILES['file']['name'];
$ext = strtolower(pathinfo($_FILES['file']['name'], PATHINFO_EXTENSION));
//new filename based on time
$newFileName = microtime(true).'.'.$ext;

//retrieve uploaded file path (temporary stored by php engine)
$source = $_FILES['file']['tmp_name'];
$dest = $tmpImageFolder.'/'.$newFileName;

//move uploaded file to tmp

//you can scale the image here with your own image functions e.g.
//$i = new Image();

//display the new file name to be used by js/ajax success function
echo json_encode($newFileName);

3 Years
Discussion Span
Last Post by Imran_18

I moved your style block to the <head> section of the code for you. You can click on "flag bad post" in the future and a moderator will help you update the content accordingly if the option for you to edit your own post is no longer available.


$('#btn-import').click(function() {

        if ($("#frm-import").valid()) {

            $('#btn-import').attr('disabled', true);

            var fd = new FormData(document.getElementById("frm-import"));
            fd.append("school_id", $('#school_id').val());
            fd.append("import_type", $('#import_type').val());

                url: "<?php echo base_url(); ?>user/process-batch-import",
                type: "POST",
                data: fd,
                enctype: 'multipart/form-data',
                processData: false,  // tell jQuery not to process the data
                contentType: false,   // tell jQuery not to set contentType
                timeout: 30000 // Should set limit timeout: 30s, because if long time not response, client will post again --> got ISSUE

            }).done(function( response ) {

                $('#btn-import').attr('disabled', false);

                if(isValidJsonString(response)) {
                    var obj = jQuery.parseJSON(response);
                    var status = obj.status;

                    if (status == 0) {
                        var msg = obj.msg;

                        if (checkingImportProgress != null) {

                    } else {

Have something to contribute to this discussion? Please be thoughtful, detailed and courteous, and be sure to adhere to our posting rules.