From 0c29043e2a35bf1176f41095a3d522ff59409cc9 Mon Sep 17 00:00:00 2001 From: Eckwain Date: Mon, 24 Nov 2025 23:57:50 +0500 Subject: [PATCH] Solved --- task01/src/com/example/task01/Logger.java | 105 ++++++++++++++++ task01/src/com/example/task01/Task01Main.java | 4 +- .../src/com/example/task02/DiscountBill.java | 49 ++++++++ task02/src/com/example/task02/Task02Main.java | 14 +-- task03/src/com/example/task03/Hours.java | 33 ++++++ .../src/com/example/task03/Milliseconds.java | 11 +- task03/src/com/example/task03/Minutes.java | 24 ++-- task03/src/com/example/task03/Seconds.java | 9 +- task03/src/com/example/task03/TimeUnit.java | 8 ++ .../src/com/example/task03/TimeUnitUtils.java | 82 ++++++++++++- .../com/example/task04/ConsoleHandler.java | 12 ++ .../src/com/example/task04/FileHandler.java | 58 +++++++++ task04/src/com/example/task04/Logger.java | 112 ++++++++++++++++++ .../src/com/example/task04/LoggerFactory.java | 18 +++ .../src/com/example/task04/MemoryHandler.java | 46 +++++++ .../com/example/task04/MessageHandler.java | 12 ++ .../example/task04/RotationFileHandler.java | 98 +++++++++++++++ task04/src/com/example/task04/Task04Main.java | 40 ++++++- 18 files changed, 711 insertions(+), 24 deletions(-) create mode 100644 task01/src/com/example/task01/Logger.java create mode 100644 task02/src/com/example/task02/DiscountBill.java create mode 100644 task03/src/com/example/task03/Hours.java create mode 100644 task04/src/com/example/task04/ConsoleHandler.java create mode 100644 task04/src/com/example/task04/FileHandler.java create mode 100644 task04/src/com/example/task04/Logger.java create mode 100644 task04/src/com/example/task04/LoggerFactory.java create mode 100644 task04/src/com/example/task04/MemoryHandler.java create mode 100644 task04/src/com/example/task04/MessageHandler.java create mode 100644 task04/src/com/example/task04/RotationFileHandler.java diff --git a/task01/src/com/example/task01/Logger.java b/task01/src/com/example/task01/Logger.java new file mode 100644 index 00000000..3da48843 --- /dev/null +++ b/task01/src/com/example/task01/Logger.java @@ -0,0 +1,105 @@ +package com.example.task01; + +import java.text.MessageFormat; +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; +import java.util.HashMap; +import java.util.Map; + +public class Logger { + private static final Map LOGGERS = new HashMap<>(); + private static final DateTimeFormatter DATE_FORMATTER = DateTimeFormatter.ofPattern("yyyy.MM.dd"); + private static final DateTimeFormatter TIME_FORMATTER = DateTimeFormatter.ofPattern("HH:mm:ss"); + + private final String name; + private Level level; + + public enum Level { + DEBUG, + INFO, + WARNING, + ERROR + } + + private Logger(String name) { + this.name = name; + this.level = Level.DEBUG; + } + + public static Logger getLogger(String name) { + return LOGGERS.computeIfAbsent(name, Logger::new); + } + + public String getName() { + return name; + } + + public Level getLevel() { + return level; + } + + public void setLevel(Level level) { + this.level = level; + } + + private boolean shouldLog(Level messageLevel) { + return messageLevel.ordinal() >= level.ordinal(); + } + + private void log(Level level, String message) { + if (!shouldLog(level)) return; + + String timestamp = getFormattedTimestamp(); + String output = String.format("[%s] %s %s - %s", level, timestamp, name, message); + + if (level == Level.ERROR || level == Level.WARNING) { + System.err.println(output); + } else { + System.out.println(output); + } + } + + private void log(Level level, String template, Object... args) { + if (!shouldLog(level)) return; + String formattedMessage = MessageFormat.format(template, args); + log(level, formattedMessage); + } + + private String getFormattedTimestamp() { + LocalDateTime now = LocalDateTime.now(); + return now.format(DATE_FORMATTER) + " " + now.format(TIME_FORMATTER); + } + + // Методы для уровней логирования + public void debug(String message) { + log(Level.DEBUG, message); + } + + public void debug(String template, Object... args) { + log(Level.DEBUG, template, args); + } + + public void info(String message) { + log(Level.INFO, message); + } + + public void info(String template, Object... args) { + log(Level.INFO, template, args); + } + + public void warning(String message) { + log(Level.WARNING, message); + } + + public void warning(String template, Object... args) { + log(Level.WARNING, template, args); + } + + public void error(String message) { + log(Level.ERROR, message); + } + + public void error(String template, Object... args) { + log(Level.ERROR, template, args); + } +} \ No newline at end of file diff --git a/task01/src/com/example/task01/Task01Main.java b/task01/src/com/example/task01/Task01Main.java index 9973557d..5fb7521c 100644 --- a/task01/src/com/example/task01/Task01Main.java +++ b/task01/src/com/example/task01/Task01Main.java @@ -2,6 +2,8 @@ public class Task01Main { public static void main(String[] args) { - + Logger logger = Logger.getLogger("main"); + logger.setLevel(Logger.Level.WARNING); + logger.warning("Disk space low: {0}GB remaining", 2.5); } } diff --git a/task02/src/com/example/task02/DiscountBill.java b/task02/src/com/example/task02/DiscountBill.java new file mode 100644 index 00000000..bfecba56 --- /dev/null +++ b/task02/src/com/example/task02/DiscountBill.java @@ -0,0 +1,49 @@ +package com.example.task02; + +/** + * Счет к оплате со скидкой + */ +public class DiscountBill extends Bill { + private final double discountPercent; + + public DiscountBill(double discountPercent) { + if (discountPercent < 0 || discountPercent > 1) { + throw new IllegalArgumentException("Скидка должна быть в диапазоне от 0 до 1"); + } + this.discountPercent = discountPercent; + } + + /** + * Возвращает процент скидки (от 0 до 1) + */ + public double getDiscountPercent() { + return discountPercent; + } + + /** + * Возвращает абсолютное значение скидки + */ + public long getDiscountAbsolute() { + long originalPrice = super.getPrice(); + return Math.round(originalPrice * discountPercent); + } + + /** + * Подсчитывает общую сумму покупки со скидкой + */ + @Override + public long getPrice() { + long originalPrice = super.getPrice(); + return originalPrice - getDiscountAbsolute(); + } + + @Override + public String toString() { + StringBuilder sb = new StringBuilder("Счет к оплате (со скидкой " + (discountPercent * 100) + "%)\n"); + // Здесь нужно получить доступ к items из родительского класса + // Поскольку items приватные, используем унаследованное поведение + return super.toString().replace("Счет к оплате", "Счет к оплате (со скидкой " + (discountPercent * 100) + "%)") + + "\nСкидка: " + getDiscountAbsolute() + + "\nИтоговая сумма: " + getPrice(); + } +} \ No newline at end of file diff --git a/task02/src/com/example/task02/Task02Main.java b/task02/src/com/example/task02/Task02Main.java index e589f2d3..876177dc 100644 --- a/task02/src/com/example/task02/Task02Main.java +++ b/task02/src/com/example/task02/Task02Main.java @@ -10,12 +10,12 @@ public class Task02Main { private static final Item ITEM6 = new Item("Товар 6", 60); public static void main(String[] args) { - Bill bill = new Bill(); - bill.add(ITEM1, 10); - bill.add(ITEM3, 3); - bill.add(ITEM6, 1); - System.out.println(bill); - bill.add(ITEM3, 3); - System.out.println(bill); + DiscountBill discountBill = new DiscountBill(0.1); // 10% скидка + discountBill.add(ITEM1, 10); + discountBill.add(ITEM2, 5); + + System.out.println(discountBill); + System.out.println("Абсолютная скидка: " + discountBill.getDiscountAbsolute()); + System.out.println("Процент скидки: " + discountBill.getDiscountPercent()); } } diff --git a/task03/src/com/example/task03/Hours.java b/task03/src/com/example/task03/Hours.java new file mode 100644 index 00000000..c9c6e8a3 --- /dev/null +++ b/task03/src/com/example/task03/Hours.java @@ -0,0 +1,33 @@ +package com.example.task03; + +/** + * Интервал в часах + */ +public class Hours implements TimeUnit { + + private final long amount; + + public Hours(long amount) { + this.amount = amount; + } + + @Override + public long toMillis() { + return amount * 60 * 60 * 1000; + } + + @Override + public long toSeconds() { + return amount * 60 * 60; + } + + @Override + public long toMinutes() { + return amount * 60; + } + + @Override + public long toHours() { + return amount; + } +} \ No newline at end of file diff --git a/task03/src/com/example/task03/Milliseconds.java b/task03/src/com/example/task03/Milliseconds.java index 5115bc7d..36dc6422 100644 --- a/task03/src/com/example/task03/Milliseconds.java +++ b/task03/src/com/example/task03/Milliseconds.java @@ -18,11 +18,16 @@ public long toMillis() { @Override public long toSeconds() { - return amount / 1000; + return Math.round(amount / 1000.0); } @Override public long toMinutes() { - return amount / 1000 * 60; + return Math.round(amount / (1000.0 * 60)); } -} + + @Override + public long toHours() { + return Math.round(amount / (1000.0 * 60 * 60)); + } +} \ No newline at end of file diff --git a/task03/src/com/example/task03/Minutes.java b/task03/src/com/example/task03/Minutes.java index d6fa0594..a944ca37 100644 --- a/task03/src/com/example/task03/Minutes.java +++ b/task03/src/com/example/task03/Minutes.java @@ -1,27 +1,33 @@ package com.example.task03; +/** + * Интервал в минутах + */ public class Minutes implements TimeUnit { + private final long amount; + public Minutes(long amount) { - // TODO: реализовать - throw new UnsupportedOperationException(); + this.amount = amount; } @Override public long toMillis() { - // TODO: реализовать - throw new UnsupportedOperationException(); + return amount * 60 * 1000; } @Override public long toSeconds() { - // TODO: реализовать - throw new UnsupportedOperationException(); + return amount * 60; } @Override public long toMinutes() { - // TODO: реализовать - throw new UnsupportedOperationException(); + return amount; + } + + @Override + public long toHours() { + return Math.round(amount / 60.0); } -} +} \ No newline at end of file diff --git a/task03/src/com/example/task03/Seconds.java b/task03/src/com/example/task03/Seconds.java index ce6bc213..918ca5ef 100644 --- a/task03/src/com/example/task03/Seconds.java +++ b/task03/src/com/example/task03/Seconds.java @@ -23,6 +23,11 @@ public long toSeconds() { @Override public long toMinutes() { - return Math.round(amount / 60); + return Math.round(amount / 60.0); } -} + + @Override + public long toHours() { + return Math.round(amount / (60.0 * 60)); + } +} \ No newline at end of file diff --git a/task03/src/com/example/task03/TimeUnit.java b/task03/src/com/example/task03/TimeUnit.java index 3b123fb8..3bcaa7c4 100644 --- a/task03/src/com/example/task03/TimeUnit.java +++ b/task03/src/com/example/task03/TimeUnit.java @@ -28,4 +28,12 @@ public interface TimeUnit { */ long toMinutes(); + /** + * Возвращает продолжительность текущего интервала, пересчитанного в часах. + * При необходимости округлять по обычным правилам округления (число, меньшее 0.5 переходит в 0, большее или равное - в 1) + * + * @return количество часов в текущем интервале + */ + long toHours(); + } diff --git a/task03/src/com/example/task03/TimeUnitUtils.java b/task03/src/com/example/task03/TimeUnitUtils.java index 790f8850..33097f6f 100644 --- a/task03/src/com/example/task03/TimeUnitUtils.java +++ b/task03/src/com/example/task03/TimeUnitUtils.java @@ -24,4 +24,84 @@ public static Milliseconds toMillis(Seconds seconds) { public static Seconds toSeconds(Milliseconds millis) { return new Seconds(millis.toSeconds()); } -} + + /** + * Конвертирует интервал в минутах в интервал в миллисекундах + * + * @param minutes интервал в минутах + * @return интервал в миллисекундах + */ + public static Milliseconds toMillis(Minutes minutes) { + return new Milliseconds(minutes.toMillis()); + } + + /** + * Конвертирует интервал в миллисекундах в интервал в минутах + * + * @param millis интервал в миллисекундах + * @return интервал в минутах + */ + public static Minutes toMinutes(Milliseconds millis) { + return new Minutes(millis.toMinutes()); + } + + /** + * Конвертирует интервал в секундах в интервал в минутах + * + * @param seconds интервал в секундах + * @return интервал в минутах + */ + public static Minutes toMinutes(Seconds seconds) { + return new Minutes(seconds.toMinutes()); + } + + /** + * Конвертирует интервал в минутах в интервал в секундах + * + * @param minutes интервал в минутах + * @return интервал в секундах + */ + public static Seconds toSeconds(Minutes minutes) { + return new Seconds(minutes.toSeconds()); + } + + /** + * Конвертирует интервал в часах в интервал в миллисекундах + * + * @param hours интервал в часах + * @return интервал в миллисекундах + */ + public static Milliseconds toMillis(Hours hours) { + return new Milliseconds(hours.toMillis()); + } + + /** + * Конвертирует интервал в миллисекундах в интервал в часах + * + * @param millis интервал в миллисекундах + * @return интервал в часах + */ + public static Hours toHours(Milliseconds millis) { + return new Hours(millis.toHours()); + } + + /** + * Конвертирует интервал в секундах в интервал в часах + * + * @param seconds интервал в секундах + * @return интервал в часах + */ + public static Hours toHours(Seconds seconds) { + return new Hours(seconds.toHours()); + } + + /** + * Конвертирует интервал в минутах в интервал в часах + * + * @param minutes интервал в минутах + * @return интервал в часах + */ + public static Hours toHours(Minutes minutes) { + return new Hours(minutes.toHours()); + } +} \ No newline at end of file diff --git a/task04/src/com/example/task04/ConsoleHandler.java b/task04/src/com/example/task04/ConsoleHandler.java new file mode 100644 index 00000000..d8b21aaf --- /dev/null +++ b/task04/src/com/example/task04/ConsoleHandler.java @@ -0,0 +1,12 @@ +package com.example.task04; + +/** + * Обработчик, выводящий сообщения в консоль + */ +public class ConsoleHandler implements MessageHandler { + + @Override + public void handleMessage(String message) { + System.out.println(message); + } +} \ No newline at end of file diff --git a/task04/src/com/example/task04/FileHandler.java b/task04/src/com/example/task04/FileHandler.java new file mode 100644 index 00000000..205bc2a0 --- /dev/null +++ b/task04/src/com/example/task04/FileHandler.java @@ -0,0 +1,58 @@ +package com.example.task04; + +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; +import java.io.PrintWriter; + +/** + * Обработчик, выводящий сообщения в файл + */ +public class FileHandler implements MessageHandler { + private final String filePath; + private PrintWriter writer; + + public FileHandler(String filePath) { + this.filePath = filePath; + + // Создаем родительские директории, если они не существуют + createParentDirs(filePath); + + try { + // Открываем файл в режиме дозаписи + this.writer = new PrintWriter(new FileWriter(filePath, true)); + } catch (IOException e) { + throw new RuntimeException("Не удалось открыть файл для записи: " + filePath, e); + } + } + + @Override + public void handleMessage(String message) { + writer.println(message); + writer.flush(); // Сбрасываем буфер после каждой записи + } + + /** + * Создает все родительские директории для указанного пути + */ + private void createParentDirs(String filePath) { + File file = new File(filePath); + File parentDir = file.getParentFile(); + + if (parentDir != null && !parentDir.exists()) { + boolean created = parentDir.mkdirs(); + if (!created) { + System.err.println("Не удалось создать директорию: " + parentDir.getAbsolutePath()); + } + } + } + + /** + * Закрывает файловый поток + */ + public void close() { + if (writer != null) { + writer.close(); + } + } +} \ No newline at end of file diff --git a/task04/src/com/example/task04/Logger.java b/task04/src/com/example/task04/Logger.java new file mode 100644 index 00000000..b61d76ba --- /dev/null +++ b/task04/src/com/example/task04/Logger.java @@ -0,0 +1,112 @@ +package com.example.task04; + +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; +import java.util.ArrayList; +import java.util.List; + +/** + * Продвинутый логгер с поддержкой различных обработчиков сообщений + */ +public class Logger { + private static final DateTimeFormatter DATE_FORMATTER = DateTimeFormatter.ofPattern("yyyy.MM.dd"); + private static final DateTimeFormatter TIME_FORMATTER = DateTimeFormatter.ofPattern("HH:mm:ss"); + + private final String name; + private Level level; + private final List handlers; + + public enum Level { + DEBUG, + INFO, + WARNING, + ERROR + } + + public Logger(String name) { + this.name = name; + this.level = Level.DEBUG; + this.handlers = new ArrayList<>(); + } + + public String getName() { + return name; + } + + public Level getLevel() { + return level; + } + + public void setLevel(Level level) { + this.level = level; + } + + /** + * Добавляет обработчик сообщений + */ + public void addHandler(MessageHandler handler) { + handlers.add(handler); + } + + /** + * Удаляет обработчик сообщений + */ + public void removeHandler(MessageHandler handler) { + handlers.remove(handler); + } + + private boolean shouldLog(Level messageLevel) { + return messageLevel.ordinal() >= level.ordinal(); + } + + private void log(Level level, String message) { + if (!shouldLog(level)) return; + + String timestamp = getFormattedTimestamp(); + String formattedMessage = String.format("[%s] %s %s - %s", + level, timestamp, name, message); + + // Передаем сообщение всем обработчикам + for (MessageHandler handler : handlers) { + handler.handleMessage(formattedMessage); + } + } + + private String getFormattedTimestamp() { + LocalDateTime now = LocalDateTime.now(); + return now.format(DATE_FORMATTER) + " " + now.format(TIME_FORMATTER); + } + + // Методы для уровней логирования + public void debug(String message) { + log(Level.DEBUG, message); + } + + public void debug(String template, Object... args) { + log(Level.DEBUG, String.format(template, args)); + } + + public void info(String message) { + log(Level.INFO, message); + } + + public void info(String template, Object... args) { + log(Level.INFO, String.format(template, args)); + } + + public void warning(String message) { + log(Level.WARNING, message); + } + + public void warning(String template, Object... args) { + log(Level.WARNING, String.format(template, args)); + } + + public void error(String message) { + log(Level.ERROR, message); + } + + public void error(String template, Object... args) { + log(Level.ERROR, String.format(template, args)); + } +} \ No newline at end of file diff --git a/task04/src/com/example/task04/LoggerFactory.java b/task04/src/com/example/task04/LoggerFactory.java new file mode 100644 index 00000000..3357d9e3 --- /dev/null +++ b/task04/src/com/example/task04/LoggerFactory.java @@ -0,0 +1,18 @@ +package com.example.task04; + +import java.util.HashMap; +import java.util.Map; + +/** + * Утилитный класс для управления логгерами + */ +public class LoggerFactory { + private static final Map LOGGERS = new HashMap<>(); + + /** + * Возвращает логгер с указанным именем + */ + public static Logger getLogger(String name) { + return LOGGERS.computeIfAbsent(name, Logger::new); + } +} \ No newline at end of file diff --git a/task04/src/com/example/task04/MemoryHandler.java b/task04/src/com/example/task04/MemoryHandler.java new file mode 100644 index 00000000..04ec91e1 --- /dev/null +++ b/task04/src/com/example/task04/MemoryHandler.java @@ -0,0 +1,46 @@ +package com.example.task04; + +import java.util.ArrayList; +import java.util.List; + +/** + * Обработчик, буферизующий сообщения в памяти + */ +public class MemoryHandler implements MessageHandler { + private final MessageHandler targetHandler; + private final int bufferSize; + private final List buffer; + + public MemoryHandler(MessageHandler targetHandler, int bufferSize) { + this.targetHandler = targetHandler; + this.bufferSize = bufferSize; + this.buffer = new ArrayList<>(bufferSize); + } + + @Override + public void handleMessage(String message) { + buffer.add(message); + + // Если буфер заполнен, сбрасываем сообщения в целевой обработчик + if (buffer.size() >= bufferSize) { + flush(); + } + } + + /** + * Принудительно сбрасывает буферизованные сообщения в целевой обработчик + */ + public void flush() { + for (String message : buffer) { + targetHandler.handleMessage(message); + } + buffer.clear(); + } + + /** + * Возвращает количество сообщений в буфере + */ + public int getBufferSize() { + return buffer.size(); + } +} \ No newline at end of file diff --git a/task04/src/com/example/task04/MessageHandler.java b/task04/src/com/example/task04/MessageHandler.java new file mode 100644 index 00000000..9ce11805 --- /dev/null +++ b/task04/src/com/example/task04/MessageHandler.java @@ -0,0 +1,12 @@ +package com.example.task04; + +/** + * Интерфейс для обработчиков сообщений логгера + */ +public interface MessageHandler { + /** + * Обрабатывает сообщение логгера + * @param message сообщение для обработки + */ + void handleMessage(String message); +} \ No newline at end of file diff --git a/task04/src/com/example/task04/RotationFileHandler.java b/task04/src/com/example/task04/RotationFileHandler.java new file mode 100644 index 00000000..ea60f9f6 --- /dev/null +++ b/task04/src/com/example/task04/RotationFileHandler.java @@ -0,0 +1,98 @@ +package com.example.task04; + +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; +import java.io.PrintWriter; +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; +import java.time.temporal.ChronoUnit; + +/** + * Обработчик с ротацией файлов по времени + */ +public class RotationFileHandler implements MessageHandler { + private final String basePath; + private final ChronoUnit rotationUnit; + private final DateTimeFormatter fileFormatter; + + private PrintWriter currentWriter; + private String currentPeriod; + private LocalDateTime lastRotationTime; + + public RotationFileHandler(String basePath, ChronoUnit rotationUnit) { + this.basePath = basePath; + this.rotationUnit = rotationUnit; + this.fileFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd_HH-mm-ss"); + this.lastRotationTime = LocalDateTime.now(); + + // Создаем родительские директории, если они не существуют + createParentDirs(basePath); + rotateIfNeeded(); + } + + @Override + public void handleMessage(String message) { + rotateIfNeeded(); + currentWriter.println(message); + currentWriter.flush(); + } + + private void rotateIfNeeded() { + LocalDateTime now = LocalDateTime.now(); + LocalDateTime truncatedNow = now.truncatedTo(rotationUnit); + LocalDateTime truncatedLast = lastRotationTime.truncatedTo(rotationUnit); + + // Если текущий период отличается от предыдущего, выполняем ротацию + if (!truncatedNow.equals(truncatedLast)) { + if (currentWriter != null) { + currentWriter.close(); + } + + String timestamp = truncatedNow.format(fileFormatter); + String fileName = basePath + "_" + timestamp + ".log"; + + try { + currentWriter = new PrintWriter(new FileWriter(fileName, true)); + lastRotationTime = now; + } catch (IOException e) { + throw new RuntimeException("Не удалось создать файл для ротации: " + fileName, e); + } + } + + // Инициализация при первом вызове + if (currentWriter == null) { + String timestamp = truncatedNow.format(fileFormatter); + String fileName = basePath + "_" + timestamp + ".log"; + try { + currentWriter = new PrintWriter(new FileWriter(fileName, true)); + } catch (IOException e) { + throw new RuntimeException("Не удалось создать файл: " + fileName, e); + } + } + } + + /** + * Создает все родительские директории для указанного пути + */ + private void createParentDirs(String filePath) { + File file = new File(filePath); + File parentDir = file.getParentFile(); + + if (parentDir != null && !parentDir.exists()) { + boolean created = parentDir.mkdirs(); + if (!created) { + System.err.println("Не удалось создать директорию: " + parentDir.getAbsolutePath()); + } + } + } + + /** + * Закрывает текущий файловый поток + */ + public void close() { + if (currentWriter != null) { + currentWriter.close(); + } + } +} \ No newline at end of file diff --git a/task04/src/com/example/task04/Task04Main.java b/task04/src/com/example/task04/Task04Main.java index 55917a30..27f7353c 100644 --- a/task04/src/com/example/task04/Task04Main.java +++ b/task04/src/com/example/task04/Task04Main.java @@ -1,7 +1,45 @@ package com.example.task04; +import java.time.temporal.ChronoUnit; + public class Task04Main { public static void main(String[] args) { + try { + // Создаем логгер + Logger logger = LoggerFactory.getLogger("main"); + logger.setLevel(Logger.Level.INFO); + + // Добавляем несколько обработчиков + logger.addHandler(new ConsoleHandler()); + logger.addHandler(new FileHandler("application.log")); + + // Создаем RotationFileHandler с обработкой возможных ошибок + try { + RotationFileHandler rotationHandler = new RotationFileHandler("logs/app", ChronoUnit.HOURS); + logger.addHandler(rotationHandler); + } catch (Exception e) { + System.err.println("Не удалось создать RotationFileHandler: " + e.getMessage()); + // Создаем резервный обработчик в текущей директории + RotationFileHandler fallbackHandler = new RotationFileHandler("app_logs", ChronoUnit.HOURS); + logger.addHandler(fallbackHandler); + } + + // MemoryHandler с буфером на 5 сообщений, сбрасывающий в консоль + MemoryHandler memoryHandler = new MemoryHandler(new ConsoleHandler(), 5); + logger.addHandler(memoryHandler); + + // Логируем сообщения + logger.info("Приложение запущено"); + logger.debug("Отладочная информация"); // Не будет выведено, т.к. уровень INFO + logger.warning("Нехватка памяти: %d МБ свободно", 512); + logger.error("Ошибка подключения к базе данных"); + + // Принудительно сбрасываем буфер MemoryHandler + memoryHandler.flush(); + } catch (Exception e) { + System.err.println("Критическая ошибка при настройке логирования: " + e.getMessage()); + e.printStackTrace(); + } } -} +} \ No newline at end of file