pentaho/pentaho-kettle · error · KettleException
GPG.ExceptionWrite
Error message
GPG.ExceptionWrite
What it means
KettleException with key GPG.ExceptionWrite is thrown by GPG.execGnuPG when writing the passphrase (inputStr) to the GnuPG process's stdin fails with an IOException. GPG.java launches gpg as an external process and feeds the passphrase through a BufferedWriter on the process output stream; if the pipe is broken the write cannot proceed. This typically means the gpg process exited or was never started correctly before the passphrase could be delivered.
Solutions
- Verify the GnuPG executable location and that it runs (gpg --version) before invoking the job entry.
- Check the gpg command-line arguments built in execGnuPG for malformed quoting (userID/filename with embedded quotes).
- Confirm the passphrase/userID supplied to the entry are correct and non-empty; a bad gpg invocation can make the process exit before reading stdin.
- Catch KettleException and log the stderr captured by psr_stderr to identify why gpg died.
Example fix
// before
out.write( inputStr );
// after
if ( inputStr != null ) {
out.write( inputStr );
out.flush();
} else {
throw new KettleException( "No passphrase supplied to GPG" );
} Defensive patterns
Strategy: try-catch
Validate before calling
Process check = new ProcessBuilder("gpg", "--version").start();
if (check.waitFor() != 0) throw new IllegalStateException("gpg not usable"); Try / catch
try {
gpg.signFile(file, userId, signedFile, true);
} catch (KettleException ke) {
if (ke.getMessage().contains("GPG.ExceptionWrite")) {
// gpg died before reading passphrase; log and re-run diagnostics
}
} Prevention
- Verify gpg is installed and executable before running the entry
- Keep filenames and userIDs free of quotes/special characters
- Capture and log gpg stderr for diagnostics
When it happens
Trigger: Calling any of decryptFile, encryptFile, signAndEncryptFile, signFile, verifySignature, or verifyDetachedSignature when the underlying gpg process has terminated or its stdin pipe is broken, so out.write(inputStr) throws IOException.
Common situations: gpg binary path is wrong so the process died immediately; gpg crashed on bad arguments (e.g. malformed --passphrase-fd options); OS killed the process; passphrase contains characters that break the writer encoding setup.
Related errors
- Cannot open control file
- Cannot open data file
- ChangeFileEncoding.Error.CreatingFile
- Could not read file
- CubeInputMeta.Exception.ErrorOpeningOrReadingCubeFile
AI-assisted analysis of pentaho/pentaho-kettle@f3058517a1 (2026-09-13).
Data as JSON: /api/errors/166d6a5a88f288c5.
Report an issue: GitHub.
Appendix: source
Thrown at engine/src/main/java/org/pentaho/di/job/entries/pgpencryptfiles/GPG.java:196
p = Runtime.getRuntime().exec( command );
} else {
ProcessBuilder processBuilder = new ProcessBuilder( "/bin/sh", "-c", command );
p = processBuilder.start();
}
} catch ( IOException io ) {
throw new KettleException( BaseMessages.getString( PKG, "GPG.IOException" ), io );
}
ProcessStreamReader psr_stdout = new ProcessStreamReader( p.getInputStream() );
ProcessStreamReader psr_stderr = new ProcessStreamReader( p.getErrorStream() );
psr_stdout.start();
psr_stderr.start();
if ( inputStr != null ) {
BufferedWriter out = new BufferedWriter( new OutputStreamWriter( p.getOutputStream() ) );
try {
out.write( inputStr );
} catch ( IOException io ) {
throw new KettleException( BaseMessages.getString( PKG, "GPG.ExceptionWrite" ), io );
} finally {
if ( out != null ) {
try {
out.close();
} catch ( Exception e ) {
// Ignore
}
}
}
}
try {
p.waitFor();
psr_stdout.join();
psr_stderr.join();
} catch ( InterruptedException i ) {
throw new KettleException( BaseMessages.getString( PKG, "GPG.ExceptionWait" ), i );View on GitHub (pinned to f3058517a1)