pentaho/pentaho-kettle · error · KettleException
JobGetMailsFromPOP.Error.NotAFolderNot
Error message
JobGetMailsFromPOP.Error.NotAFolderNot
What it means
createOutputDirectory() resolves the output folder via KettleVFS and checks folder.exists(); if the path exists but its VFS FileType is not FileType.FOLDER (e.g. a regular file or symlink to a file), the entry throws this KettleException with the folder name as a message parameter. It prevents attempting folder operations (createFolder, message writes) on a non-directory path.
Solutions
- Remove or rename the file that occupies the configured output path, then let the entry create/verify the directory.
- Point the 'Output directory' field at a directory path (trailing path segment, not a filename).
- Check the resolved variable value (log it or test in a Get Variable step) to make sure it expands to the intended directory.
Example fix
// before output directory = /data/mails.bak (a file) // after output directory = /data/mails (directory, file moved aside)
Defensive patterns
Strategy: validation
Validate before calling
File out = new File(environmentSubstitute(getOutputFolder()));
if (out.exists() && !out.isDirectory()) {
throw new IllegalArgumentException("Output path exists but is not a directory: " + out);
} Try / catch
try { executeJobEntry(); } catch (KettleException e) {
if (e.getMessage().contains("NotAFolderNot")) {
logError("Configured output path is a file, not a directory: " + e.getMessage());
} else { throw e; }
} Prevention
- Point output directory at a directory path, never a file.
- Check for leftover files at the configured path after archive/cleanup jobs.
- Log the resolved variable value before running in production.
When it happens
Trigger: createOutputDirectory(FOLDER_OUTPUT) where the resolved folderName exists on disk/VFS as a file, not a directory.
Common situations: User points the output directory at an existing file (e.g. a zip or log file path); a variable expansion produced a filename rather than a directory; a previous run created a file at the intended folder path.
Related errors
- JobGetMailsFromPOP.Error.AttachmentFolderNotAFolder
- JobGetMailsFromPOP.Error.AttachmentFolderEmpty
- JobGetMailsFromPOP.Error.AttachmentFolderNotExist
- JobGetMailsFromPOP.Error.OutputFolderEmpty
- JobGetMailsFromPOP.Error.OutputFolderNotExist
AI-assisted analysis of pentaho/pentaho-kettle@f3058517a1 (2026-09-13).
Data as JSON: /api/errors/57213aa443a1c355.
Report an issue: GitHub.
Appendix: source
Thrown at plugins/email-messages/impl/src/main/java/org/pentaho/di/job/entries/getpop/JobEntryGetPOP.java:1590
} else {
folderName = getRealOutputDirectory();
}
break;
}
if ( Utils.isEmpty( folderName ) ) {
switch ( folderType ) {
case JobEntryGetPOP.FOLDER_OUTPUT:
throw new KettleException( BaseMessages.getString( PKG, "JobGetMailsFromPOP.Error.OutputFolderEmpty" ) );
case JobEntryGetPOP.FOLDER_ATTACHMENTS:
throw new KettleException( BaseMessages.getString( PKG, "JobGetMailsFromPOP.Error.AttachmentFolderEmpty" ) );
}
}
FileObject folder = KettleVFS.getInstance( parentJobMeta.getBowl() ).getFileObject( folderName, this );
if ( folder.exists() ) {
if ( folder.getType() != FileType.FOLDER ) {
switch ( folderType ) {
case JobEntryGetPOP.FOLDER_OUTPUT:
throw new KettleException( BaseMessages.getString(
PKG, "JobGetMailsFromPOP.Error.NotAFolderNot", folderName ) );
case JobEntryGetPOP.FOLDER_ATTACHMENTS:
throw new KettleException( BaseMessages.getString(
PKG, "JobGetMailsFromPOP.Error.AttachmentFolderNotAFolder", folderName ) );
}
}
if ( isDebug() ) {
switch ( folderType ) {
case JobEntryGetPOP.FOLDER_OUTPUT:
logDebug( BaseMessages.getString( PKG, "JobGetMailsFromPOP.Log.OutputFolderExists", folderName ) );
break;
case JobEntryGetPOP.FOLDER_ATTACHMENTS:
logDebug( BaseMessages.getString( PKG, "JobGetMailsFromPOP.Log.AttachmentFolderExists", folderName ) );
break;
}
}
} else {
if ( isCreateLocalFolder() ) {View on GitHub (pinned to f3058517a1)