TestNameEditsConfigs.java
上传用户:quxuerui
上传日期:2018-01-08
资源大小:41811k
文件大小:16k
源码类别:

网格计算

开发平台:

Java

  1. /**
  2.  * Licensed to the Apache Software Foundation (ASF) under one
  3.  * or more contributor license agreements.  See the NOTICE file
  4.  * distributed with this work for additional information
  5.  * regarding copyright ownership.  The ASF licenses this file
  6.  * to you under the Apache License, Version 2.0 (the
  7.  * "License"); you may not use this file except in compliance
  8.  * with the License.  You may obtain a copy of the License at
  9.  *
  10.  *     http://www.apache.org/licenses/LICENSE-2.0
  11.  *
  12.  * Unless required by applicable law or agreed to in writing, software
  13.  * distributed under the License is distributed on an "AS IS" BASIS,
  14.  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  15.  * See the License for the specific language governing permissions and
  16.  * limitations under the License.
  17.  */
  18. package org.apache.hadoop.hdfs.server.namenode;
  19. import junit.framework.TestCase;
  20. import java.io.*;
  21. import java.util.Random;
  22. import org.apache.hadoop.conf.Configuration;
  23. import org.apache.hadoop.hdfs.MiniDFSCluster;
  24. import org.apache.hadoop.fs.FSDataOutputStream;
  25. import org.apache.hadoop.fs.FileSystem;
  26. import org.apache.hadoop.fs.FileUtil;
  27. import org.apache.hadoop.fs.Path;
  28. /**
  29.  * This class tests various combinations of dfs.name.dir 
  30.  * and dfs.name.edits.dir configurations.
  31.  */
  32. public class TestNameEditsConfigs extends TestCase {
  33.   static final long SEED = 0xDEADBEEFL;
  34.   static final int BLOCK_SIZE = 4096;
  35.   static final int FILE_SIZE = 8192;
  36.   static final int NUM_DATA_NODES = 3;
  37.   static final String FILE_IMAGE = "current/fsimage";
  38.   static final String FILE_EDITS = "current/edits";
  39.   short replication = 3;
  40.   private File base_dir = new File(
  41.       System.getProperty("test.build.data", "build/test/data"), "dfs/");
  42.   protected void setUp() throws java.lang.Exception {
  43.     if(base_dir.exists())
  44.       tearDown();
  45.   }
  46.   protected void tearDown() throws java.lang.Exception {
  47.     if (!FileUtil.fullyDelete(base_dir)) 
  48.       throw new IOException("Cannot remove directory " + base_dir);
  49.   }
  50.   private void writeFile(FileSystem fileSys, Path name, int repl)
  51.     throws IOException {
  52.     FSDataOutputStream stm = fileSys.create(name, true,
  53.                                             fileSys.getConf().getInt("io.file.buffer.size", 4096),
  54.                                             (short)repl, (long)BLOCK_SIZE);
  55.     byte[] buffer = new byte[FILE_SIZE];
  56.     Random rand = new Random(SEED);
  57.     rand.nextBytes(buffer);
  58.     stm.write(buffer);
  59.     stm.close();
  60.   }
  61.   void checkImageAndEditsFilesExistence(File dir, 
  62.                                         boolean imageMustExist,
  63.                                         boolean editsMustExist) {
  64.     assertTrue(imageMustExist == new File(dir, FILE_IMAGE).exists());
  65.     assertTrue(editsMustExist == new File(dir, FILE_EDITS).exists());
  66.   }
  67.   private void checkFile(FileSystem fileSys, Path name, int repl)
  68.     throws IOException {
  69.     assertTrue(fileSys.exists(name));
  70.     int replication = fileSys.getFileStatus(name).getReplication();
  71.     assertEquals("replication for " + name, repl, replication);
  72.     long size = fileSys.getContentSummary(name).getLength();
  73.     assertEquals("file size for " + name, size, (long)FILE_SIZE);
  74.   }
  75.   private void cleanupFile(FileSystem fileSys, Path name)
  76.     throws IOException {
  77.     assertTrue(fileSys.exists(name));
  78.     fileSys.delete(name, true);
  79.     assertTrue(!fileSys.exists(name));
  80.   }
  81.   SecondaryNameNode startSecondaryNameNode(Configuration conf
  82.                                           ) throws IOException {
  83.     conf.set("dfs.secondary.http.address", "0.0.0.0:0");
  84.     return new SecondaryNameNode(conf);
  85.   }
  86.   /**
  87.    * Test various configuration options of dfs.name.dir and dfs.name.edits.dir
  88.    * The test creates files and restarts cluster with different configs.
  89.    * 1. Starts cluster with shared name and edits dirs
  90.    * 2. Restarts cluster by adding additional (different) name and edits dirs
  91.    * 3. Restarts cluster by removing shared name and edits dirs by allowing to 
  92.    *    start using separate name and edits dirs
  93.    * 4. Restart cluster by adding shared directory again, but make sure we 
  94.    *    do not read any stale image or edits. 
  95.    * All along the test, we create and delete files at reach restart to make
  96.    * sure we are reading proper edits and image.
  97.    */
  98.   public void testNameEditsConfigs() throws IOException {
  99.     Path file1 = new Path("TestNameEditsConfigs1");
  100.     Path file2 = new Path("TestNameEditsConfigs2");
  101.     Path file3 = new Path("TestNameEditsConfigs3");
  102.     MiniDFSCluster cluster = null;
  103.     SecondaryNameNode secondary = null;
  104.     Configuration conf = null;
  105.     FileSystem fileSys = null;
  106.     File newNameDir = new File(base_dir, "name");
  107.     File newEditsDir = new File(base_dir, "edits");
  108.     File nameAndEdits = new File(base_dir, "name_and_edits");
  109.     File checkpointNameDir = new File(base_dir, "secondname");
  110.     File checkpointEditsDir = new File(base_dir, "secondedits");
  111.     File checkpointNameAndEdits = new File(base_dir, "second_name_and_edits");
  112.     
  113.     // Start namenode with same dfs.name.dir and dfs.name.edits.dir
  114.     conf = new Configuration();
  115.     conf.set("dfs.name.dir", nameAndEdits.getPath());
  116.     conf.set("dfs.name.edits.dir", nameAndEdits.getPath());
  117.     conf.set("fs.checkpoint.dir", checkpointNameAndEdits.getPath());
  118.     conf.set("fs.checkpoint.edits.dir", checkpointNameAndEdits.getPath());
  119.     replication = (short)conf.getInt("dfs.replication", 3);
  120.     // Manage our own dfs directories
  121.     cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, true, false, true, null,
  122.                                   null, null, null);
  123.     cluster.waitActive();
  124.     secondary = startSecondaryNameNode(conf);
  125.     fileSys = cluster.getFileSystem();
  126.     try {
  127.       assertTrue(!fileSys.exists(file1));
  128.       writeFile(fileSys, file1, replication);
  129.       checkFile(fileSys, file1, replication);
  130.       secondary.doCheckpoint();
  131.     } finally {
  132.       fileSys.close();
  133.       cluster.shutdown();
  134.       secondary.shutdown();
  135.     }
  136.     // Start namenode with additional dfs.name.dir and dfs.name.edits.dir
  137.     conf =  new Configuration();
  138.     assertTrue(newNameDir.mkdir());
  139.     assertTrue(newEditsDir.mkdir());
  140.     conf.set("dfs.name.dir", nameAndEdits.getPath() +
  141.               "," + newNameDir.getPath());
  142.     conf.set("dfs.name.edits.dir", nameAndEdits.getPath() + 
  143.              "," + newEditsDir.getPath());
  144.     conf.set("fs.checkpoint.dir", checkpointNameDir.getPath() +
  145.              "," + checkpointNameAndEdits.getPath());
  146.     conf.set("fs.checkpoint.edits.dir", checkpointEditsDir.getPath() +
  147.              "," + checkpointNameAndEdits.getPath());
  148.     replication = (short)conf.getInt("dfs.replication", 3);
  149.     // Manage our own dfs directories. Do not format.
  150.     cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, false, false, true, 
  151.                                   null, null, null, null);
  152.     cluster.waitActive();
  153.     secondary = startSecondaryNameNode(conf);
  154.     fileSys = cluster.getFileSystem();
  155.     try {
  156.       assertTrue(fileSys.exists(file1));
  157.       checkFile(fileSys, file1, replication);
  158.       cleanupFile(fileSys, file1);
  159.       writeFile(fileSys, file2, replication);
  160.       checkFile(fileSys, file2, replication);
  161.       secondary.doCheckpoint();
  162.     } finally {
  163.       fileSys.close();
  164.       cluster.shutdown();
  165.       secondary.shutdown();
  166.     }
  167.     checkImageAndEditsFilesExistence(nameAndEdits, true, true);
  168.     checkImageAndEditsFilesExistence(newNameDir, true, false);
  169.     checkImageAndEditsFilesExistence(newEditsDir, false, true);
  170.     checkImageAndEditsFilesExistence(checkpointNameAndEdits, true, true);
  171.     checkImageAndEditsFilesExistence(checkpointNameDir, true, false);
  172.     checkImageAndEditsFilesExistence(checkpointEditsDir, false, true);
  173.     // Now remove common directory both have and start namenode with 
  174.     // separate name and edits dirs
  175.     new File(nameAndEdits, FILE_EDITS).renameTo(
  176.         new File(newNameDir, FILE_EDITS));
  177.     new File(nameAndEdits, FILE_IMAGE).renameTo(
  178.         new File(newEditsDir, FILE_IMAGE));
  179.     new File(checkpointNameAndEdits, FILE_EDITS).renameTo(
  180.         new File(checkpointNameDir, FILE_EDITS));
  181.     new File(checkpointNameAndEdits, FILE_IMAGE).renameTo(
  182.         new File(checkpointEditsDir, FILE_IMAGE));
  183.     conf =  new Configuration();
  184.     conf.set("dfs.name.dir", newNameDir.getPath());
  185.     conf.set("dfs.name.edits.dir", newEditsDir.getPath());
  186.     conf.set("fs.checkpoint.dir", checkpointNameDir.getPath());
  187.     conf.set("fs.checkpoint.edits.dir", checkpointEditsDir.getPath());
  188.     replication = (short)conf.getInt("dfs.replication", 3);
  189.     cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, false, false, true,
  190.                                   null, null, null, null);
  191.     cluster.waitActive();
  192.     secondary = startSecondaryNameNode(conf);
  193.     fileSys = cluster.getFileSystem();
  194.     try {
  195.       assertTrue(!fileSys.exists(file1));
  196.       assertTrue(fileSys.exists(file2));
  197.       checkFile(fileSys, file2, replication);
  198.       cleanupFile(fileSys, file2);
  199.       writeFile(fileSys, file3, replication);
  200.       checkFile(fileSys, file3, replication);
  201.       secondary.doCheckpoint();
  202.     } finally {
  203.       fileSys.close();
  204.       cluster.shutdown();
  205.       secondary.shutdown();
  206.     }
  207.     checkImageAndEditsFilesExistence(newNameDir, true, false);
  208.     checkImageAndEditsFilesExistence(newEditsDir, false, true);
  209.     checkImageAndEditsFilesExistence(checkpointNameDir, true, false);
  210.     checkImageAndEditsFilesExistence(checkpointEditsDir, false, true);
  211.     // Add old name_and_edits dir. File system should not read image or edits
  212.     // from old dir
  213.     assertTrue(FileUtil.fullyDelete(new File(nameAndEdits, "current")));
  214.     assertTrue(FileUtil.fullyDelete(new File(checkpointNameAndEdits, "current")));
  215.     conf = new Configuration();
  216.     conf.set("dfs.name.dir", nameAndEdits.getPath() +
  217.               "," + newNameDir.getPath());
  218.     conf.set("dfs.name.edits.dir", nameAndEdits +
  219.               "," + newEditsDir.getPath());
  220.     conf.set("fs.checkpoint.dir", checkpointNameDir.getPath() +
  221.         "," + checkpointNameAndEdits.getPath());
  222.     conf.set("fs.checkpoint.edits.dir", checkpointEditsDir.getPath() +
  223.         "," + checkpointNameAndEdits.getPath());
  224.     replication = (short)conf.getInt("dfs.replication", 3);
  225.     cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, false, false, true,
  226.                                   null, null, null, null);
  227.     cluster.waitActive();
  228.     secondary = startSecondaryNameNode(conf);
  229.     fileSys = cluster.getFileSystem();
  230.     try {
  231.       assertTrue(!fileSys.exists(file1));
  232.       assertTrue(!fileSys.exists(file2));
  233.       assertTrue(fileSys.exists(file3));
  234.       checkFile(fileSys, file3, replication);
  235.       secondary.doCheckpoint();
  236.     } finally {
  237.       fileSys.close();
  238.       cluster.shutdown();
  239.       secondary.shutdown();
  240.     }
  241.     checkImageAndEditsFilesExistence(nameAndEdits, true, true);
  242.     checkImageAndEditsFilesExistence(checkpointNameAndEdits, true, true);
  243.   }
  244.   /**
  245.    * Test various configuration options of dfs.name.dir and dfs.name.edits.dir
  246.    * This test tries to simulate failure scenarios.
  247.    * 1. Start cluster with shared name and edits dir
  248.    * 2. Restart cluster by adding separate name and edits dirs
  249.    * 3. Restart cluster by removing shared name and edits dir
  250.    * 4. Restart cluster with old shared name and edits dir, but only latest 
  251.    *    name dir. This should fail since we dont have latest edits dir
  252.    * 5. Restart cluster with old shared name and edits dir, but only latest
  253.    *    edits dir. This should fail since we dont have latest name dir
  254.    */
  255.   public void testNameEditsConfigsFailure() throws IOException {
  256.     Path file1 = new Path("TestNameEditsConfigs1");
  257.     Path file2 = new Path("TestNameEditsConfigs2");
  258.     Path file3 = new Path("TestNameEditsConfigs3");
  259.     MiniDFSCluster cluster = null;
  260.     Configuration conf = null;
  261.     FileSystem fileSys = null;
  262.     File newNameDir = new File(base_dir, "name");
  263.     File newEditsDir = new File(base_dir, "edits");
  264.     File nameAndEdits = new File(base_dir, "name_and_edits");
  265.     
  266.     // Start namenode with same dfs.name.dir and dfs.name.edits.dir
  267.     conf = new Configuration();
  268.     conf.set("dfs.name.dir", nameAndEdits.getPath());
  269.     conf.set("dfs.name.edits.dir", nameAndEdits.getPath());
  270.     replication = (short)conf.getInt("dfs.replication", 3);
  271.     // Manage our own dfs directories
  272.     cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, true, false, true, null,
  273.                                   null, null, null);
  274.     cluster.waitActive();
  275.     fileSys = cluster.getFileSystem();
  276.     try {
  277.       assertTrue(!fileSys.exists(file1));
  278.       writeFile(fileSys, file1, replication);
  279.       checkFile(fileSys, file1, replication);
  280.     } finally  {
  281.       fileSys.close();
  282.       cluster.shutdown();
  283.     }
  284.     // Start namenode with additional dfs.name.dir and dfs.name.edits.dir
  285.     conf =  new Configuration();
  286.     assertTrue(newNameDir.mkdir());
  287.     assertTrue(newEditsDir.mkdir());
  288.     conf.set("dfs.name.dir", nameAndEdits.getPath() +
  289.               "," + newNameDir.getPath());
  290.     conf.set("dfs.name.edits.dir", nameAndEdits.getPath() +
  291.               "," + newEditsDir.getPath());
  292.     replication = (short)conf.getInt("dfs.replication", 3);
  293.     // Manage our own dfs directories. Do not format.
  294.     cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, false, false, true, 
  295.                                   null, null, null, null);
  296.     cluster.waitActive();
  297.     fileSys = cluster.getFileSystem();
  298.     try {
  299.       assertTrue(fileSys.exists(file1));
  300.       checkFile(fileSys, file1, replication);
  301.       cleanupFile(fileSys, file1);
  302.       writeFile(fileSys, file2, replication);
  303.       checkFile(fileSys, file2, replication);
  304.     } finally {
  305.       fileSys.close();
  306.       cluster.shutdown();
  307.     }
  308.     
  309.     // Now remove common directory both have and start namenode with 
  310.     // separate name and edits dirs
  311.     conf =  new Configuration();
  312.     conf.set("dfs.name.dir", newNameDir.getPath());
  313.     conf.set("dfs.name.edits.dir", newEditsDir.getPath());
  314.     replication = (short)conf.getInt("dfs.replication", 3);
  315.     cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, false, false, true,
  316.                                   null, null, null, null);
  317.     cluster.waitActive();
  318.     fileSys = cluster.getFileSystem();
  319.     try {
  320.       assertTrue(!fileSys.exists(file1));
  321.       assertTrue(fileSys.exists(file2));
  322.       checkFile(fileSys, file2, replication);
  323.       cleanupFile(fileSys, file2);
  324.       writeFile(fileSys, file3, replication);
  325.       checkFile(fileSys, file3, replication);
  326.     } finally {
  327.       fileSys.close();
  328.       cluster.shutdown();
  329.     }
  330.     // Add old shared directory for name and edits along with latest name
  331.     conf = new Configuration();
  332.     conf.set("dfs.name.dir", newNameDir.getPath() + "," + 
  333.              nameAndEdits.getPath());
  334.     conf.set("dfs.name.edits.dir", nameAndEdits.getPath());
  335.     replication = (short)conf.getInt("dfs.replication", 3);
  336.     try {
  337.       cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, false, false, true,
  338.                                   null, null, null, null);
  339.       assertTrue(false);
  340.     } catch (IOException e) { // expect to fail
  341.       System.out.println("cluster start failed due to missing " +
  342.                          "latest edits dir");
  343.     } finally {
  344.       cluster = null;
  345.     }
  346.     // Add old shared directory for name and edits along with latest edits
  347.     conf = new Configuration();
  348.     conf.set("dfs.name.dir", nameAndEdits.getPath());
  349.     conf.set("dfs.name.edits.dir", newEditsDir.getPath() +
  350.              "," + nameAndEdits.getPath());
  351.     replication = (short)conf.getInt("dfs.replication", 3);
  352.     try {
  353.       cluster = new MiniDFSCluster(0, conf, NUM_DATA_NODES, false, false, true,
  354.                                    null, null, null, null);
  355.       assertTrue(false);
  356.     } catch (IOException e) { // expect to fail
  357.       System.out.println("cluster start failed due to missing latest name dir");
  358.     } finally {
  359.       cluster = null;
  360.     }
  361.   }
  362. }