pentaho/pentaho-kettle · error · FileSystemException

vfs.provider.local/create-folder.error

vfs.provider.local/create-folder.error

Error message

vfs.provider.local/create-folder.error

What it means

Thrown by S3CommonFileObject.doCreateFolder() when the S3 putObject call that creates a zero-byte folder-marker object (key ending with '/') fails with an AmazonS3Exception. VFS folders in S3 are emulated, so folder creation is really an S3 object PUT; any S3-side rejection surfaces as this FileSystemException.

Solutions

  1. Check the wrapped AmazonS3Exception message/error code for the real cause (AccessDenied, NoSuchBucket, etc.)
  2. Verify the AWS credentials/IAM policy allow s3:PutObject on the target bucket/key prefix
  3. Confirm the bucket exists and the region/endpoint in the VFS config matches the bucket's actual region
  4. Retry with backoff if the code is SlowDown/throttling

Example fix

// before
fileSystem.getS3Client().putObject( putObjectRequest );
// after
try {
  fileSystem.getS3Client().putObject( putObjectRequest );
} catch ( AmazonS3Exception e ) {
  if ( "SlowDown".equals( e.getErrorCode() ) ) { /* retry with backoff */ }
  throw new FileSystemException( "vfs.provider.local/create-folder.error", this, e );
}
Defensive patterns

Strategy: try-catch

Validate before calling

// before creating
FileObject f = fsManager.resolveFile( "s3://bucket/prefix/" );
if ( f.exists() ) { return; } // already there
// preflight: creds + bucket
s3Client.getObjectMetadata( bucketName, probeKey ); // throws if bucket/creds bad

Type guard

boolean isS3FolderCreatable( FileObject f ) {
  return f instanceof S3CommonFileObject && f.getName().getDepth() > 0;
}

Try / catch

try {
  fileObject.createFolder();
} catch ( FileSystemException e ) {
  Throwable cause = e.getCause();
  if ( cause instanceof AmazonS3Exception && "AccessDenied".equals( ((AmazonS3Exception) cause).getErrorCode() ) ) {
    // handle permissions problem
  }
  throw e;
}

Prevention

When it happens

Trigger: Calling createFolder() on an S3 VFS file object when putObject on the '<key>/' placeholder object returns an AmazonS3Exception (e.g. access denied, no such bucket, throttling).

Common situations: IAM policy missing s3:PutObject; typo'd or deleted bucket name; bucket in a region the client is misconfigured for; S3 rate limiting; KMS key not permitted for the caller.

Understand the failure class

Background: "failed to write file", "Could not save figure", "Error saving remote file" — file write failed: causes and fixes across languages and libraries — this error's family across 38 libraries.

Related errors


AI-assisted analysis of pentaho/pentaho-kettle@f3058517a1 (2026-09-13). Data as JSON: /api/errors/8b5ebf4aea9b489d. Report an issue: GitHub.

Appendix: source

Thrown at plugins/s3-vfs/core/src/main/java/org/pentaho/s3common/S3CommonFileObject.java:510

  @Override
  protected void doCreateFolder() throws Exception {
    if ( !isRootBucket() ) {
      // create meta-data for your folder and set content-length to 0
      ObjectMetadata metadata = new ObjectMetadata();
      metadata.setContentLength( 0 );
      metadata.setContentType( "binary/octet-stream" );

      // create empty content
      InputStream emptyContent = new ByteArrayInputStream( new byte[ 0 ] );

      // create a PutObjectRequest passing the folder name suffixed by /
      PutObjectRequest putObjectRequest = createPutObjectRequest( bucketName, key + DELIMITER, emptyContent, metadata );

      // send request to S3 to create folder
      try {
        fileSystem.getS3Client().putObject( putObjectRequest );
      } catch ( AmazonS3Exception e ) {
        throw new FileSystemException( "vfs.provider.local/create-folder.error", this, e );
      }
    } else {
      throw new FileSystemException( "vfs.provider/create-folder-not-supported.error" );
    }
  }


  protected PutObjectRequest createPutObjectRequest( String bucketName, String key, InputStream inputStream,
                                                     ObjectMetadata objectMetadata ) {
    return new PutObjectRequest( bucketName, key, inputStream, objectMetadata );
  }

  @Override
  protected void doRename( FileObject newFile ) throws Exception {
    // no folder renames on S3
    if ( getType().equals( FileType.FOLDER ) ) {
      logger.debug( "recursively moving folder [{}] -> [{}]", this.getPublicURIString(), newFile.getPublicURIString() );
      doFolderMove( this, newFile );

View on GitHub (pinned to f3058517a1)