pentaho/pentaho-kettle · error · KettleException
Failed to copy directory into itself
Error message
Failed to copy directory into itself
What it means
Thrown by renameDirectory when id_directory equals id_directory_parent, i.e. a rename/move is requested that would make a directory its own parent. The library explicitly blocks this because a directory cannot contain itself. It is a pre-validation guard, thrown before any database write.
Solutions
- Check that the new parent directory is not the directory being moved before calling the API
- Compare ObjectIds: if id_directory.equals(id_directory_parent), abort or pick a different parent
- In UI code, disable dropping a node onto itself
- Ensure RepositoryDirectory.getObjectId() is set (null-vs-set confusion can lead to wrong comparisons)
Example fix
// before
repository.renameRepositoryDirectory( dirId, repo.findDirectory( "/a/b" ), null ); // if /a/b IS dirId -> throws
// after
RepositoryDirectoryInterface parent = repo.findDirectory( "/a/b" );
if ( !parent.getObjectId().equals( dirId ) ) {
repository.renameRepositoryDirectory( dirId, parent, null );
} Defensive patterns
Strategy: validation
Validate before calling
if ( id_directory.equals( id_directory_parent ) ) {
throw new IllegalArgumentException( "Target parent must differ from the directory being moved" );
} Type guard
boolean isValidMoveTarget( ObjectId sourceId, RepositoryDirectoryInterface newParent ) {
return newParent != null && !newParent.getObjectId().equals( sourceId );
} Prevention
- Compare ObjectIds of source and new parent before any move
- In UI code, disable dropping a node onto itself
- Compute parent directories from distinct variables to avoid self-assignment
- Set ObjectIds explicitly before comparisons to avoid null/sentinel mismatches
When it happens
Trigger: Calling repository.renameRepositoryDirectory(id, newParentDir, newName) where newParentDir is the directory being moved itself, or calling the delegate's renameDirectory(id, id, name) directly with identical ObjectIds.
Common situations: UI drag-and-drop mishandled so a folder is dropped onto itself; code that computes the target parent from the same variable used for the source; off-by-one in tree navigation passing the same node as parent.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- Directory cannot become a child to itself
- A connection of type PALO is expected
- A connection of type PALO is expected
- A server socket allocation always has to accompanied by a…
- A server socket allocation always has to accompanied by…
AI-assisted analysis of pentaho/pentaho-kettle@f3058517a1 (2026-09-13).
Data as JSON: /api/errors/d72dcf0a32eb1cf4.
Report an issue: GitHub.
Appendix: source
Thrown at engine/src/main/java/org/pentaho/di/repository/kdr/delegates/KettleDatabaseRepositoryDirectoryDelegate.java:214
}
repository.directoryDelegate.deleteDirectory( dir.getObjectId() );
}
/**
* Move / rename a directory in the repository
*
* @param id_directory
* Id of the directory to be moved/renamed
* @param id_directory_parent
* Id of the new parent directory (null if the parent does not change)
* @param newName
* New name for this directory (null if the name does not change)
* @throws KettleException
*/
public synchronized void renameDirectory( ObjectId id_directory, ObjectId id_directory_parent, String newName ) throws KettleException {
if ( id_directory.equals( id_directory_parent ) ) {
// Make sure the directory cannot become its own parent
throw new KettleException( "Failed to copy directory into itself" );
} else {
// Make sure the directory does not become a descendant of itself
RepositoryDirectory rd = new RepositoryDirectory();
loadRepositoryDirectory( rd, id_directory );
if ( rd.findDirectory( id_directory_parent ) != null ) {
// The parent directory is a child of this directory. Do not proceed
throw new KettleException( "Directory cannot become a child to itself" );
} else {
// Check for duplication
RepositoryDirectory newParent = new RepositoryDirectory();
loadRepositoryDirectory( newParent, id_directory_parent );
RepositoryDirectory child = newParent.findChild( newName == null ? rd.getName() : newName );
if ( child != null ) {
throw new KettleException( "Destination directory already contains a diectory with requested name" );
}
}
}
View on GitHub (pinned to f3058517a1)