001 /** 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018 019 package org.apache.hadoop.yarn.client.api; 020 021 import java.io.IOException; 022 import java.util.EnumSet; 023 import java.util.List; 024 import java.util.Map; 025 import java.util.Set; 026 027 import org.apache.hadoop.classification.InterfaceAudience; 028 import org.apache.hadoop.classification.InterfaceAudience.Private; 029 import org.apache.hadoop.classification.InterfaceAudience.Public; 030 import org.apache.hadoop.classification.InterfaceStability; 031 import org.apache.hadoop.classification.InterfaceStability.Unstable; 032 import org.apache.hadoop.io.Text; 033 import org.apache.hadoop.service.AbstractService; 034 import org.apache.hadoop.yarn.api.ApplicationClientProtocol; 035 import org.apache.hadoop.yarn.api.protocolrecords.GetApplicationReportRequest; 036 import org.apache.hadoop.yarn.api.protocolrecords.ReservationDeleteRequest; 037 import org.apache.hadoop.yarn.api.protocolrecords.ReservationDeleteResponse; 038 import org.apache.hadoop.yarn.api.protocolrecords.ReservationSubmissionRequest; 039 import org.apache.hadoop.yarn.api.protocolrecords.ReservationSubmissionResponse; 040 import org.apache.hadoop.yarn.api.protocolrecords.ReservationUpdateRequest; 041 import org.apache.hadoop.yarn.api.protocolrecords.ReservationUpdateResponse; 042 import org.apache.hadoop.yarn.api.protocolrecords.SubmitApplicationRequest; 043 import org.apache.hadoop.yarn.api.records.ApplicationAttemptId; 044 import org.apache.hadoop.yarn.api.records.ApplicationAttemptReport; 045 import org.apache.hadoop.yarn.api.records.ApplicationId; 046 import org.apache.hadoop.yarn.api.records.ApplicationReport; 047 import org.apache.hadoop.yarn.api.records.ApplicationSubmissionContext; 048 import org.apache.hadoop.yarn.api.records.ContainerId; 049 import org.apache.hadoop.yarn.api.records.ContainerReport; 050 import org.apache.hadoop.yarn.api.records.NodeId; 051 import org.apache.hadoop.yarn.api.records.NodeReport; 052 import org.apache.hadoop.yarn.api.records.NodeState; 053 import org.apache.hadoop.yarn.api.records.QueueInfo; 054 import org.apache.hadoop.yarn.api.records.QueueUserACLInfo; 055 import org.apache.hadoop.yarn.api.records.ReservationDefinition; 056 import org.apache.hadoop.yarn.api.records.ReservationId; 057 import org.apache.hadoop.yarn.api.records.Token; 058 import org.apache.hadoop.yarn.api.records.YarnApplicationState; 059 import org.apache.hadoop.yarn.api.records.YarnClusterMetrics; 060 import org.apache.hadoop.yarn.client.api.impl.YarnClientImpl; 061 import org.apache.hadoop.yarn.exceptions.ApplicationIdNotProvidedException; 062 import org.apache.hadoop.yarn.exceptions.ApplicationNotFoundException; 063 import org.apache.hadoop.yarn.exceptions.YarnException; 064 import org.apache.hadoop.yarn.security.AMRMTokenIdentifier; 065 066 @InterfaceAudience.Public 067 @InterfaceStability.Stable 068 public abstract class YarnClient extends AbstractService { 069 070 /** 071 * Create a new instance of YarnClient. 072 */ 073 @Public 074 public static YarnClient createYarnClient() { 075 YarnClient client = new YarnClientImpl(); 076 return client; 077 } 078 079 @Private 080 protected YarnClient(String name) { 081 super(name); 082 } 083 084 /** 085 * <p> 086 * Obtain a {@link YarnClientApplication} for a new application, 087 * which in turn contains the {@link ApplicationSubmissionContext} and 088 * {@link org.apache.hadoop.yarn.api.protocolrecords.GetNewApplicationResponse} 089 * objects. 090 * </p> 091 * 092 * @return {@link YarnClientApplication} built for a new application 093 * @throws YarnException 094 * @throws IOException 095 */ 096 public abstract YarnClientApplication createApplication() 097 throws YarnException, IOException; 098 099 /** 100 * <p> 101 * Submit a new application to <code>YARN.</code> It is a blocking call - it 102 * will not return {@link ApplicationId} until the submitted application is 103 * submitted successfully and accepted by the ResourceManager. 104 * </p> 105 * 106 * <p> 107 * Users should provide an {@link ApplicationId} as part of the parameter 108 * {@link ApplicationSubmissionContext} when submitting a new application, 109 * otherwise it will throw the {@link ApplicationIdNotProvidedException}. 110 * </p> 111 * 112 * <p>This internally calls {@link ApplicationClientProtocol#submitApplication 113 * (SubmitApplicationRequest)}, and after that, it internally invokes 114 * {@link ApplicationClientProtocol#getApplicationReport 115 * (GetApplicationReportRequest)} and waits till it can make sure that the 116 * application gets properly submitted. If RM fails over or RM restart 117 * happens before ResourceManager saves the application's state, 118 * {@link ApplicationClientProtocol 119 * #getApplicationReport(GetApplicationReportRequest)} will throw 120 * the {@link ApplicationNotFoundException}. This API automatically resubmits 121 * the application with the same {@link ApplicationSubmissionContext} when it 122 * catches the {@link ApplicationNotFoundException}</p> 123 * 124 * @param appContext 125 * {@link ApplicationSubmissionContext} containing all the details 126 * needed to submit a new application 127 * @return {@link ApplicationId} of the accepted application 128 * @throws YarnException 129 * @throws IOException 130 * @see #createApplication() 131 */ 132 public abstract ApplicationId submitApplication( 133 ApplicationSubmissionContext appContext) throws YarnException, 134 IOException; 135 136 /** 137 * <p> 138 * Kill an application identified by given ID. 139 * </p> 140 * 141 * @param applicationId 142 * {@link ApplicationId} of the application that needs to be killed 143 * @throws YarnException 144 * in case of errors or if YARN rejects the request due to 145 * access-control restrictions. 146 * @throws IOException 147 * @see #getQueueAclsInfo() 148 */ 149 public abstract void killApplication(ApplicationId applicationId) throws YarnException, 150 IOException; 151 152 /** 153 * <p> 154 * Get a report of the given Application. 155 * </p> 156 * 157 * <p> 158 * In secure mode, <code>YARN</code> verifies access to the application, queue 159 * etc. before accepting the request. 160 * </p> 161 * 162 * <p> 163 * If the user does not have <code>VIEW_APP</code> access then the following 164 * fields in the report will be set to stubbed values: 165 * <ul> 166 * <li>host - set to "N/A"</li> 167 * <li>RPC port - set to -1</li> 168 * <li>client token - set to "N/A"</li> 169 * <li>diagnostics - set to "N/A"</li> 170 * <li>tracking URL - set to "N/A"</li> 171 * <li>original tracking URL - set to "N/A"</li> 172 * <li>resource usage report - all values are -1</li> 173 * </ul> 174 * </p> 175 * 176 * @param appId 177 * {@link ApplicationId} of the application that needs a report 178 * @return application report 179 * @throws YarnException 180 * @throws IOException 181 */ 182 public abstract ApplicationReport getApplicationReport(ApplicationId appId) 183 throws YarnException, IOException; 184 185 /** 186 * Get the AMRM token of the application. 187 * <p/> 188 * The AMRM token is required for AM to RM scheduling operations. For 189 * managed Application Masters Yarn takes care of injecting it. For unmanaged 190 * Applications Masters, the token must be obtained via this method and set 191 * in the {@link org.apache.hadoop.security.UserGroupInformation} of the 192 * current user. 193 * <p/> 194 * The AMRM token will be returned only if all the following conditions are 195 * met: 196 * <li> 197 * <ul>the requester is the owner of the ApplicationMaster</ul> 198 * <ul>the application master is an unmanaged ApplicationMaster</ul> 199 * <ul>the application master is in ACCEPTED state</ul> 200 * </li> 201 * Else this method returns NULL. 202 * 203 * @param appId {@link ApplicationId} of the application to get the AMRM token 204 * @return the AMRM token if available 205 * @throws YarnException 206 * @throws IOException 207 */ 208 public abstract org.apache.hadoop.security.token.Token<AMRMTokenIdentifier> 209 getAMRMToken(ApplicationId appId) throws YarnException, IOException; 210 211 /** 212 * <p> 213 * Get a report (ApplicationReport) of all Applications in the cluster. 214 * </p> 215 * 216 * <p> 217 * If the user does not have <code>VIEW_APP</code> access for an application 218 * then the corresponding report will be filtered as described in 219 * {@link #getApplicationReport(ApplicationId)}. 220 * </p> 221 * 222 * @return a list of reports of all running applications 223 * @throws YarnException 224 * @throws IOException 225 */ 226 public abstract List<ApplicationReport> getApplications() 227 throws YarnException, IOException; 228 229 /** 230 * <p> 231 * Get a report (ApplicationReport) of Applications 232 * matching the given application types in the cluster. 233 * </p> 234 * 235 * <p> 236 * If the user does not have <code>VIEW_APP</code> access for an application 237 * then the corresponding report will be filtered as described in 238 * {@link #getApplicationReport(ApplicationId)}. 239 * </p> 240 * 241 * @param applicationTypes 242 * @return a list of reports of applications 243 * @throws YarnException 244 * @throws IOException 245 */ 246 public abstract List<ApplicationReport> getApplications( 247 Set<String> applicationTypes) throws YarnException, IOException; 248 249 /** 250 * <p> 251 * Get a report (ApplicationReport) of Applications matching the given 252 * application states in the cluster. 253 * </p> 254 * 255 * <p> 256 * If the user does not have <code>VIEW_APP</code> access for an application 257 * then the corresponding report will be filtered as described in 258 * {@link #getApplicationReport(ApplicationId)}. 259 * </p> 260 * 261 * @param applicationStates 262 * @return a list of reports of applications 263 * @throws YarnException 264 * @throws IOException 265 */ 266 public abstract List<ApplicationReport> 267 getApplications(EnumSet<YarnApplicationState> applicationStates) 268 throws YarnException, IOException; 269 270 /** 271 * <p> 272 * Get a report (ApplicationReport) of Applications matching the given 273 * application types and application states in the cluster. 274 * </p> 275 * 276 * <p> 277 * If the user does not have <code>VIEW_APP</code> access for an application 278 * then the corresponding report will be filtered as described in 279 * {@link #getApplicationReport(ApplicationId)}. 280 * </p> 281 * 282 * @param applicationTypes 283 * @param applicationStates 284 * @return a list of reports of applications 285 * @throws YarnException 286 * @throws IOException 287 */ 288 public abstract List<ApplicationReport> getApplications( 289 Set<String> applicationTypes, 290 EnumSet<YarnApplicationState> applicationStates) throws YarnException, 291 IOException; 292 293 /** 294 * <p> 295 * Get metrics ({@link YarnClusterMetrics}) about the cluster. 296 * </p> 297 * 298 * @return cluster metrics 299 * @throws YarnException 300 * @throws IOException 301 */ 302 public abstract YarnClusterMetrics getYarnClusterMetrics() throws YarnException, 303 IOException; 304 305 /** 306 * <p> 307 * Get a report of nodes ({@link NodeReport}) in the cluster. 308 * </p> 309 * 310 * @param states The {@link NodeState}s to filter on. If no filter states are 311 * given, nodes in all states will be returned. 312 * @return A list of node reports 313 * @throws YarnException 314 * @throws IOException 315 */ 316 public abstract List<NodeReport> getNodeReports(NodeState... states) 317 throws YarnException, IOException; 318 319 /** 320 * <p> 321 * Get a delegation token so as to be able to talk to YARN using those tokens. 322 * 323 * @param renewer 324 * Address of the renewer who can renew these tokens when needed by 325 * securely talking to YARN. 326 * @return a delegation token ({@link Token}) that can be used to 327 * talk to YARN 328 * @throws YarnException 329 * @throws IOException 330 */ 331 public abstract Token getRMDelegationToken(Text renewer) 332 throws YarnException, IOException; 333 334 /** 335 * <p> 336 * Get information ({@link QueueInfo}) about a given <em>queue</em>. 337 * </p> 338 * 339 * @param queueName 340 * Name of the queue whose information is needed 341 * @return queue information 342 * @throws YarnException 343 * in case of errors or if YARN rejects the request due to 344 * access-control restrictions. 345 * @throws IOException 346 */ 347 public abstract QueueInfo getQueueInfo(String queueName) throws YarnException, 348 IOException; 349 350 /** 351 * <p> 352 * Get information ({@link QueueInfo}) about all queues, recursively if there 353 * is a hierarchy 354 * </p> 355 * 356 * @return a list of queue-information for all queues 357 * @throws YarnException 358 * @throws IOException 359 */ 360 public abstract List<QueueInfo> getAllQueues() throws YarnException, IOException; 361 362 /** 363 * <p> 364 * Get information ({@link QueueInfo}) about top level queues. 365 * </p> 366 * 367 * @return a list of queue-information for all the top-level queues 368 * @throws YarnException 369 * @throws IOException 370 */ 371 public abstract List<QueueInfo> getRootQueueInfos() throws YarnException, IOException; 372 373 /** 374 * <p> 375 * Get information ({@link QueueInfo}) about all the immediate children queues 376 * of the given queue 377 * </p> 378 * 379 * @param parent 380 * Name of the queue whose child-queues' information is needed 381 * @return a list of queue-information for all queues who are direct children 382 * of the given parent queue. 383 * @throws YarnException 384 * @throws IOException 385 */ 386 public abstract List<QueueInfo> getChildQueueInfos(String parent) throws YarnException, 387 IOException; 388 389 /** 390 * <p> 391 * Get information about <em>acls</em> for <em>current user</em> on all the 392 * existing queues. 393 * </p> 394 * 395 * @return a list of queue acls ({@link QueueUserACLInfo}) for 396 * <em>current user</em> 397 * @throws YarnException 398 * @throws IOException 399 */ 400 public abstract List<QueueUserACLInfo> getQueueAclsInfo() throws YarnException, 401 IOException; 402 403 /** 404 * <p> 405 * Get a report of the given ApplicationAttempt. 406 * </p> 407 * 408 * <p> 409 * In secure mode, <code>YARN</code> verifies access to the application, queue 410 * etc. before accepting the request. 411 * </p> 412 * 413 * @param applicationAttemptId 414 * {@link ApplicationAttemptId} of the application attempt that needs 415 * a report 416 * @return application attempt report 417 * @throws YarnException 418 * @throws {@link ApplicationAttemptNotFoundException} if application attempt 419 * not found 420 * @throws IOException 421 */ 422 public abstract ApplicationAttemptReport getApplicationAttemptReport( 423 ApplicationAttemptId applicationAttemptId) throws YarnException, IOException; 424 425 /** 426 * <p> 427 * Get a report of all (ApplicationAttempts) of Application in the cluster. 428 * </p> 429 * 430 * @param applicationId 431 * @return a list of reports for all application attempts for specified 432 * application. 433 * @throws YarnException 434 * @throws IOException 435 */ 436 public abstract List<ApplicationAttemptReport> getApplicationAttempts( 437 ApplicationId applicationId) throws YarnException, IOException; 438 439 /** 440 * <p> 441 * Get a report of the given Container. 442 * </p> 443 * 444 * <p> 445 * In secure mode, <code>YARN</code> verifies access to the application, queue 446 * etc. before accepting the request. 447 * </p> 448 * 449 * @param containerId 450 * {@link ContainerId} of the container that needs a report 451 * @return container report 452 * @throws YarnException 453 * @throws {@link ContainerNotFoundException} if container not found. 454 * @throws IOException 455 */ 456 public abstract ContainerReport getContainerReport(ContainerId containerId) 457 throws YarnException, IOException; 458 459 /** 460 * <p> 461 * Get a report of all (Containers) of ApplicationAttempt in the cluster. 462 * </p> 463 * 464 * @param applicationAttemptId 465 * @return a list of reports of all containers for specified application 466 * attempts 467 * @throws YarnException 468 * @throws IOException 469 */ 470 public abstract List<ContainerReport> getContainers( 471 ApplicationAttemptId applicationAttemptId) throws YarnException, 472 IOException; 473 474 /** 475 * <p> 476 * Attempts to move the given application to the given queue. 477 * </p> 478 * 479 * @param appId 480 * Application to move. 481 * @param queue 482 * Queue to place it in to. 483 * @throws YarnException 484 * @throws IOException 485 */ 486 public abstract void moveApplicationAcrossQueues(ApplicationId appId, 487 String queue) throws YarnException, IOException; 488 489 /** 490 * <p> 491 * The interface used by clients to submit a new reservation to the 492 * {@code ResourceManager}. 493 * </p> 494 * 495 * <p> 496 * The client packages all details of its request in a 497 * {@link ReservationSubmissionRequest} object. This contains information 498 * about the amount of capacity, temporal constraints, and gang needs. 499 * Furthermore, the reservation might be composed of multiple stages, with 500 * ordering dependencies among them. 501 * </p> 502 * 503 * <p> 504 * In order to respond, a new admission control component in the 505 * {@code ResourceManager} performs an analysis of the resources that have 506 * been committed over the period of time the user is requesting, verify that 507 * the user requests can be fulfilled, and that it respect a sharing policy 508 * (e.g., {@code CapacityOverTimePolicy}). Once it has positively determined 509 * that the ReservationRequest is satisfiable the {@code ResourceManager} 510 * answers with a {@link ReservationSubmissionResponse} that includes a 511 * {@link ReservationId}. Upon failure to find a valid allocation the response 512 * is an exception with the message detailing the reason of failure. 513 * </p> 514 * 515 * <p> 516 * The semantics guarantees that the {@link ReservationId} returned, 517 * corresponds to a valid reservation existing in the time-range request by 518 * the user. The amount of capacity dedicated to such reservation can vary 519 * overtime, depending of the allocation that has been determined. But it is 520 * guaranteed to satisfy all the constraint expressed by the user in the 521 * {@link ReservationDefinition} 522 * </p> 523 * 524 * @param request request to submit a new Reservation 525 * @return response contains the {@link ReservationId} on accepting the 526 * submission 527 * @throws YarnException if the reservation cannot be created successfully 528 * @throws IOException 529 * 530 */ 531 @Public 532 @Unstable 533 public abstract ReservationSubmissionResponse submitReservation( 534 ReservationSubmissionRequest request) throws YarnException, IOException; 535 536 /** 537 * <p> 538 * The interface used by clients to update an existing Reservation. This is 539 * referred to as a re-negotiation process, in which a user that has 540 * previously submitted a Reservation. 541 * </p> 542 * 543 * <p> 544 * The allocation is attempted by virtually substituting all previous 545 * allocations related to this Reservation with new ones, that satisfy the new 546 * {@link ReservationDefinition}. Upon success the previous allocation is 547 * atomically substituted by the new one, and on failure (i.e., if the system 548 * cannot find a valid allocation for the updated request), the previous 549 * allocation remains valid. 550 * </p> 551 * 552 * @param request to update an existing Reservation (the 553 * {@link ReservationUpdateRequest} should refer to an existing valid 554 * {@link ReservationId}) 555 * @return response empty on successfully updating the existing reservation 556 * @throws YarnException if the request is invalid or reservation cannot be 557 * updated successfully 558 * @throws IOException 559 * 560 */ 561 @Public 562 @Unstable 563 public abstract ReservationUpdateResponse updateReservation( 564 ReservationUpdateRequest request) throws YarnException, IOException; 565 566 /** 567 * <p> 568 * The interface used by clients to remove an existing Reservation. 569 * </p> 570 * 571 * @param request to remove an existing Reservation (the 572 * {@link ReservationDeleteRequest} should refer to an existing valid 573 * {@link ReservationId}) 574 * @return response empty on successfully deleting the existing reservation 575 * @throws YarnException if the request is invalid or reservation cannot be 576 * deleted successfully 577 * @throws IOException 578 * 579 */ 580 @Public 581 @Unstable 582 public abstract ReservationDeleteResponse deleteReservation( 583 ReservationDeleteRequest request) throws YarnException, IOException; 584 585 /** 586 * <p> 587 * The interface used by client to get node to labels mappings in existing cluster 588 * </p> 589 * 590 * @return node to labels mappings 591 * @throws YarnException 592 * @throws IOException 593 */ 594 @Public 595 @Unstable 596 public abstract Map<NodeId, Set<String>> getNodeToLabels() 597 throws YarnException, IOException; 598 599 /** 600 * <p> 601 * The interface used by client to get node labels in the cluster 602 * </p> 603 * 604 * @return cluster node labels collection 605 * @throws YarnException 606 * @throws IOException 607 */ 608 @Public 609 @Unstable 610 public abstract Set<String> getClusterNodeLabels() 611 throws YarnException, IOException; 612 }