Collection of useful utilities for Java games and apps. A lot of interesting utilities that could maybe still find some use if you work with Java...
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
mightyutils/src/mightypork/utils/logging/Log.java

344 lines
6.4 KiB

package mightypork.utils.logging;
import java.io.File;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.util.HashMap;
import java.util.logging.Level;
import mightypork.utils.Str;
import mightypork.utils.annotations.FactoryMethod;
import mightypork.utils.logging.monitors.LogMonitor;
import mightypork.utils.logging.monitors.LogMonitorStdout;
import mightypork.utils.logging.writers.ArchivingLog;
import mightypork.utils.logging.writers.LogWriter;
import mightypork.utils.logging.writers.SimpleLog;
/**
* A log.
*
* @author Ondřej Hruška (MightyPork)
*/
public class Log {
private static LogWriter main = null;
private static boolean enabled = true;
private static final LogMonitorStdout sysoMonitor = new LogMonitorStdout();
private static final long start_ms = System.currentTimeMillis();
private static HashMap<String, SimpleLog> logs = new HashMap<>();
/**
* Create a logger. If another with the name already exists, it'll be
* retrieved instead of creating a new one.
*
* @param logName log name (used for filename, should be application-unique)
* @param logFile log file; old logs will be kept here too.
* @param oldLogsCount number of old logs to keep, -1 infinite, 0 none.
* @return the created Log instance
*/
@FactoryMethod
public static synchronized LogWriter create(String logName, File logFile, int oldLogsCount)
{
if (logs.containsKey(logName)) return logs.get(logName);
final ArchivingLog log = new ArchivingLog(logName, logFile, oldLogsCount);
log.init();
logs.put(logName, log);
return log;
}
/**
* Create a logger. If another with the name already exists, it'll be
* retrieved instead of creating a new one.
*
* @param logName log name (used for filename, must be application-unique)
* @param logFile log file; old logs will be kept here too.
* @return the created Log instance
*/
@FactoryMethod
public static synchronized LogWriter create(String logName, File logFile)
{
if (logs.containsKey(logName)) return logs.get(logName);
final SimpleLog log = new SimpleLog(logName, logFile);
log.init();
logs.put(logName, log);
return log;
}
public static void setMainLogger(LogWriter log)
{
main = log;
}
public static LogWriter getMainLogger()
{
return main;
}
public static void addMonitor(LogMonitor mon)
{
assertInited();
main.addMonitor(mon);
}
public static void removeMonitor(LogMonitor mon)
{
assertInited();
main.removeMonitor(mon);
}
private static void assertInited()
{
if (main == null) throw new IllegalStateException("Main logger not initialized.");
}
/**
* Log a message
*
* @param level message level
* @param msg message text
*/
public static void log(Level level, String msg)
{
if (enabled) {
sysoMonitor.onMessageLogged(level, formatMessage(level, msg, null, start_ms));
if (main != null) {
main.log(level, msg);
}
}
}
/**
* Log a message
*
* @param level message level
* @param msg message text
* @param t thrown exception
*/
public static void log(Level level, String msg, Throwable t)
{
if (enabled) {
sysoMonitor.onMessageLogged(level, formatMessage(level, msg, t, start_ms));
if (main != null) {
main.log(level, msg, t);
}
}
}
/**
* Log FINE message
*
* @param msg message
*/
public static void f1(String msg)
{
log(Level.FINE, msg);
}
/**
* Log FINER message
*
* @param msg message
*/
public static void f2(String msg)
{
log(Level.FINER, msg);
}
/**
* Log FINEST message
*
* @param msg message
*/
public static void f3(String msg)
{
log(Level.FINEST, msg);
}
/**
* Log INFO message
*
* @param msg message
*/
public static void i(String msg)
{
log(Level.INFO, msg);
}
/**
* Log WARNING message (less severe than ERROR)
*
* @param msg message
*/
public static void w(String msg)
{
log(Level.WARNING, msg);
}
/**
* Log ERROR message
*
* @param msg message
*/
public static void e(String msg)
{
log(Level.SEVERE, msg);
}
/**
* Log warning message with exception
*
* @param msg message
* @param thrown thrown exception
*/
public static void w(String msg, Throwable thrown)
{
log(Level.WARNING, msg, thrown);
}
/**
* Log exception thrown as warning
*
* @param thrown thrown exception
*/
public static void w(Throwable thrown)
{
log(Level.WARNING, null, thrown);
}
/**
* Log error message
*
* @param msg message
* @param thrown thrown exception
*/
public static void e(String msg, Throwable thrown)
{
log(Level.SEVERE, msg, thrown);
}
/**
* Log exception thrown as error
*
* @param thrown thrown exception
*/
public static void e(Throwable thrown)
{
log(Level.SEVERE, null, thrown);
}
public static void enable(boolean flag)
{
enabled = flag;
}
public static void setSysoutLevel(Level level)
{
sysoMonitor.setLevel(level);
}
public static void setLevel(Level level)
{
assertInited();
main.setLevel(level);
}
/**
* Get stack trace from throwable
*
* @param t
* @return trace
*/
public static String getStackTrace(Throwable t)
{
final StringWriter sw = new StringWriter();
final PrintWriter pw = new PrintWriter(sw, true);
t.printStackTrace(pw);
pw.flush();
sw.flush();
return sw.toString();
}
public static String formatMessage(Level level, String message, Throwable throwable, long start_ms)
{
if (message == null) message = "";
final String nl = System.getProperty("line.separator");
if (message.length() > 0) {
if (message.equals("\n")) {
return nl;
}
if (message.charAt(0) == '\n') {
message = nl + message.substring(1);
}
}
final long time_ms = (System.currentTimeMillis() - start_ms);
final double time_s = time_ms / 1000D;
final String time = String.format("%6.2f ", time_s);
final String time_blank = Str.repeat(" ", time.length());
String prefix = "[ ? ]";
if (level == Level.FINE) {
prefix = "[ # ] ";
} else if (level == Level.FINER) {
prefix = "[ - ] ";
} else if (level == Level.FINEST) {
prefix = "[ ] ";
} else if (level == Level.INFO) {
prefix = "[ i ] ";
} else if (level == Level.SEVERE) {
prefix = "[!E!] ";
} else if (level == Level.WARNING) {
prefix = "[!W!] ";
}
message = time + prefix + message.replaceAll("\n", nl + time_blank + prefix) + nl;
if (throwable != null) {
message += getStackTrace(throwable);
}
return message;
}
}