Search code examples
codeignitercodeigniter-4

CI4 - Trying to move image but get error "could not move file php6WkH2s to /var/www/example.com/development.example.com/app_dir/public/ ()


I am trying to upload a file and move it to public/ folder. The file uploads without problem to writable folder, however, it is the moving to the public folder that has a problem.

Here is my code;

$update_post->move(ROOTPATH.'public/', $update_post.'.'.$fileType);

Path is correct. When I echo out echo ROOTPATH.'public/'; and then manually copy/paste, I do get to the destination directory.

Permissions correct. There are my permission on the public/ directory:

drwxr-xr-x  9 www-data www-data  4096 Jan 30 01:08 public

Any hints appreciated.


Solution

  • Reason:

    It's because the move(string $targetPath, ?string $name = null, bool $overwrite = false) method's $name argument is invalid.

    $update_post->move( ... , $update_post.'.'.$fileType);

    Explanation:

    Concatenating an class CodeIgniter\Files\File extends SplFileInfo instance calls the inherited SplFileInfo class's __toString() method which returns the path to the file as a string.

    Note that it doesn't return the filename, which is what you're interested in.

    Solution:

    You should instead pass in the basename instead.

    $update_post->move(
        ROOTPATH . 'public/',
        $update_post->getBasename()
    );
    

    Alternatively, since you're not changing the destination filename, it's cleaner to just not pass in the second parameter of the move(...) method. I.e:

    
    $update_post->move(
        ROOTPATH . 'public'
    );
    
    

    Addendum:

    If you wish to change the destination filename to a new name, try this instead:

    guessExtension()

    Attempts to determine the file extension based on the trusted getMimeType() method. If the mime type is unknown, will return null. This is often a more trusted source than simply using the extension provided by the filename. Uses the values in app/Config/Mimes.php to determine extension:

    
    $newFileName = "site_logo"; // New filename without suffixing it with a file extension.
    $fileExtension = $update_post->guessExtension();
    
    $update_post->move(
        ROOTPATH . 'public',
        $newFileName . (empty($fileExtension) ? '' : '.' . $fileExtension)
    );
    
    

    Notes:

    The move(...) method returns a new File instance for the relocated file, so you must capture the result if the resulting location is needed: $newRelocatedFileInstance = $update_post->move(...);