org.opendaylight.yangtools.yang.parser.system.test.Main.java Source code

Java tutorial

Introduction

Here is the source code for org.opendaylight.yangtools.yang.parser.system.test.Main.java

Source

/*
 * Copyright (c) 2016 Cisco Systems, Inc. and others.  All rights reserved.
 *
 * This program and the accompanying materials are made available under the
 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
 * and is available at http://www.eclipse.org/legal/epl-v10.html
 */
package org.opendaylight.yangtools.yang.parser.system.test;

import com.google.common.base.Stopwatch;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashSet;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.apache.commons.cli.BasicParser;
import org.apache.commons.cli.CommandLine;
import org.apache.commons.cli.CommandLineParser;
import org.apache.commons.cli.HelpFormatter;
import org.apache.commons.cli.Option;
import org.apache.commons.cli.Options;
import org.apache.commons.cli.ParseException;
import org.apache.log4j.BasicConfigurator;
import org.opendaylight.yangtools.yang.common.QName;
import org.opendaylight.yangtools.yang.model.api.SchemaContext;

/**
 * Main class of Yang parser system test.
 *
 * yang-system-test [-f features] [-h help] [-p path] [-v verbose] yangFiles...
 *  -f,--features <arg>   features is a string in the form
 *                        [feature(,feature)*] and feature is a string in the form
 *                        [($namespace?revision=$revision)$local_name].
 *                        This option is used to prune the data model by removing
 *                        all nodes that are defined with a "if-feature".
 *  -h,--help             print help message and exit.
 *  -p,--path <arg>       path is a colon (:) separated list of directories
 *                        to search for yang modules.
 *  -r, --recursive       recursive search of directories specified by -p option
 *  -v,--verbose          shows details about the results of test running.
 *
 */
public class Main {
    private static final Logger LOG = Logger.getLogger(Main.class.getName());
    private static final int MB = 1024 * 1024;

    private static Options createOptions() {
        final Options options = new Options();

        final Option help = new Option("h", "help", false, "print help message and exit.");
        help.setRequired(false);
        options.addOption(help);

        final Option path = new Option("p", "path", true,
                "path is a colon (:) separated list of directories to search for yang modules.");
        path.setRequired(false);
        options.addOption(path);

        final Option recursiveSearch = new Option("r", "recursive", false,
                "recursive search of directories specified by -p option.");
        recursiveSearch.setRequired(false);
        options.addOption(recursiveSearch);

        final Option verbose = new Option("v", "verbose", false,
                "shows details about the results of test running.");
        verbose.setRequired(false);
        options.addOption(verbose);

        final Option feature = new Option("f", "features", true,
                "features is a string in the form [feature(,feature)*] and feature is a string in the form "
                        + "[($namespace?revision=$revision)$local_name]. This option is used to prune the data model by removing "
                        + "all nodes that are defined with a \"if-feature\".");
        feature.setRequired(false);
        options.addOption(feature);
        return options;
    }

    public static void main(final String[] args) {

        BasicConfigurator.configure();

        final HelpFormatter formatter = new HelpFormatter();
        final Options options = createOptions();
        final CommandLine arguments = parseArguments(args, options, formatter);

        if (arguments.hasOption("help")) {
            printHelp(options, formatter);
            return;
        }

        if (arguments.hasOption("verbose")) {
            LOG.setLevel(Level.CONFIG);
        } else {
            LOG.setLevel(Level.SEVERE);
        }

        final List<String> yangLibDirs = initYangDirsPath(arguments);
        final List<String> yangFiles = Arrays.asList(arguments.getArgs());
        final HashSet<QName> supportedFeatures = initSupportedFeatures(arguments);

        runSystemTest(yangLibDirs, yangFiles, supportedFeatures, arguments.hasOption("recursive"));
    }

    private static void runSystemTest(final List<String> yangLibDirs, final List<String> yangFiles,
            final HashSet<QName> supportedFeatures, final boolean recursiveSearch) {
        LOG.log(Level.INFO, "Yang model dirs: {0} ", yangLibDirs);
        LOG.log(Level.INFO, "Yang model files: {0} ", yangFiles);
        LOG.log(Level.INFO, "Supported features: {0} ", supportedFeatures);

        SchemaContext context = null;

        printMemoryInfo("start");
        final Stopwatch stopWatch = Stopwatch.createStarted();

        try {
            context = SystemTestUtils.parseYangSources(yangLibDirs, yangFiles, supportedFeatures, recursiveSearch);
        } catch (final Exception e) {
            LOG.log(Level.SEVERE, "Failed to create SchemaContext.", e);
            System.exit(1);
        }

        stopWatch.stop();
        LOG.log(Level.INFO, "Elapsed time: {0}", stopWatch);
        printMemoryInfo("end");
        LOG.log(Level.INFO, "SchemaContext resolved Successfully. {0}", context);
        Runtime.getRuntime().gc();
        printMemoryInfo("after gc");
    }

    private static List<String> initYangDirsPath(final CommandLine arguments) {
        final List<String> yangDirs = new ArrayList<>();
        if (arguments.hasOption("path")) {
            for (final String pathArg : arguments.getOptionValues("path")) {
                yangDirs.addAll(Arrays.asList(pathArg.split(":")));
            }
        }
        return yangDirs;
    }

    private static HashSet<QName> initSupportedFeatures(final CommandLine arguments) {
        HashSet<QName> supportedFeatures = null;
        if (arguments.hasOption("features")) {
            supportedFeatures = new HashSet<>();
            for (final String pathArg : arguments.getOptionValues("features")) {
                supportedFeatures.addAll(createQNames(pathArg.split(",")));
            }
        }
        return supportedFeatures;
    }

    private static Collection<? extends QName> createQNames(final String[] featuresArg) {
        final HashSet<QName> qnames = new HashSet<>();
        for (final String featureStr : featuresArg) {
            qnames.add(QName.create(featureStr));
        }

        return qnames;
    }

    private static CommandLine parseArguments(final String[] args, final Options options,
            final HelpFormatter formatter) {
        final CommandLineParser parser = new BasicParser();

        CommandLine cmd = null;
        try {
            cmd = parser.parse(options, args);
        } catch (final ParseException e) {
            LOG.log(Level.SEVERE, "Failed to parse command line options.", e);
            printHelp(options, formatter);

            System.exit(1);
        }

        return cmd;
    }

    private static void printHelp(final Options options, final HelpFormatter formatter) {
        formatter.printHelp("yang-system-test [-f features] [-h help] [-p path] [-v verbose] yangFiles...",
                options);
    }

    private static void printMemoryInfo(final String info) {
        LOG.log(Level.INFO, "Memory INFO [{0}]: free {1}MB, used {2}MB, total {3}MB, max {4}MB",
                new Object[] { info, Runtime.getRuntime().freeMemory() / MB,
                        (Runtime.getRuntime().totalMemory() - Runtime.getRuntime().freeMemory()) / MB,
                        Runtime.getRuntime().totalMemory() / MB, Runtime.getRuntime().maxMemory() / MB });
    }
}