aboutsummaryrefslogtreecommitdiffstats
path: root/tools/tools-common/src/main/java
diff options
context:
space:
mode:
Diffstat (limited to 'tools/tools-common/src/main/java')
-rw-r--r--tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliOptions.java105
-rw-r--r--tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliParser.java119
-rw-r--r--tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/Console.java352
-rw-r--r--tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/OutputFile.java136
-rw-r--r--tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/package-info.java27
5 files changed, 739 insertions, 0 deletions
diff --git a/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliOptions.java b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliOptions.java
new file mode 100644
index 000000000..277769be2
--- /dev/null
+++ b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliOptions.java
@@ -0,0 +1,105 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2016-2018 Ericsson. 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.
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.apex.tools.common;
+
+import org.apache.commons.cli.Option;
+
+/**
+ * Standard application CLI options.
+ *
+ * @author Sven van der Meer (sven.van.der.meer@ericsson.com)
+ */
+public final class CliOptions {
+
+ /** Private constructor to prevent instantiation. */
+ private CliOptions() {}
+
+ /** A console option with "-c" and "--console". */
+ public static final Option CONSOLE =
+ Option.builder("c").longOpt("console").desc("application as console with input from standard in").build();
+
+ /** A help option with "-h" and "--help". */
+ public static final Option HELP =
+ Option.builder("h").longOpt("help").desc("prints this help and usage screen").build();
+
+ /** A version option with "-v" and "--version". */
+ public static final Option VERSION =
+ Option.builder("v").longOpt("version").desc("prints the application version").build();
+
+ /** A print-stacktrace option with "--print-stacktrace". */
+ public static final Option PRINTSTACKTRACE =
+ Option.builder().longOpt("print-stacktrace").desc("prints stack traces for any exception").build();
+
+ /** A check-java-class option with "--check-java-class". */
+ public static final Option CHECKJAVACLASS = Option.builder("j").longOpt("check-java-class")
+ .desc("switch on checking of Java class references, requires JAR in class path").build();
+
+ /** A quiet option with "-q" and "--quiet". */
+ public static final Option QUIET =
+ Option.builder("q").longOpt("quiet").desc("application in quiet mode, no output at all").build();
+
+ /** A no-warning option with "--no-warnings". */
+ public static final Option NOWARNINGS =
+ Option.builder().longOpt("no-warnings").desc("switch off all warnings").build();
+
+ /** A no-error option with "--no-errors". */
+ public static final Option NOERRORS =
+ Option.builder().longOpt("no-errors").desc("switch off error messages").build();
+
+ /** A no-progress option with "--no-progress". */
+ public static final Option SHOWPROGRESS =
+ Option.builder().longOpt("no-progress").desc("switch off progress information").build();
+
+ /** A file-in option with "-f" and "--input-file". */
+ public static final Option FILEIN =
+ Option.builder("f").hasArg().argName("FILE").longOpt("input-file").desc("set the input file").build();
+
+ /** A file-out option with "-o" and "--output-file". */
+ public static final Option FILEOUT = Option.builder("o").hasArg().argName("FILE").longOpt("output-file")
+ .desc("set the output file").required(false).build();
+
+ /** An overwrite option with "-ow" and "--overwrite". */
+ public static final Option OVERWRITE = Option.builder("ow").required(false).longOpt("overwrite")
+ .desc("overwrite the output file if it exists. This option can only be used with the -" + FILEOUT.getOpt()
+ + " option")
+ .build();
+
+ /** An option for the policy model file with "-m" and "--model". */
+ public static final Option MODELFILE = Option.builder("m").hasArg().argName("MODEL-FILE").longOpt("model")
+ .desc("set the input policy model file").build();
+
+ /** A type option defining what type is used for events with "-t" and "--type". */
+ public static final Option TYPE = Option.builder("t").hasArg().argName("TYPE").longOpt("type").desc(
+ "set the event type for generation, one of: stimuli (trigger events), response (action events), internal (events between states)")
+ .build();
+
+ /** A server option with "-s" and "--server". */
+ public static final Option SERVER = Option.builder("s").hasArg().argName("HOSTNAME").longOpt("server")
+ .desc("set the Websocket server hostname, default: localhost").build();
+
+ /** A port option with "-p" and "--port". */
+ public static final Option PORT = Option.builder("p").hasArg().argName("PORT").longOpt("port")
+ .desc("set the Websocket server port, default: 8887").build();
+
+ /** A skip validation option with "-sv" and "--skip-validation". */
+ public static final Option SKIPVALIDATION = Option.builder("sv").longOpt("skip-validation")
+ .desc("switch of validation of the input file").required(false).type(boolean.class).build();
+}
diff --git a/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliParser.java b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliParser.java
new file mode 100644
index 000000000..588abfc6b
--- /dev/null
+++ b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/CliParser.java
@@ -0,0 +1,119 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2016-2018 Ericsson. 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.
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.apex.tools.common;
+
+////
+//// NOTE: This file contains tags for ASCIIDOC
+//// DO NOT REMOVE any of those tag lines, e.g.
+////// tag::**
+////// end::**
+////
+
+import java.util.Scanner;
+
+import org.apache.commons.cli.CommandLine;
+import org.apache.commons.cli.CommandLineParser;
+import org.apache.commons.cli.DefaultParser;
+import org.apache.commons.cli.Option;
+import org.apache.commons.cli.Options;
+import org.apache.commons.cli.ParseException;
+
+/**
+ * Application CLI parser.
+ *
+ * @author Sven van der Meer (sven.van.der.meer@ericsson.com)
+ */
+public class CliParser {
+
+ /** The local set of CLI options. */
+ private final Options options;
+
+ /** The command line, null on start, not null after successful parse. */
+ private CommandLine cmd;
+
+ /**
+ * Creates a new CLI parser.
+ */
+ public CliParser() {
+ options = new Options();
+ }
+
+ /**
+ * Adds an option to the parser.
+ *
+ * @param option the new option, must not be null
+ * @return self to allow chaining
+ */
+ public CliParser addOption(final Option option) {
+ if (option == null) {
+ throw new IllegalStateException("CLI parser: given option was null");
+ }
+ options.addOption(option);
+ return this;
+ }
+
+ /**
+ * Parses the arguments with the set options.
+ *
+ * @param args the arguments to parse
+ * @return a command line with parsed arguments, null on parse errors.
+ */
+ public CommandLine parseCli(final String[] args) {
+ final CommandLineParser parser = new DefaultParser();
+ try {
+ cmd = parser.parse(options, args);
+ } catch (final ParseException ex) {
+ System.err.println("Parsing failed. Reason: " + ex.getMessage());
+ ex.printStackTrace();
+ }
+ return cmd;
+ }
+
+ /**
+ * Returns the parsed command line.
+ *
+ * @return the parsed command line, null if nothing parsed
+ */
+ public CommandLine getCommandLine() {
+ return cmd;
+ }
+
+ /**
+ * Returns the CLI options.
+ *
+ * @return CLI options
+ */
+ public Options getOptions() {
+ return options;
+ }
+
+ /**
+ * Returns the version for an application as set by Maven.
+ *
+ * @return version, null if version file <code>/app-version.txt</code> was not found
+ */
+ @SuppressWarnings("resource")
+ // tag::cliParserVersion[]
+ public String getAppVersion() {
+ return new Scanner(CliParser.class.getResourceAsStream("/app-version.txt"), "UTF-8").useDelimiter("\\A").next();
+ }
+ // end::cliParserVersion[]
+}
diff --git a/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/Console.java b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/Console.java
new file mode 100644
index 000000000..571333147
--- /dev/null
+++ b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/Console.java
@@ -0,0 +1,352 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2016-2018 Ericsson. 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.
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.apex.tools.common;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.commons.lang3.StringUtils;
+import org.apache.commons.text.StrBuilder;
+import org.slf4j.helpers.MessageFormatter;
+
+/**
+ * A console for printing messages with functionality similar to loggers. The class provides a static instance for all
+ * parts of an application. The default configuration is to not collect errors or warnings. The default types being
+ * activated are errors, warnings, and info messages.
+ *
+ * @author Sven van der Meer (sven.van.der.meer@ericsson.com)
+ */
+public final class Console {
+
+ /** The console as static object. */
+ public static final Console CONSOLE = new Console();
+
+ /** Type for a quiet console, no messages being printed. */
+ public static final int TYPE_QUIET = 0;
+
+ /** Type for printing error messages. */
+ public static final int TYPE_ERROR = 0b0001;
+
+ /** Type for printing warning messages. */
+ public static final int TYPE_WARNING = 0b0010;
+
+ /** Type for printing information messages. */
+ public static final int TYPE_INFO = 0b0100;
+
+ /** Type for printing progress messages. */
+ public static final int TYPE_PROGRESS = 0b1000;
+
+ /** Type for printing debug messages. */
+ public static final int TYPE_DEBUG = 0b001_0000;
+
+ /** Type for printing trace messages. */
+ public static final int TYPE_TRACE = 0b010_0000;
+
+ /** Type for printing stack traces of caught exceptions. */
+ public static final int TYPE_STACKTRACE = 0b110_0000;
+
+ /** Type for a verbose console, activating all message types. */
+ public static final int TYPE_VERBOSE = 0b111_1111;
+
+ /** Configuration for a collecting error messages. */
+ public static final int CONFIG_COLLECT_ERRORS = 0b0001;
+
+ /** Configuration for a collecting warning messages. */
+ public static final int CONFIG_COLLECT_WARNINGS = 0b0010;
+
+ /** The setting for message types, set using type flags. */
+ private int types;
+
+ /** The console configuration, set using configuration flags. */
+ private int configuration;
+
+ /** A name for the application, if set used as prefix for messages. */
+ private String appName;
+
+ /** The list of errors, filled if error collection is activates. */
+ private final List<String> errors;
+
+ /** The list of warnings, filled if warning collection is activates. */
+ private final List<String> warnings;
+
+ /**
+ * Creates a new console. The constructor is private since the class provides static access to an instance. The
+ * default for types is verbose.
+ */
+ private Console() {
+ types = TYPE_VERBOSE;
+
+ configuration = 0;
+ errors = new ArrayList<>();
+ warnings = new ArrayList<>();
+ }
+
+ /**
+ * Sets the application name.
+ *
+ * @param appName new application name, use <code>null</code> to reset the application name, a non-blank string for
+ * a new name, blank strings are ignored
+ */
+ public void setAppName(final String appName) {
+ if (appName == null) {
+ this.appName = null;
+ } else if (!StringUtils.isBlank(appName)) {
+ this.appName = appName;
+ }
+ }
+
+ /**
+ * Returns the application name.
+ *
+ * @return application name, null if not set, non-blank string otherwise
+ */
+ public String getAppName() {
+ return appName;
+ }
+
+ /**
+ * Activates a type.
+ *
+ * @param type the type to activate
+ */
+ public void activate(final int type) {
+ types = types | type;
+ }
+
+ /**
+ * Deactivates a type.
+ *
+ * @param type type to deactivate
+ */
+ public void deActivate(final int type) {
+ types = types & ~type;
+ }
+
+ /**
+ * Sets the type to the given type, effectively deactivating all other types.
+ *
+ * @param type new type
+ */
+ public void set(final int type) {
+ types = type;
+ }
+
+ /**
+ * Configures the console. Use the configuration flags in combination for the required configuration. For instance,
+ * to collect errors and warnings use <code>CONFIG_COLLECT_ERRORS | CONFIG_COLLECT_WARNINGS</code>.
+ *
+ * @param config the new configuration, overwrites the current configuration, 0 deactivates all settings
+ */
+ public void configure(final int config) {
+ this.configuration = config;
+ }
+
+ /**
+ * Sets the type to the given types, effectively deactivating all other types.
+ *
+ * @param ts array of types to set
+ */
+ public void set(final int... ts) {
+ this.types = 0;
+ for (final int type : ts) {
+ this.activate(type);
+ }
+ }
+
+ /**
+ * Prints an error message with message and objects if {@link #TYPE_ERROR} is set; and increases the error count.
+ * Errors are collected (if configuration is set) and the error counter is increased regardless of the console error
+ * type settings.
+ *
+ * @param message the error message, using the same format as the SLF4J MessageFormatter, nothing done if
+ * <code>blank</code>
+ * @param objects the objects for substitution in the message
+ */
+ public void error(final String message, final Object... objects) {
+ if (StringUtils.isBlank(message)) {
+ return;
+ }
+
+ final StrBuilder err = new StrBuilder();
+ if (appName != null) {
+ err.append(this.getAppName()).append(": ");
+ }
+ err.append("error: ");
+ err.append(MessageFormatter.arrayFormat(message, objects).getMessage());
+
+ if ((types & TYPE_ERROR) == TYPE_ERROR) {
+ System.err.println(err.build());
+ }
+ if ((configuration & CONFIG_COLLECT_ERRORS) == CONFIG_COLLECT_ERRORS) {
+ errors.add(err.build());
+ }
+ }
+
+ /**
+ * Prints a warning message with message and objects if {@link #TYPE_WARNING} is set; and increases the warning
+ * count. Warnings are collected (if configuration is set) and the warning counter is increased regardless of the
+ * console warning type settings.
+ *
+ * @param message the warning message, using the same format as the SLF4J MessageFormatter, nothing done if
+ * <code>blank</code>
+ * @param objects the objects for substitution in the message
+ */
+ public void warn(final String message, final Object... objects) {
+ if (StringUtils.isBlank(message)) {
+ return;
+ }
+
+ final StrBuilder warn = new StrBuilder();
+ if (appName != null) {
+ warn.append(this.getAppName()).append(": ");
+ }
+ warn.append("warning: ");
+ warn.append(MessageFormatter.arrayFormat(message, objects).getMessage());
+
+ if ((types & TYPE_WARNING) == TYPE_WARNING) {
+ System.err.println(warn.build());
+ }
+ if ((configuration & CONFIG_COLLECT_WARNINGS) == CONFIG_COLLECT_WARNINGS) {
+ warnings.add(warn.build());
+ }
+ }
+
+ /**
+ * Prints an info message with message and objects if {@link #TYPE_INFO} is set.
+ *
+ * @param message the warning message, using the same format as the SLF4J MessageFormatter, nothing done if
+ * <code>blank</code>
+ * @param objects the objects for substitution in the message
+ */
+ public void info(final String message, final Object... objects) {
+ if (StringUtils.isBlank(message)) {
+ return;
+ }
+
+ if ((types & TYPE_INFO) == TYPE_INFO) {
+ if (appName != null) {
+ System.err.print(appName + ": ");
+ }
+ System.err.println(MessageFormatter.arrayFormat(message, objects).getMessage());
+ }
+ }
+
+ /**
+ * Prints a progress message with message and objects if {@link #TYPE_PROGRESS} is set.
+ *
+ * @param message the warning message, using the same format as the SLF4J MessageFormatter, nothing done if
+ * <code>blank</code>
+ * @param objects the objects for substitution in the message
+ */
+ public void progress(final String message, final Object... objects) {
+ if (StringUtils.isBlank(message)) {
+ return;
+ }
+
+ if ((types & TYPE_PROGRESS) == TYPE_PROGRESS) {
+ if (appName != null) {
+ System.err.print(appName + ": ");
+ }
+ System.err.print("progress: ");
+ System.err.println(MessageFormatter.arrayFormat(message, objects).getMessage());
+ }
+ }
+
+ /**
+ * Prints a debug message with message and objects if {@link #TYPE_DEBUG} is set.
+ *
+ * @param message the warning message, using the same format as the SLF4J MessageFormatter, nothing done if
+ * <code>blank</code>
+ * @param objects the objects for substitution in the message
+ */
+ public void debug(final String message, final Object... objects) {
+ if (StringUtils.isBlank(message)) {
+ return;
+ }
+
+ if ((types & TYPE_DEBUG) == TYPE_DEBUG) {
+ if (appName != null) {
+ System.err.print(appName + ": ");
+ }
+ System.err.print("debug: ");
+ System.err.println(MessageFormatter.arrayFormat(message, objects).getMessage());
+ }
+ }
+
+ /**
+ * Prints a trace message with message and objects if {@link #TYPE_TRACE} is set.
+ *
+ * @param message the warning message, using the same format as the SLF4J MessageFormatter, nothing done if
+ * <code>blank</code>
+ * @param objects the objects for substitution in the message
+ */
+ public void trace(final String message, final Object... objects) {
+ if (StringUtils.isBlank(message)) {
+ return;
+ }
+
+ if ((types & TYPE_TRACE) == TYPE_TRACE) {
+ if (appName != null) {
+ System.err.print(appName + ": ");
+ }
+ System.err.print("trace: ");
+ System.err.println(MessageFormatter.arrayFormat(message, objects).getMessage());
+ }
+ }
+
+ /**
+ * Prints message, cause, and stack trace for a given exception if {@link #TYPE_STACKTRACE} is set.
+ *
+ * @param exception the exception to print, ignored if <code>null</code>
+ */
+ public void stacktrace(final Exception exception) {
+ if (exception == null) {
+ return;
+ }
+
+ if ((types & TYPE_STACKTRACE) == TYPE_STACKTRACE) {
+ if (appName != null) {
+ System.err.print(appName + ": ");
+ }
+ System.err.println("exception stack trace: ");
+ System.err.println(" - message: " + exception.getMessage());
+ if (exception.getCause() != null) {
+ System.err.println(" - cause: " + exception.getCause());
+ }
+ exception.printStackTrace();
+ }
+ }
+
+ /**
+ * Resets the error counter and the list of errors.
+ */
+ public void resetErrors() {
+ errors.clear();
+ }
+
+ /**
+ * Resets the warning counter and the list of warnings.
+ */
+ public void resetWarnings() {
+ warnings.clear();
+ }
+
+}
diff --git a/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/OutputFile.java b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/OutputFile.java
new file mode 100644
index 000000000..b529a7e08
--- /dev/null
+++ b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/OutputFile.java
@@ -0,0 +1,136 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2016-2018 Ericsson. 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.
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ * ============LICENSE_END=========================================================
+ */
+
+package org.onap.policy.apex.tools.common;
+
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.io.Writer;
+import java.nio.file.FileSystems;
+import java.nio.file.Path;
+
+import org.apache.commons.lang3.StringUtils;
+import org.apache.commons.lang3.Validate;
+
+/**
+ * Standard output file handling and tests.
+ *
+ * @author Sven van der Meer (sven.van.der.meer@ericsson.com)
+ */
+public class OutputFile {
+
+ /** The output file name. */
+ private final String fileName;
+
+ /** The output file name. */
+ private final boolean overwrite;
+
+ /**
+ * Creates a new object for a given file name.
+ *
+ * @param fileName the file name
+ */
+ public OutputFile(final String fileName) {
+ this(fileName, false);
+ }
+
+ /**
+ * Creates a new object for a given file name.
+ *
+ * @param fileName the file name
+ * @param overwrite if the file already exists, can it be overwritten, or should an error be raised
+ */
+ public OutputFile(final String fileName, final boolean overwrite) {
+ Validate.notBlank(fileName);
+ this.fileName = fileName;
+ this.overwrite = overwrite;
+ }
+
+ /**
+ * Get a File object for this output file.
+ *
+ * @return a File object for this output file
+ */
+ public File toFile() {
+ final Path fp = FileSystems.getDefault().getPath(fileName);
+ return fp.toFile();
+ }
+
+ /**
+ * Get a Writer object for this output file.
+ *
+ * @return a Writer object for this output file
+ */
+ public Writer toWriter() {
+ try {
+ return new BufferedWriter(new FileWriter(toFile()));
+ } catch (final IOException e) {
+ return null;
+ }
+ }
+
+ /**
+ * Get a OutputStream object for this output file.
+ *
+ * @return an OutputStream object for this output file
+ */
+ public OutputStream toOutputStream() {
+ try {
+ return new FileOutputStream(toFile());
+ } catch (final IOException e) {
+ return null;
+ }
+ }
+
+ /**
+ * Validates the output file. Validation tests for file name being blank, file existing, creation, and finally
+ * can-write.
+ *
+ * @return null on success, an error message on error
+ */
+ public String validate() {
+ if (StringUtils.isBlank(fileName)) {
+ return "file name was blank";
+ }
+
+ final File file = toFile();
+ if (file.exists()) {
+ if (!overwrite) {
+ return "file already exists";
+ }
+ } else {
+ try {
+ file.createNewFile();
+ } catch (final IOException e) {
+ return "could not create output file: " + e.getMessage();
+ }
+ }
+
+ if (!file.canWrite()) {
+ return "cannot write to file";
+ }
+
+ return null;
+ }
+}
diff --git a/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/package-info.java b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/package-info.java
new file mode 100644
index 000000000..e193aac5d
--- /dev/null
+++ b/tools/tools-common/src/main/java/org/onap/policy/apex/tools/common/package-info.java
@@ -0,0 +1,27 @@
+/*-
+ * ============LICENSE_START=======================================================
+ * Copyright (C) 2016-2018 Ericsson. 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.
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ * ============LICENSE_END=========================================================
+ */
+
+/**
+ * Utilities for APEX related applications, such as CLI parser and application console.
+ *
+ * @author Sven van der Meer (sven.van.der.meer@ericsson.com)
+ */
+
+package org.onap.policy.apex.tools.common;