{"record":{"id":"9b9cf8d735bf7b14","repo":"apache/hadoop","slug":"dst-already-exists","errorCode":null,"errorMessage":"{dst} already exists.","messagePattern":"(.+?) already exists\\.","errorType":"validation","errorClass":"IOException","httpStatus":null,"severity":"error","filePath":"hadoop-tools/hadoop-federation-balance/src/main/java/org/apache/hadoop/tools/fedbalance/DistCpProcedure.java","lineNumber":188,"sourceCode":"      return false;\n    case FINISH:\n      finish();\n      return true;\n    default:\n      throw new IOException(\"Unexpected stage=\" + stage);\n    }\n  }\n\n  /**\n   * Pre check of src and dst.\n   */\n  void preCheck() throws IOException {\n    FileStatus status = srcFs.getFileStatus(src);\n    if (!status.isDirectory()) {\n      throw new IOException(src + \" should be a directory.\");\n    }\n    if (dstFs.exists(dst)) {\n      throw new IOException(dst + \" already exists.\");\n    }\n    if (srcFs.exists(new Path(src, HdfsConstants.DOT_SNAPSHOT_DIR))) {\n      throw new IOException(src + \" shouldn't enable snapshot.\");\n    }\n    updateStage(Stage.INIT_DISTCP);\n  }\n\n  /**\n   * The initial distcp. Copying src to dst.\n   */\n  void initDistCp() throws IOException, RetryException {\n    RunningJobStatus job = getCurrentJob();\n    if (job != null) {\n      // the distcp has been submitted.\n      if (job.isComplete()) {\n        jobId = null; // unset jobId because the job is done.\n        if (job.isSuccessful()) {\n          updateStage(Stage.DIFF_DISTCP);","sourceCodeStart":170,"sourceCodeEnd":206,"githubUrl":"https://github.com/apache/hadoop/blob/2add9630210752f88ceb1bb74eb65e37bf41da8e/hadoop-tools/hadoop-federation-balance/src/main/java/org/apache/hadoop/tools/fedbalance/DistCpProcedure.java#L170-L206","documentation":"The second clause of DistCpProcedure.preCheck(): the destination must NOT exist, because the initial distcp creates it and later stages compute diffs against that copy. If dstFs.exists(dst) is true, the balance job aborts before any data is moved. Distinguish it from error 5046: this check runs at procedure start (preCheck), while 5046 fires during (re)submission of the initial distcp job itself.","triggerScenarios":"Submitting a fedbalance job whose -dst already exists: leftover output from a previous failed run, a directory pre-created by provisioning tooling, or running the same balance command twice.","commonSituations":"Re-running a balance job that failed midway without cleaning up; operators pre-creating the destination 'to save time'; -dst accidentally pointing at existing production data.","solutions":["If dst is a leftover from an earlier attempt, delete it ('hdfs dfs -rm -r <dst>') and resubmit the job.","Otherwise choose a fresh destination path that does not exist yet.","Never pre-create dst; fedbalance/distcp creates it as part of the initial copy."],"exampleFix":"# before\nhdfs fedbalance -src hdfs://ns1/data -dst hdfs://ns2/data   # /data already exists\n\n# after\nhdfs dfs -rm -r hdfs://ns2/data   # if it is a leftover\nhdfs fedbalance -src hdfs://ns1/data -dst hdfs://ns2/data/incoming-run1","handlingStrategy":"validation","validationCode":"Path dst = new Path(\"hdfs://ns2/balance/data\");\nFileSystem dstFs = dst.getFileSystem(conf);\nif (dstFs.exists(dst)) {\n  throw new IllegalStateException(\"dst already exists; delete it or pick a fresh path before fedbalance\");\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never pre-create the fedbalance destination; the initial distcp creates it.","Automate cleanup of failed runs (delete dst) before resubmitting a balance job."],"tags":["fedbalance","federation-balance","precheck","destination-exists","distcp"],"backgroundTag":"destination-path-exists","analyzedSha":"2add9630210752f88ceb1bb74eb65e37bf41da8e","analyzedAt":"2026-08-22T19:55:07.957Z","schemaVersion":2},"datasetVersion":"2026-08-22T20:17:22.307Z"}