{"record":{"id":"1dcb00b1f332ef3c","repo":"pentaho/pentaho-kettle","slug":"zipfile-error-notafolder","errorCode":null,"errorMessage":"ZipFile.Error.NotAFolder","messagePattern":"ZipFile\\.Error\\.NotAFolder","errorType":"exception","errorClass":"KettleException","httpStatus":null,"severity":"error","filePath":"engine/src/main/java/org/pentaho/di/trans/steps/zipfile/ZipFile.java","lineNumber":275,"sourceCode":"      }\n    }\n\n    return true;\n  }\n\n  private void processFile( String folder ) throws Exception {\n\n    switch ( meta.getOperationType() ) {\n      case ZipFileMeta.OPERATION_TYPE_MOVE:\n        FileObject file = null;\n        FileObject moveToFolder = null;\n        try {\n          // Move to folder\n          moveToFolder = KettleVFS.getInstance( getTransMeta().getBowl() ).getFileObject( folder, this );\n\n          if ( moveToFolder.exists() ) {\n            if ( moveToFolder.getType() != FileType.FOLDER ) {\n              throw new KettleException( BaseMessages.getString( PKG, \"ZipFile.Error.NotAFolder\", folder ) );\n            }\n          } else {\n            moveToFolder.createFolder();\n          }\n\n          // get target filename\n          String targetfilename =\n            KettleVFS.getFilename( moveToFolder )\n              + Const.FILE_SEPARATOR + data.sourceFile.getName().getBaseName();\n          file = KettleVFS.getInstance( getTransMeta().getBowl() ).getFileObject( targetfilename, this );\n\n          // Move file\n          data.sourceFile.moveTo( file );\n\n        } finally {\n          if ( file != null ) {\n            try {\n              file.close();","sourceCodeStart":257,"sourceCodeEnd":293,"githubUrl":"https://github.com/pentaho/pentaho-kettle/blob/f3058517a153da500bf4551f46d79b91bf8ec552/engine/src/main/java/org/pentaho/di/trans/steps/zipfile/ZipFile.java#L257-L293","documentation":"The ZipFile step throws this when the configured 'move to folder' path exists but is a regular file (or other non-folder VFS object), so the step cannot move processed source files into it. It is thrown from processFile after resolving the folder path via KettleVFS, before moving files, aborting the row processing.","triggerScenarios":"Running the ZipFile transformation step with a 'move files to folder' setting whose target path points at an existing non-directory file; moveToFolder.exists() is true but getType() != FileType.FOLDER.","commonSituations":"Typo or stale path in the 'Move/store files in folder' field that collides with an existing file; a variable/field substitution resolving to a file instead of a directory; a cleanup job replaced the folder with a file of the same name.","solutions":["Inspect the resolved folder path at runtime and ensure it is a directory (or does not exist, in which case the step creates it).","Remove or rename the regular file that currently occupies the target folder path.","Fix variable/field expressions feeding the movetofolderfield so they resolve to the intended directory path.","Enable 'Create parent folder' (createparentfolder) and use a fresh target directory name so the step creates it itself."],"exampleFix":"// before: target path 'out/archive' is an existing file\n// after: remove the conflicting file or point the step at a real directory\nrm /data/out/archive   # was a file blocking the folder path\nmkdir -p /data/out/archive","handlingStrategy":"validation","validationCode":"FileObject folder = KettleVFS.getInstance().getFileObject(path);\nif (folder.exists() && folder.getType() != FileType.FOLDER) {\n    throw new IllegalArgumentException(\"Move-to path is not a folder: \" + path);\n}","typeGuard":"boolean isFolder(FileObject f) throws FileSystemException {\n    return f != null && f.exists() && f.getType() == FileType.FOLDER;\n}","tryCatchPattern":"try {\n    runTransformation(zipFileTrans);\n} catch (KettleException e) {\n    if (e.getMessage().contains(\"NotAFolder\")) { /* fix/recreate the folder path */ }\n    throw e;\n}","preventionTips":["Pre-create the move-to folder in the ETL pipeline before the ZipFile step.","Never let file cleanup jobs replace directories with files at the same path.","Log the fully-resolved (variable-substituted) folder path at startup for verification."],"tags":["filesystem","vfs","kettle-step","configuration"],"backgroundTag":"path-is-not-a-directory","analyzedSha":"f3058517a153da500bf4551f46d79b91bf8ec552","analyzedAt":"2026-09-13T14:04:16.340Z","contentChangedAt":"2026-09-13T14:04:16.340Z","schemaVersion":2},"datasetVersion":"2026-09-20T23:17:15.980Z"}