pentaho/pentaho-kettle · error · KettleException

ChangeFileEncoding.Error.SourceFileNotExists

ChangeFileEncoding.Error.SourceFileNotExists

Error message

ChangeFileEncoding.Error.SourceFileNotExists

What it means

The Change File Encoding step resolves the source filename through KettleVFS and checks data.sourceFile.exists(). If the file does not exist on the filesystem/VFS, it throws this KettleException with the source path in the message. The step cannot re-encode a file it cannot open.

Solutions

  1. Check the exact path in the error message and confirm the file exists: ls '<path from message>'.
  2. Fix the source filename field value or the dynamic field so it points to an existing file.
  3. Convert to an absolute path or set the correct working directory / Kettle variables.
  4. Add an upstream 'Check if file exists' step or an ETL Metadata Injection guard to fail fast with a clearer message.

Example fix

// before: path built from an unset variable
String sourceFilename = "${INPUT_DIR}/data.txt"; // resolves literally
// after: resolve via VariableSpace
String sourceFilename = getTransMeta().environmentSubstitute( "${INPUT_DIR}" ) + "/data.txt";
Defensive patterns

Strategy: validation

Validate before calling

import java.io.File;
// Java caller-side check before running the transformation
File src = new File( resolvedSourcePath );
if ( !src.exists() ) {
  throw new IllegalStateException( "Source file missing: " + src.getAbsolutePath() );
}

Try / catch

try {
  trans.execute( null );
} catch ( KettleException e ) {
  if ( e.getMessage().contains( "SourceFileNotExists" ) ) {
    log.warn( "Source file missing, skipping: {}", e.getMessage() );
  } else { throw e; }
}

Prevention

When it happens

Trigger: In processRow: data.sourceFile = KettleVFS.getInstance(...).getFileObject(sourceFilename); then if (!data.sourceFile.exists()) throw — the resolved source path does not exist at run time.

Common situations: Typo in the source filename field value; the file was deleted or moved between pipeline planning and execution; relative path resolved against an unexpected working directory; wrong case sensitivity on Linux; a variable like ${FILE} is unset so the path is literal '/${FILE}'.

Understand the failure class

Background: "File not found" and ENOENT errors: why libraries can't find a file that should exist — this error's family across 50 libraries.

Related errors


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

Appendix: source

Thrown at plugins/core/impl/src/main/java/org/pentaho/di/trans/steps/changefileencoding/ChangeFileEncoding.java:139

      // get source filename
      String sourceFilename = data.inputRowMeta.getString( outputRow, data.indexOfFileename );
      if ( Utils.isEmpty( sourceFilename ) ) {
        throw new KettleException( BaseMessages.getString( PKG, "ChangeFileEncoding.Error.SourceFileIsEmpty",
          meta.getDynamicFilenameField() ) );
      }

      // get target filename
      String targetFilename = data.inputRowMeta.getString( outputRow, data.indexOfTargetFileename );
      if ( Utils.isEmpty( targetFilename ) ) {
        throw new KettleException( BaseMessages.getString( PKG, "ChangeFileEncoding.Error.TargetFileIsEmpty",
          meta.getTargetFilenameField() ) );
      }

      data.sourceFile = KettleVFS.getInstance( getTransMeta().getBowl() ).getFileObject( sourceFilename );

      // Check if source file exists
      if ( !data.sourceFile.exists() ) {
        throw new KettleException(
            BaseMessages.getString( PKG, "ChangeFileEncoding.Error.SourceFileNotExists", sourceFilename ) );
      }

      // Check if source file is a file
      if ( data.sourceFile.getType() != FileType.FILE ) {
        throw new KettleException(
            BaseMessages.getString( PKG, "ChangeFileEncoding.Error.SourceFileNotAFile", sourceFilename ) );
      }

      // create directory only if not exists
      if ( !data.sourceFile.getParent().exists() ) {
        if ( meta.isCreateParentFolder() ) {
          data.sourceFile.getParent().createFolder();
        } else {
          throw new KettleException( BaseMessages.getString( PKG, "ChangeFileEncoding.Error.ParentFolderNotExist",
            data.sourceFile.getParent().toString() ) );
        }
      }

View on GitHub (pinned to f3058517a1)