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    package org.apache.hadoop.hdfs.tools;
019    
020    import java.io.PrintStream;
021    import java.util.Arrays;
022    import java.util.Collection;
023    
024    import org.apache.commons.logging.Log;
025    import org.apache.commons.logging.LogFactory;
026    import org.apache.hadoop.conf.Configuration;
027    import org.apache.hadoop.fs.CommonConfigurationKeys;
028    import org.apache.hadoop.ha.HAAdmin;
029    import org.apache.hadoop.ha.HAServiceTarget;
030    import org.apache.hadoop.hdfs.DFSConfigKeys;
031    import org.apache.hadoop.hdfs.DFSUtil;
032    import org.apache.hadoop.hdfs.HdfsConfiguration;
033    import org.apache.hadoop.util.ToolRunner;
034    
035    /**
036     * Class to extend HAAdmin to do a little bit of HDFS-specific configuration.
037     */
038    public class DFSHAAdmin extends HAAdmin {
039    
040      private static final Log LOG = LogFactory.getLog(DFSHAAdmin.class);
041    
042      private String nameserviceId;
043    
044      protected void setErrOut(PrintStream errOut) {
045        this.errOut = errOut;
046      }
047      
048      protected void setOut(PrintStream out) {
049        this.out = out;
050      }
051    
052      @Override
053      public void setConf(Configuration conf) {
054        if (conf != null) {
055          conf = addSecurityConfiguration(conf);
056        }
057        super.setConf(conf);
058      }
059    
060      /**
061       * Add the requisite security principal settings to the given Configuration,
062       * returning a copy.
063       * @param conf the original config
064       * @return a copy with the security settings added
065       */
066      public static Configuration addSecurityConfiguration(Configuration conf) {
067        // Make a copy so we don't mutate it. Also use an HdfsConfiguration to
068        // force loading of hdfs-site.xml.
069        conf = new HdfsConfiguration(conf);
070        String nameNodePrincipal = conf.get(
071            DFSConfigKeys.DFS_NAMENODE_KERBEROS_PRINCIPAL_KEY, "");
072        if (LOG.isDebugEnabled()) {
073          LOG.debug("Using NN principal: " + nameNodePrincipal);
074        }
075    
076        conf.set(CommonConfigurationKeys.HADOOP_SECURITY_SERVICE_USER_NAME_KEY,
077            nameNodePrincipal);
078        return conf;
079      }
080    
081      /**
082       * Try to map the given namenode ID to its service address.
083       */
084      @Override
085      protected HAServiceTarget resolveTarget(String nnId) {
086        HdfsConfiguration conf = (HdfsConfiguration)getConf();
087        return new NNHAServiceTarget(conf, nameserviceId, nnId);
088      }
089    
090      @Override
091      protected String getUsageString() {
092        return "Usage: DFSHAAdmin [-ns <nameserviceId>]";
093      }
094    
095      @Override
096      protected int runCmd(String[] argv) throws Exception {
097        if (argv.length < 1) {
098          printUsage(errOut);
099          return -1;
100        }
101    
102        int i = 0;
103        String cmd = argv[i++];
104    
105        if ("-ns".equals(cmd)) {
106          if (i == argv.length) {
107            errOut.println("Missing nameservice ID");
108            printUsage(errOut);
109            return -1;
110          }
111          nameserviceId = argv[i++];
112          if (i >= argv.length) {
113            errOut.println("Missing command");
114            printUsage(errOut);
115            return -1;
116          }
117          argv = Arrays.copyOfRange(argv, i, argv.length);
118        }
119        
120        return super.runCmd(argv);
121      }
122      
123      /**
124       * returns the list of all namenode ids for the given configuration 
125       */
126      @Override
127      protected Collection<String> getTargetIds(String namenodeToActivate) {
128        return DFSUtil.getNameNodeIds(getConf(), (nameserviceId != null)? nameserviceId : DFSUtil.getNamenodeNameServiceId(getConf()));
129      }
130      
131      public static void main(String[] argv) throws Exception {
132        int res = ToolRunner.run(new DFSHAAdmin(), argv);
133        System.exit(res);
134      }
135    }