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 */ 018package org.apache.hadoop.hbase.regionserver.storefiletracker; 019 020import java.io.IOException; 021import java.io.PrintStream; 022import org.apache.commons.lang3.StringUtils; 023import org.apache.hadoop.conf.Configuration; 024import org.apache.hadoop.conf.Configured; 025import org.apache.hadoop.fs.FileSystem; 026import org.apache.hadoop.fs.LocatedFileStatus; 027import org.apache.hadoop.fs.Path; 028import org.apache.hadoop.fs.RemoteIterator; 029import org.apache.hadoop.hbase.HBaseConfiguration; 030import org.apache.hadoop.hbase.HBaseInterfaceAudience; 031import org.apache.hadoop.hbase.HConstants; 032import org.apache.hadoop.hbase.TableName; 033import org.apache.hadoop.hbase.util.CommonFSUtils; 034import org.apache.hadoop.util.Tool; 035import org.apache.hadoop.util.ToolRunner; 036import org.apache.yetus.audience.InterfaceAudience; 037import org.apache.yetus.audience.InterfaceStability; 038import org.slf4j.Logger; 039import org.slf4j.LoggerFactory; 040 041import org.apache.hbase.thirdparty.org.apache.commons.cli.CommandLine; 042import org.apache.hbase.thirdparty.org.apache.commons.cli.CommandLineParser; 043import org.apache.hbase.thirdparty.org.apache.commons.cli.HelpFormatter; 044import org.apache.hbase.thirdparty.org.apache.commons.cli.Option; 045import org.apache.hbase.thirdparty.org.apache.commons.cli.OptionGroup; 046import org.apache.hbase.thirdparty.org.apache.commons.cli.Options; 047import org.apache.hbase.thirdparty.org.apache.commons.cli.ParseException; 048import org.apache.hbase.thirdparty.org.apache.commons.cli.PosixParser; 049 050import org.apache.hadoop.hbase.shaded.protobuf.generated.StoreFileTrackerProtos.StoreFileList; 051 052@InterfaceAudience.LimitedPrivate(HBaseInterfaceAudience.TOOLS) 053@InterfaceStability.Evolving 054public class StoreFileListFilePrettyPrinter extends Configured implements Tool { 055 private static final Logger LOG = LoggerFactory.getLogger(StoreFileListFilePrettyPrinter.class); 056 057 private Options options = new Options(); 058 059 private final String fileOption = "f"; 060 private final String columnFamilyOption = "cf"; 061 private final String regionOption = "r"; 062 private final String tableNameOption = "t"; 063 064 private final String cmdString = "sft"; 065 066 private String namespace; 067 private String regionName; 068 private String columnFamily; 069 private String tableName; 070 private Path path; 071 private PrintStream err = System.err; 072 private PrintStream out = System.out; 073 074 public StoreFileListFilePrettyPrinter() { 075 super(); 076 init(); 077 } 078 079 public StoreFileListFilePrettyPrinter(Configuration conf) { 080 super(conf); 081 init(); 082 } 083 084 private void init() { 085 OptionGroup files = new OptionGroup(); 086 options.addOption(new Option(tableNameOption, "table", true, 087 "Table to scan. Pass table name; e.g. test_table")); 088 options.addOption(new Option(columnFamilyOption, "columnfamily", true, 089 "column family to scan. Pass column family name; e.g. f")); 090 files.addOption(new Option(regionOption, "region", true, 091 "Region to scan. Pass region name; e.g. '3d58e9067bf23e378e68c071f3dd39eb'")); 092 files.addOption(new Option(fileOption, "file", true, 093 "File to scan. Pass full-path; e.g. /root/hbase-3.0.0-alpha-4-SNAPSHOT/hbase-data/" 094 + "data/default/tbl-sft/093fa06bf84b3b631007f951a14b8457/f/.filelist/f2.1655139542249")); 095 options.addOptionGroup(files); 096 } 097 098 public boolean parseOptions(String[] args) throws ParseException, IOException { 099 HelpFormatter formatter = new HelpFormatter(); 100 if (args.length == 0) { 101 formatter.printHelp(cmdString, options, true); 102 return false; 103 } 104 105 CommandLineParser parser = new PosixParser(); 106 CommandLine cmd = parser.parse(options, args); 107 108 if (cmd.hasOption(fileOption)) { 109 path = new Path(cmd.getOptionValue(fileOption)); 110 } else { 111 regionName = cmd.getOptionValue(regionOption); 112 if (StringUtils.isEmpty(regionName)) { 113 err.println("Region name is not specified."); 114 formatter.printHelp(cmdString, options, true); 115 System.exit(1); 116 } 117 columnFamily = cmd.getOptionValue(columnFamilyOption); 118 if (StringUtils.isEmpty(columnFamily)) { 119 err.println("Column family is not specified."); 120 formatter.printHelp(cmdString, options, true); 121 System.exit(1); 122 } 123 String tableNameWtihNS = cmd.getOptionValue(tableNameOption); 124 if (StringUtils.isEmpty(tableNameWtihNS)) { 125 err.println("Table name is not specified."); 126 formatter.printHelp(cmdString, options, true); 127 System.exit(1); 128 } 129 TableName tn = TableName.valueOf(tableNameWtihNS); 130 namespace = tn.getNamespaceAsString(); 131 tableName = tn.getNameAsString(); 132 } 133 return true; 134 } 135 136 public int run(String[] args) { 137 if (getConf() == null) { 138 throw new RuntimeException("A Configuration instance must be provided."); 139 } 140 boolean pass = true; 141 try { 142 CommonFSUtils.setFsDefault(getConf(), CommonFSUtils.getRootDir(getConf())); 143 if (!parseOptions(args)) { 144 return 1; 145 } 146 } catch (IOException ex) { 147 LOG.error("Error parsing command-line options", ex); 148 return 1; 149 } catch (ParseException ex) { 150 LOG.error("Error parsing command-line options", ex); 151 return 1; 152 } 153 FileSystem fs = null; 154 if (path != null) { 155 try { 156 fs = path.getFileSystem(getConf()); 157 if (fs.isDirectory(path)) { 158 err.println("ERROR, wrong path given: " + path); 159 return 2; 160 } 161 return print(fs, path); 162 } catch (IOException e) { 163 LOG.error("Error reading " + path, e); 164 return 2; 165 } 166 } else { 167 try { 168 Path root = CommonFSUtils.getRootDir(getConf()); 169 Path baseDir = new Path(root, HConstants.BASE_NAMESPACE_DIR); 170 Path nameSpacePath = new Path(baseDir, namespace); 171 Path tablePath = new Path(nameSpacePath, tableName); 172 Path regionPath = new Path(tablePath, regionName); 173 Path cfPath = new Path(regionPath, columnFamily); 174 Path sftPath = new Path(cfPath, StoreFileListFile.TRACK_FILE_DIR); 175 176 fs = FileSystem.newInstance(regionPath.toUri(), getConf()); 177 178 RemoteIterator<LocatedFileStatus> iterator = fs.listFiles(sftPath, false); 179 180 while (iterator.hasNext()) { 181 LocatedFileStatus lfs = iterator.next(); 182 if ( 183 lfs.isFile() 184 && StoreFileListFile.TRACK_FILE_PATTERN.matcher(lfs.getPath().getName()).matches() 185 ) { 186 out.println("Printing contents for file " + lfs.getPath().toString()); 187 int ret = print(fs, lfs.getPath()); 188 if (ret != 0) { 189 pass = false; 190 } 191 } 192 } 193 } catch (IOException e) { 194 LOG.error("Error processing " + e); 195 return 2; 196 } 197 } 198 return pass ? 0 : 2; 199 } 200 201 private int print(FileSystem fs, Path path) throws IOException { 202 try { 203 if (!fs.exists(path)) { 204 err.println("ERROR, file doesnt exist: " + path); 205 return 2; 206 } 207 } catch (IOException e) { 208 err.println("ERROR, reading file: " + path + e); 209 return 2; 210 } 211 StoreFileList storeFile = StoreFileListFile.load(fs, path); 212 int end = storeFile.getStoreFileCount(); 213 for (int i = 0; i < end; i++) { 214 out.println(storeFile.getStoreFile(i).getName()); 215 } 216 return 0; 217 } 218 219 public static void main(String[] args) throws Exception { 220 Configuration conf = HBaseConfiguration.create(); 221 int ret = ToolRunner.run(conf, new StoreFileListFilePrettyPrinter(), args); 222 System.exit(ret); 223 } 224}