0

I have a console app that interacts with hardware. My idea was to log all exceptions with their stacktraces so valuable information is not lost due to not having a pipe to a file.

But how to handle the location of that file? I cant ask for a path each time.

That is why i thought just put the file next to the executable. But cant be sure where the app will reside. And I have not found a distinct answer to "how to get the app path"

I found: new java.io.File("").getAbsolutePath(); But no explanation how this works.

And: getClass().getProtectionDomain().getCodeSource().getLocation().getPath(); But the op said this only may work. Is there another way to handle the errorlogging / a sure way to get the app path?

Community
  • 1
  • 1
Git
  • 214
  • 5
  • 16
  • 2
    How about using one of the standard logging frameworks and follow their documentation. You could try e.g. a combination of slf4j and logback and the config of the latter will define where the logs will go, into a file, into an elasticsearch instance or to the terminal. If you then go for a file, this can be either absolute or relative location... – Oleg Sklyar Aug 01 '16 at 13:18
  • a relative path to the app or to the current directory? – Git Aug 01 '16 at 13:28
  • 1
    This would be the question to the particular logging framework you go for. With respect to logback the following answer will help: http://stackoverflow.com/questions/16480052/is-there-a-way-in-logback-xml-to-specify-file-log-destination-through-classpath – Oleg Sklyar Aug 01 '16 at 13:31
  • Please formulate a complete answer and you get my vote =) – Git Aug 01 '16 at 13:50

1 Answers1

1

The standard approach to logging exceptions in all types of applications is to use one of the standard logging frameworks and defining its configuration externally to the application. Exceptions will be logged as ERROR and handled appropriately.

One could suggest e.g. slf4j (logging interface) together with logback (the matching implementation), but other will do as well.

When writing the code, the interface needs to be available at compile time as the code is programmed and compiled against it:

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class MyClass {

  private static final Logger LOGGER = LoggerFactory.getLogger(Myclass.class);

  public void method() {
    try {
      ...
    } catch (IOException ex) {
      LOGGER.error("method failed to do what was expected: {}", ex);
      throw ex;
    }

A particular implementation needs to be provided at runtime (e.g. added to a jar while packaging) or added to the classpath at runtime.

Next, a configuration matching the particular implementation needs to be provided at runtime, which for logback may look like this:

<?xml version="1.0" encoding="UTF-8"?>
<configuration scan="true">
  <appender name="FILE" class="ch.qos.logback.core.FileAppender">
  <file>myapp.log</file>
  <encoder>
    <pattern>%logger{35} - %msg%n</pattern>
  </encoder>
</appender>

  <root level="error">
    <appender-ref ref="FILE"/>
  </root>
</configuration>

Further details see under:

Community
  • 1
  • 1
Oleg Sklyar
  • 9,834
  • 6
  • 39
  • 62
  • You seem to be making an effort to avoid mentioning the [logging built into Java SE](http://docs.oracle.com/javase/8/docs/api/java/util/logging/package-summary.html), which is as good as all of those other options, and has the advantage of requiring no additional libraries. – VGR Aug 01 '16 at 14:28
  • No, I am not making this effort. I am using the above as an example to explain the actual answer (that is using "a logging framework") just because this setup is what I have experienced in a number of projects and what has been de-facto an industry standard at least until recently. Please suggest an edit if there is better solution using while sticking to a logging framework. – Oleg Sklyar Aug 01 '16 at 20:20