didi/DoKit · error · IllegalArgumentException
Path must not be empty.
Error message
Path must not be empty.
What it means
DokitPicasso.load(String path) treats null as a deliberate no-op request (placeholder-only) but rejects empty or whitespace-only strings with IllegalArgumentException('Path must not be empty.'), because Uri.parse("") would produce a request no handler can serve. It is an argument-contract error: the caller passed a string, but it carries no usable location.
Source
Thrown at Android/dokit/src/main/java/com/didichuxing/doraemonkit/picasso/DokitPicasso.java:298
* <p>
* This path may be a remote URL, file resource (prefixed with {@code file:}), content resource
* (prefixed with {@code content:}), or android resource (prefixed with {@code
* android.resource:}.
* <p>
* Passing {@code null} as a {@code path} will not trigger any request but will set a
* placeholder, if one is specified.
*
* @see #load(Uri)
* @see #load(File)
* @see #load(int)
* @throws IllegalArgumentException if {@code path} is empty or blank string.
*/
public RequestCreator load(String path) {
if (path == null) {
return new RequestCreator(this, null, 0);
}
if (path.trim().length() == 0) {
throw new IllegalArgumentException("Path must not be empty.");
}
return load(Uri.parse(path));
}
/**
* Start an image request using the specified image file. This is a convenience method for
* calling {@link #load(Uri)}.
* <p>
* Passing {@code null} as a {@code file} will not trigger any request but will set a
* placeholder, if one is specified.
* <p>
* Equivalent to calling {@link #load(Uri) load(Uri.fromFile(file))}.
*
* @see #load(Uri)
* @see #load(String)
* @see #load(int)
*/
public RequestCreator load(File file) {View on GitHub (pinned to 626827cddb)
Solutions
- Normalize before loading: treat blank strings as absent, same as null
- Fix the producer so optional fields are null rather than empty strings
- Use .error(placeholder) plus the guard so the UI still shows something
Example fix
// before
DokitPicasso.with(context).load(item.avatarUrl).into(avatar); // avatarUrl == ""
// after
RequestCreator rq = (item.avatarUrl == null || item.avatarUrl.trim().isEmpty())
? DokitPicasso.with(context).load(R.drawable.avatar_placeholder)
: DokitPicasso.with(context).load(item.avatarUrl);
rq.into(avatar); Defensive patterns
Strategy: validation
Validate before calling
static boolean isBlank(String s) { return s == null || s.trim().isEmpty(); }
RequestCreator rq = isBlank(path)
? picasso.load(R.drawable.placeholder)
: picasso.load(path);
rq.into(view); Try / catch
// Cheap guard makes try-catch unnecessary; if calling untrusted code:
try {
picasso.load(path).into(view);
} catch (IllegalArgumentException e) {
if ("Path must not be empty.".equals(e.getMessage())) {
view.setImageResource(R.drawable.placeholder);
} else throw e;
} Prevention
- Normalize optional image fields to null at the data layer; treat blank as absent
- Kotlin: model URLs as String? and gate loads with if (!url.isNullOrBlank())
- Add .error(placeholder) everywhere optional images load
When it happens
Trigger: load("") or load(" ") from a model field that was never populated; data binding where the path expression evaluates to empty; trailing/leading whitespace introduced by JSON trimming bugs; lint-blocking null checks converted to empty strings.
Common situations: Feed items with an optional image URL where the server sends "" instead of null; getString(R.string.x) returning empty in flavor builds.
Related errors
AI-assisted analysis of didi/DoKit@626827cddb (2026-08-14).
Data as JSON: /api/errors/b8a91e88ff960f53.
Report an issue: GitHub.