chinabugotech/hutool · error · IllegalArgumentException
Destination Dir must be a Directory !
Error message
Destination Dir must be a Directory !
What it means
ImgUtil.sliceByRowsAndCols creates destDir if absent, but if a path exists at destDir that is NOT a directory (i.e. a regular file), it throws IllegalArgumentException. The precondition is that destDir must either not exist or be an actual directory.
Source
Thrown at hutool-core/src/main/java/cn/hutool/core/img/ImgUtil.java:544
public static void sliceByRowsAndCols(Image srcImage, File destDir, int rows, int cols) {
sliceByRowsAndCols(srcImage, destDir, IMAGE_TYPE_JPEG, rows, cols);
}
/**
* 图像切割(指定切片的行数和列数),默认RGB模式
*
* @param srcImage 源图像,如果非{@link BufferedImage},则默认使用RGB模式
* @param destDir 切片目标文件夹
* @param format 目标文件格式
* @param rows 目标切片行数。默认2,必须是范围 [1, 20] 之内
* @param cols 目标切片列数。默认2,必须是范围 [1, 20] 之内
* @since 5.8.6
*/
public static void sliceByRowsAndCols(Image srcImage, File destDir, String format, int rows, int cols) {
if (false == destDir.exists()) {
FileUtil.mkdir(destDir);
} else if (false == destDir.isDirectory()) {
throw new IllegalArgumentException("Destination Dir must be a Directory !");
}
if (rows <= 0 || rows > 20) {
rows = 2; // 切片行数
}
if (cols <= 0 || cols > 20) {
cols = 2; // 切片列数
}
// 读取源图像
int srcWidth = srcImage.getWidth(null); // 源图宽度
int srcHeight = srcImage.getHeight(null); // 源图高度
int destWidth = NumberUtil.partValue(srcWidth, cols); // 每张切片的宽度
int destHeight = NumberUtil.partValue(srcHeight, rows); // 每张切片的高度
// 循环建立切片
Image tag;
for (int i = 0; i < rows; i++) {View on GitHub (pinned to 8870454b2a)
Solutions
- Choose a destDir path that is exclusively a directory; delete or rename any conflicting file first.
- Check destDir: if it exists and isFile(), remove/rename it before calling slice.
- Use a dedicated, freshly created output folder per run.
Example fix
// before
ImgUtil.sliceByRowsAndCols(img, new File("out.png"), "png", 2, 2); // out.png is a file
// after
File dir = new File("out_slices");
if (dir.isFile()) dir.delete();
ImgUtil.sliceByRowsAndCols(img, dir, "png", 2, 2); Defensive patterns
Strategy: validation
Validate before calling
void requireDirTarget(File d){ if(d.exists() && !d.isDirectory()) throw new IllegalStateException("destDir is a file: "+d); } Type guard
boolean isUsableDirTarget(File d){ return d==null || !d.exists() || d.isDirectory(); } Try / catch
try { ImgUtil.sliceByRowsAndCols(img, dir, fmt, r, c); }
catch (IllegalArgumentException e){ if(e.getMessage().contains("must be a Directory")) { dir = new File(dir, "slices"); } else throw e; } Prevention
- Use dedicated output directories per job.
- Clear conflicting files before slicing.
- Prefer a fresh temp dir for slice output.
When it happens
Trigger: Passing a File for destDir whose path is already occupied by a regular file; reusing an output path that was previously a file; destDir pointing to a file created by another process.
Common situations: Output directory path colliding with an existing file; users passing the image's own path as destDir; CI artifacts left behind from a prior run.
Related errors
AI-assisted analysis of chinabugotech/hutool@8870454b2a (2026-08-14).
Data as JSON: /api/errors/e51eda7cb862c4a7.
Report an issue: GitHub.