apache/hadoop · error · IOException
Invalid reservationId: {} specified for the app: {}
Error message
Invalid reservationId: {} specified for the app: {} What it means
YARNRunner.submitJob reads mapreduce.job.reservation.id and passes it to ReservationId.parseReservationId. That method accepts 'reservation_<clusterTimestamp>_<seq>' and, when the prefix and field count pass but the timestamp or sequence part is not numeric, throws NumberFormatException. YARNRunner converts it into an IOException that names the bad value and the application ID, aborting job submission before the ApplicationSubmissionContext reaches the ResourceManager.
Source
Thrown at hadoop-mapreduce-project/hadoop-mapreduce-client/hadoop-mapreduce-client-jobclient/src/main/java/org/apache/hadoop/mapred/YARNRunner.java:622
ApplicationSubmissionContext appContext =
recordFactory.newRecordInstance(ApplicationSubmissionContext.class);
appContext.setApplicationId(applicationId); // ApplicationId
appContext.setQueue( // Queue name
jobConf.get(JobContext.QUEUE_NAME,
YarnConfiguration.DEFAULT_QUEUE_NAME));
// add reservationID if present
ReservationId reservationID = null;
try {
reservationID =
ReservationId.parseReservationId(jobConf
.get(JobContext.RESERVATION_ID));
} catch (NumberFormatException e) {
// throw exception as reservationid as is invalid
String errMsg =
"Invalid reservationId: " + jobConf.get(JobContext.RESERVATION_ID)
+ " specified for the app: " + applicationId;
LOG.warn(errMsg);
throw new IOException(errMsg);
}
if (reservationID != null) {
appContext.setReservationID(reservationID);
LOG.info("SUBMITTING ApplicationSubmissionContext app:" + applicationId
+ " to queue:" + appContext.getQueue() + " with reservationId:"
+ appContext.getReservationID());
}
appContext.setApplicationName( // Job name
jobConf.get(JobContext.JOB_NAME,
YarnConfiguration.DEFAULT_APPLICATION_NAME));
appContext.setCancelTokensWhenComplete(
conf.getBoolean(MRJobConfig.JOB_CANCEL_DELEGATION_TOKEN, true));
appContext.setAMContainerSpec(amContainer); // AM Container
appContext.setMaxAppAttempts(
conf.getInt(MRJobConfig.MR_AM_MAX_ATTEMPTS,
MRJobConfig.DEFAULT_MR_AM_MAX_ATTEMPTS));
// Setup the AM ResourceRequestsView on GitHub (pinned to 2add963021)
Solutions
- Use the exact string returned by ReservationId.toString() from the reservation system that created it (format: reservation_<clusterTimestamp>_<sequence>, both numeric)
- If no reservation is intended, unset mapreduce.job.reservation.id instead of leaving a placeholder value
- Validate the value with ReservationId.parseReservationId before job submission so the failure surfaces at the configuration boundary, not inside submitJob
- Check the ResourceManager/capacity scheduler reservationACLs and reservation system logs to re-obtain the correct ID if it came from an automation pipeline
Example fix
// before
conf.set("mapreduce.job.reservation.id", "res-2026-07-01");
// after
ReservationId rid = reservationClient.getReservationReservationId(...); // from ReservationSystem
conf.set("mapreduce.job.reservation.id", rid.toString()); // e.g. "reservation_1689372000000_0001" Defensive patterns
Strategy: validation
Validate before calling
String rid = conf.get(MRJobConfig.RESERVATION_ID); // mapreduce.job.reservation.id
if (rid != null) {
try {
ReservationId.parseReservationId(rid); // expects reservation_<ts>_<seq>, both numeric
} catch (IOException | NumberFormatException e) {
throw new IllegalArgumentException("Refusing to submit: bad reservation id: " + rid, e);
}
} Try / catch
try {
RunningJob job = jobClient.submitJob(jobConf);
} catch (IOException e) {
if (e.getMessage() != null && e.getMessage().startsWith("Invalid reservationId:")) {
// re-read the reservation from the ReservationSystem and resubmit
}
throw e;
} Prevention
- Always propagate the string from ReservationId.toString() instead of hand-formatting IDs
- Validate reservation IDs at CLI/service boundaries before they reach job conf
- Never leave placeholder values in mapreduce.job.reservation.id; unset the key instead
When it happens
Trigger: Setting mapreduce.job.reservation.id (JobContext.RESERVATION_ID) to a string like 'reservation_abc_1' or 'reservation_1234_xyz' (non-numeric timestamp/sequence fields), then calling JobClient.submitJob / YARNRunner.submitJob. Note: values with a wrong prefix or wrong underscore-field count fail inside parseReservationId with IOException before the NumberFormatException path, so this specific message implies the shape was right but a field was non-numeric.
Common situations: Hand-typed reservation IDs in scripts or CLI flags; reservation IDs copied with extra characters or split across shell variables; passing IDs generated by a different cluster or tool that formats timestamps with separators; forgetting that only IDs returned by the YARN ReservationSystem are valid.
Related errors
- "Not creating intermediate history logDir: [" + doneDirPath
- ShuffleProvider Service: {} was NOT found in the list of aux
- Invalid specification for distributed-cache artifacts of typ
- {} is incompatible with {} mode.
- Not submitting job. Job directory {} already exists!! This i
AI-assisted analysis of apache/hadoop@2add963021 (2026-08-22).
Data as JSON: /api/errors/df7411e8b859a868.
Report an issue: GitHub.