package com.linkedin.databus.bootstrap.utils; /* * * Copyright 2013 LinkedIn Corp. All rights reserved * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY * KIND, either express or implied. See the License for the * specific language governing permissions and limitations * under the License. * */ import java.io.FileInputStream; import java.io.IOException; import java.sql.Connection; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import java.util.ArrayList; import java.util.List; import java.util.Properties; import org.apache.commons.cli.CommandLine; import org.apache.commons.cli.CommandLineParser; import org.apache.commons.cli.GnuParser; import org.apache.commons.cli.HelpFormatter; import org.apache.commons.cli.Option; import org.apache.commons.cli.OptionBuilder; import org.apache.commons.cli.Options; import org.apache.commons.cli.ParseException; import org.apache.log4j.ConsoleAppender; import org.apache.log4j.Logger; import org.apache.log4j.PatternLayout; import org.apache.log4j.PropertyConfigurator; import com.linkedin.databus.bootstrap.common.BootstrapCleanerConfig; import com.linkedin.databus.bootstrap.common.BootstrapCleanerStaticConfig; import com.linkedin.databus.bootstrap.common.BootstrapConfig; import com.linkedin.databus.bootstrap.common.BootstrapDBCleaner; import com.linkedin.databus.bootstrap.common.BootstrapReadOnlyConfig; import com.linkedin.databus.core.util.ConfigLoader; import com.linkedin.databus2.util.DBHelper; /* * * Bootstrap DB Cleaner StandAlone Script. * * Used for manually cleaning bootstrap DB. * */ public class BootstrapDBCleanerMain { public static final String MODULE = BootstrapSeederMain.class.getName(); public static final Logger LOG = Logger.getLogger(MODULE); public static final String HELP_OPT_LONG_NAME = "help"; public static final char HELP_OPT_CHAR = 'h'; public static final String BOOTSTRAP_SOURCES_OPT_LONG_NAME = "sources"; public static final char BOOTSTRAP_SOURCES_PROP_OPT_CHAR = 's'; public static final String BOOTSTRAP_DB_PROPS_OPT_LONG_NAME = "bootstrap_db_props"; public static final char BOOTSTRAP_DB_PROP_OPT_CHAR = 'p'; public static final String CLEANER_CMD_LINE_PROPS_OPT_LONG_NAME = "cleaner_cmdline_props"; public static final char CLEANER_CMD_LINE_PROPS_OPT_CHAR = 'c'; public static final String LOG4J_PROPS_OPT_LONG_NAME = "log_props"; public static final char LOG4J_PROPS_OPT_CHAR = 'l'; private static BootstrapCleanerStaticConfig _sCleanerConfig = null; private static BootstrapReadOnlyConfig _sBootstrapConfig = null; private static List<String> _sSources = null; private static Properties _sBootstrapConfigProps = null; /** * @param args */ public static void main(String[] args) throws Exception { parseArgs(args); BootstrapCleanerConfig config = new BootstrapCleanerConfig(); BootstrapConfig bsConfig = new BootstrapConfig(); ConfigLoader<BootstrapCleanerStaticConfig> configLoader = new ConfigLoader<BootstrapCleanerStaticConfig>("databus.bootstrap.cleaner.", config); ConfigLoader<BootstrapReadOnlyConfig> configLoader2 = new ConfigLoader<BootstrapReadOnlyConfig>("databus.bootstrap.db.", bsConfig); _sCleanerConfig = configLoader.loadConfig(_sBootstrapConfigProps); _sBootstrapConfig = configLoader2.loadConfig(_sBootstrapConfigProps); BootstrapDBCleaner cleaner = new BootstrapDBCleaner("StandAloneCleaner", _sCleanerConfig, _sBootstrapConfig, null, _sSources); cleaner.doClean(); } @SuppressWarnings("static-access") public static void parseArgs(String[] args) throws IOException { CommandLineParser cliParser = new GnuParser(); Option helpOption = OptionBuilder.withLongOpt(HELP_OPT_LONG_NAME) .withDescription("Help screen") .create(HELP_OPT_CHAR); Option dbOption = OptionBuilder.withLongOpt(BOOTSTRAP_DB_PROPS_OPT_LONG_NAME) .withDescription("Bootstrap Cleaner and DB properties to use") .hasArg() .withArgName("property_file") .create(BOOTSTRAP_DB_PROP_OPT_CHAR); Option cmdLinePropsOption1 = OptionBuilder.withLongOpt(CLEANER_CMD_LINE_PROPS_OPT_LONG_NAME) .withDescription("Cmd line override of cleaner config properties. Semicolon separated.") .hasArg() .withArgName("Semicolon_separated_properties") .create(CLEANER_CMD_LINE_PROPS_OPT_CHAR); Option log4jPropsOption = OptionBuilder.withLongOpt(LOG4J_PROPS_OPT_LONG_NAME) .withDescription("Log4j properties to use") .hasArg() .withArgName("property_file") .create(LOG4J_PROPS_OPT_CHAR); Option sourcesOption = OptionBuilder.withLongOpt(BOOTSTRAP_SOURCES_OPT_LONG_NAME) .withDescription("Comma seperated list of sourceNames. If not provided, no source will be cleaned up") .hasArg() .withArgName("comma-seperated sources") .create(BOOTSTRAP_SOURCES_PROP_OPT_CHAR); Options options = new Options(); options.addOption(helpOption); options.addOption(dbOption); options.addOption(cmdLinePropsOption1); options.addOption(log4jPropsOption); options.addOption(sourcesOption); CommandLine cmd = null; try { cmd = cliParser.parse(options, args); } catch (ParseException pe) { LOG.error("Bootstrap Physical Config: failed to parse command-line options.", pe); throw new RuntimeException("Bootstrap Physical Config: failed to parse command-line options.", pe); } if (cmd.hasOption(LOG4J_PROPS_OPT_CHAR)) { String log4jPropFile = cmd.getOptionValue(LOG4J_PROPS_OPT_CHAR); PropertyConfigurator.configure(log4jPropFile); LOG.info("Using custom logging settings from file " + log4jPropFile); } else { PatternLayout defaultLayout = new PatternLayout("%d{ISO8601} +%r [%t] (%p) {%c} %m%n"); ConsoleAppender defaultAppender = new ConsoleAppender(defaultLayout); Logger.getRootLogger().removeAllAppenders(); Logger.getRootLogger().addAppender(defaultAppender); LOG.info("Using default logging settings"); } if (cmd.hasOption(HELP_OPT_CHAR)) { printCliHelp(options); System.exit(0); } if (cmd.hasOption(BOOTSTRAP_SOURCES_PROP_OPT_CHAR)) { _sSources = new ArrayList<String>(); String srcListStr = cmd.getOptionValue(BOOTSTRAP_SOURCES_PROP_OPT_CHAR); LOG.info("Going to run cleaner for only these sources : " + srcListStr); String[] srcList = srcListStr.split(","); for (String s: srcList) _sSources.add(s); } if (!cmd.hasOption(BOOTSTRAP_DB_PROP_OPT_CHAR) ) throw new RuntimeException("Bootstrap config is not provided"); String propFile = cmd.getOptionValue(BOOTSTRAP_DB_PROP_OPT_CHAR); LOG.info("Loading bootstrap DB config from properties file " + propFile); _sBootstrapConfigProps = new Properties(); FileInputStream f = new FileInputStream(propFile); try { _sBootstrapConfigProps.load(f); } finally { f.close(); } if (cmd.hasOption(CLEANER_CMD_LINE_PROPS_OPT_CHAR)) { String cmdLinePropString = cmd.getOptionValue(CLEANER_CMD_LINE_PROPS_OPT_CHAR); updatePropsFromCmdLine(_sBootstrapConfigProps, cmdLinePropString); } } private static void printCliHelp(Options cliOptions) { HelpFormatter helpFormatter = new HelpFormatter(); helpFormatter.printHelp("java " + BootstrapDBCleanerMain.class.getName(), cliOptions); } private static void updatePropsFromCmdLine(Properties props, String cmdLinePropString) { String[] cmdLinePropSplit = cmdLinePropString.split(";"); for(String s : cmdLinePropSplit) { String[] onePropSplit = s.split("="); if (onePropSplit.length != 2) { LOG.error("CMD line property setting " + s + "is not valid!"); } else { LOG.info("CMD line Property overwride: " + s); props.put(onePropSplit[0], onePropSplit[1]); } } } /* * Get the sourceIds which are bootstrapped in this DB * * @return list of SrcIds */ private static List<String> getSourceNames(Connection conn) throws SQLException { List<String> srcNames = new ArrayList<String>(); String sql = "select src from bootstrap_sources"; ResultSet rs = null; PreparedStatement stmt = null; try { stmt = conn.prepareStatement(sql); rs = stmt.executeQuery(); while (rs.next()) { String name = rs.getString(1); srcNames.add(name); } } finally { DBHelper.close(rs,stmt,null); } return srcNames; } }