• Welcome to the Chevereto User Community!

    Here, users from all over the world come together to learn, share, and collaborate on everything related to Chevereto. It's a place to exchange ideas, ask questions, and help improve the software.

    Please keep in mind:

    • This community is user-driven. Always be polite and respectful to others.
    • Support development by purchasing a Chevereto license, which also gives you priority support.
    • Go further by joining the Community Subscription for even faster response times and to help sustain this space
  • Chevereto Support CLST

    Support response

    Support checklist

    • Got a Something went wrong message? Read this guide and provide the actual error. Do not skip this.
    • Confirm that the server meets the System Requirements
    • Check for any available Hotfix - your issue could be already reported/fixed
    • Read documentation - It will be required to Debug and understand Errors for a faster support response

FTP external storage ignores daily folder after update to 4.5.7 — files are saved to YYYY/MM instead of YYYY/MM/DD

evil

Chevereto Member

Reproduction steps​

  • Update Chevereto from version 4.5.5 to 4.5.7
  • Configure an external storage using FTP
  • Enable date-based upload folders using the YYYY/MM/DD structure
  • Upload a new image on a given day, for example 2026/09/07
  • Check the file location on the external FTP storage

Unexpected result​

  • The uploaded image is stored in:

    2026/09/image.jpg

    instead of:

    2026/09/07/image.jpg
  • The final directory for the current day is not created
  • All uploaded images are placed directly in the monthly directory
  • The upload itself appears to complete successfully
  • However, the uploaded image is not displayed because the application expects the file to exist in the daily directory, e.g. 2026/09/07/, while the actual file is stored in 2026/09/
This issue started after updating from 4.5.5 to 4.5.7.

Error log message​

No relevant error is displayed during the upload. The upload completes successfully, but the file is stored in an incorrect directory on the external FTP storage.
 
Hello,

Your analysis omits the fact that neither version 4.5.6 nor 4.5.7 touched the Ftp.php file, the last version which touched that file was 4.5.3.

Moved to server issues.
 
Unfortunately, this started immediately after I updated from 4.5.5 to 4.5.7, so I’m not sure what exactly changed or why it started happening.

What I can confirm is that when I switch the storage setting from date-based folders to direct storage without date folders, everything works correctly.

The issue only occurs when using the date-based folder structure.
 
Class Ftp doesn't depend on any external user land code as it is self-contained, meaning that this issue was a coincidence rather than caused by the upgrade as you presume.

PHP:
namespace Chevereto\Legacy\Classes;

use Exception;
use Throwable;

class Ftp
{

Class Ftp depends on the underlying FTP library installed with your PHP language installation, perhaps you can lookup for any change there and report back to us.
 
I performed an investigation and found a reproducible interaction between Ftp.php and Chevereto’s global error-reporting configuration.

Environment​

  • Chevereto: 4.5.7
  • PHP: 8.3.6
  • PHP package: php8.3-common 8.3.6-0ubuntu0.24.04.10
  • FTP extension enabled
  • FTP server reports UNIX
  • Passive FTP enabled
  • Date-based upload path generated by Chevereto: 2026/09/07/

Observed FTP behavior​

Using the active storage credentials and read-only FTP operations:

bucket_cwd_ok=true
year_cwd_ok=true
month_cwd_ok=true
day_cwd_ok=false
pwd_leaf=09
The FTP server behaves according to the PHP FTP contract: attempting to enter the missing 07 directory returns false, emits a warning and leaves the working directory at 09.

Relevant Chevereto code​

app/src/Legacy/Classes/Ftp.php, approximately lines 71–78:

public function chdir(string $path): void
{
try {
ftp_chdir($this->ftp, $path);
} catch (Throwable $e) {
throw new Exception("Unable to change dir '{$path}'", 600, $e);
}
}
The return value of ftp_chdir() is not checked.

According to PHP documentation, ftp_chdir() returns false and emits an E_WARNING when the directory change fails:

https://www.php.net/manual/en/function.ftp-chdir.php

The same pattern exists in mkdirRecursive():

try {
ftp_chdir($this->ftp, $cwd);
} catch (Throwable $e) {
try {
ftp_mkdir($this->ftp, $part);
} catch (Throwable $e) {
// ...
}

try {
ftp_chdir($this->ftp, $part);
} catch (Throwable $e) {
// ...
}
}
Neither ftp_chdir() nor ftp_mkdir() has its return value checked.

Interaction with​

During application bootstrap, Chevereto executes this in app/src/Legacy/functions.php, approximately line 1600:

if (cheveretoVersionInstalled() !== '') {
error_reporting(0);
Chevereto registers ThrowableHandler::ERROR_AS_EXCEPTION, but that handler contains logic equivalent to:

if (! (error_reporting() & $severity)) {
return;
}
Therefore, after error_reporting(0), FTP warnings are not converted into exceptions.

As a result, the catch blocks in Ftp.php do not run when an FTP function returns false.

Direct reproduction using Chevereto’s installed​

I reproduced the issue without creating directories or uploading files:

  1. Registered Chevereto’s ERROR_AS_EXCEPTION handler.
  2. Set error_reporting(0), matching the application runtime.
  3. Connected using the installed Chevereto\Legacy\Classes\Ftp.
  4. Entered the existing 2026/09/ directory.
  5. Called Ftp::chdir() for the missing 2026/09/07/.
  6. Inspected the resulting FTP working directory.
Result:

error_reporting=0
missing_day_threw=false
pwd_leaf_after_missing_day=09
Ftp::chdir() returned normally even though the requested directory did not exist, and the connection remained inside 09.

Resulting upload flow​

The likely execution path is:

  1. Image.php correctly generates 2026/09/07/.
  2. Storage.php calls:
    $API->mkdirRecursive($pathPrefix);
  3. ftp_chdir() for 07 returns false.
  4. Because warnings are disabled, no exception is thrown.
  5. The catch block containing ftp_mkdir() is skipped.
  6. Ftp:😛ut() again attempts chdir() but ignores its false result.
  7. The FTP connection remains in 2026/09/.
  8. ftp_put() successfully uploads the file into the month directory.
  9. Chevereto stores the expected date path in the database and later tries to load the file from 2026/09/07/.
This exactly matches the observed symptom.

Version comparison​

The following logic appears unchanged between the public 4.5.5 and 4.5.7 sources:

  • Generation of the Y/m/d/ prefix in Image.php
  • Passing keyprefix to Storage::uploadFiles()
  • Global error_reporting(0)
  • Throwable-handler registration
Therefore, this may be a latent defect exposed after the upgrade rather than a PHP FTP extension regression introduced at the same time.

The FTP extension behaves correctly according to its documented return contract.

Suggested fix​

Please check the return values explicitly instead of relying on warnings being converted into exceptions:

public function chdir(string $path): void
{
if (@ftp_chdir($this->ftp, $path) === false) {
throw new Exception("Unable to change dir '{$path}'", 600);
}
}
Inside mkdirRecursive():

if (@ftp_chdir($this->ftp, $cwd)) {
continue;
}

if (@ftp_mkdir($this->ftp, $part) === false) {
throw new Exception(
"Can't make recursive dir for {$part}",
600
);
}

if (@ftp_chdir($this->ftp, $part) === false) {
throw new Exception(
"Unable to change dir to {$part}",
600
);
}
The return value of ftp_put() should also be checked so that a failed transfer cannot be reported as successful.

I used OpenAI Codex, to assist with this diagnosis. 😉
 
Back
Top