Java поиск последнего файла в каталоге от даты в имени файла - PullRequest
0 голосов
/ 05 марта 2020

У меня есть каталог, в который я получаю файлы, соответствующие шаблону ABC_STOCK_List_YYYYMMDD_YYYYMMDD.csv. Я пишу запланированный сервис в java, где мне нужно проверить файл на сегодня, дату, а затем выполнить мой процесс для этого файла.

ABC_STOCK_List_20200220_20200220.csv
ABC_STOCK_List_20200219_20200219.csv
ABC_STOCK_List_20200218_20200218.csv
ABC_STOCK_List_20200217_20200217.csv

Пока у меня есть это:

private Optional<File> findLatestFile(final String dir) {
    return Stream.of(new File(dir).listFiles())
                 .filter(
                         file -> !file.isDirectory()
                                 && file.getName().startsWith(prefix)
                                 && file.getName().endsWith(".csv")
                                 && isTodaysFile(file)
                 )
                 .findFirst();

}

private boolean isTodaysFile(File file) {
    return false;
}

Мне нужна помощь с isTodaysFile(), которая должна проверить последнее YYYYMMDD - сегодняшняя дата. Он должен опираться не только на дату из имени файла, но и на время файловой системы created или modified, которое также должно быть сегодня.

1 Ответ

1 голос
/ 05 марта 2020

Вот мой подход к этой проблеме. Сначала я создал две вспомогательные функции, одна из которых извлекает дату окончания из имени файла, а другая - файловую систему modified время. Я не думаю, что нужно проверять время created, поскольку всегда созданное время меньше или равно измененному времени даты.

Функция, которая извлекает дату окончания имени файла:

private LocalDate getEndDate(File file) {
    String fileName = file.getName();
    String fileNameWithoutExtension = fileName.substring(0, fileName.lastIndexOf("."));
    String[] fileNameChunks = fileNameWithoutExtension.split("_");
    String endDateAsString = fileNameChunks[fileNameChunks.length - 1];

    return LocalDate.parse(endDateAsString, DateTimeFormatter.ofPattern("yyyyMMdd"));
}

Далее, функция, которая извлекает файловую систему modified для файла. Для этого я использую Files#getLastModifiedTime для получения даты modified:

private LocalDate getLastModifiedDate(File file, ZoneId zoneId) {
    try {
        return ZonedDateTime
                .ofInstant(Files.getLastModifiedTime(file.toPath()).toInstant(), zoneId)
                .toLocalDate();
    } catch (IOException e) {
        throw new RuntimeException("Could not read file attributes: " + file.getAbsolutePath());
    }
}

В конце концов, это просто вызов этих функций и выполнение проверок:

boolean isTodaysFile(File file) {
    Clock systemUTCClock = Clock.systemUTC();
    LocalDate localDateNow = LocalDate.now(systemUTCClock);

    LocalDate fileEndDate = getEndDate(file);

    // first check - validate that the file name's end date is today
    if (!fileEndDate.isEqual(localDateNow)) {
        return false;
    }

    LocalDate lastModifiedDate = getLastModifiedDate(file, systemUTCClock.getZone());

    // second check - validate that the modified that is today
    // no need to check the creation date, since creation date is always less or equal to the last modified date
    return lastModifiedDate.equals(localDateNow);
}

Я использую Clock.systemUTC() и создаю для него все даты, чтобы убедиться, что мы всегда используем UT C.

  • LocalDate.now(systemUTCClock)
  • systemUTCClock.getZone()

Если входные файлы в каталоге:

ABC_STOCK_List_20200220_20200220.csv
ABC_STOCK_List_20200219_20200219.csv
ABC_STOCK_List_20200218_20200218.csv
ABC_STOCK_List_20200217_20200217.csv
ABC_STOCK_List_20200305_20200305.csv

На дату написания этой записи текущая дата 03-05-2020 . Выходной файл при вызове findLatestFile:

ABC_STOCK_List_20200217_20200305.csv

Примечания:

  • Я не выполнял никаких проверок формата имени файла. Если что-то не так с форматом, вы можете получить некоторые ошибки при получении даты окончания.
...