Search code examples
javawindowscsvgraalvm

java.time.format.DateTimeParseException is raised only when my code is executed in Windows 10


The following code throws a java.time.format.DateTimeParseException only when it's executed in a Windows 10 environment (Version Version 10.0.19045.5247). I tested it using two different JVMs, Graal JDK 17.0.2 and Eclipse Adoptium 11.0.15.10-hotspot, from two different IDEs (IntelliJ IDEA 2024.1.7 Ultimate and VS Code 1.96.2):

package com.xxx    

import java.io.*;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class Main {
    public static void main(String[] args) {
        final File FILE = new File("C:\\Users\\xxx\\Downloads\\alarms.csv");
        // example date: Dec 19, 2024 5:20:53 PM
        final String DATE_PATTERN_REGEX = "\"([a-zA-Z]{3} [0-9]{1,2}, 2024 [0-9]{1,2}:[0-9]{1,2}:[0-9]{1,2} PM)\"";
        final Pattern PATTERN = Pattern.compile(DATE_PATTERN_REGEX);
        final String DATE_PATTERN = "MMM dd, yyyy KK:mm:ss a";
        final DateTimeFormatter DATE_TIME_FORMAT = DateTimeFormatter.ofPattern(DATE_PATTERN);

        try (BufferedReader br = new BufferedReader(new FileReader(FILE))) {
            br.lines().forEach(line -> {
                Matcher matcher = PATTERN.matcher(line);
                List<LocalDateTime> timestamps = new ArrayList<>(2);
                while (matcher.find()) {
                    timestamps.add(LocalDateTime.parse(matcher.group(1), DATE_TIME_FORMAT));
                }
                if (timestamps.size() == 2) {
                    if (timestamps.get(0).equals(timestamps.get(1))) {
                        System.out.println(line);
                    }
                }
            });
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

A sample line of the file alarms.csv is the following one:

major,"Dec 19, 2024 5:20:53 PM","Dec 19, 2024 5:21:00 PM",interface:xxx,onu-loss-of-phy-layer,"Event=loss of PHY connectivity with ONU due to missing bursts (LOFi/LOSi or LOBi), Serial-Number=xxx, Reg-ID=, CT-Name=xxx; model-name: xxx; description: xxx",0-1 min

The full stack trace of the thrown exception is the following:

java.time.format.DateTimeParseException: Text 'Dec 19, 2024 5:20:53 PM' could not be parsed at index 0
    at java.base/java.time.format.DateTimeFormatter.parseResolved0(DateTimeFormatter.java:2052)
    at java.base/java.time.format.DateTimeFormatter.parse(DateTimeFormatter.java:1954)
    at java.base/java.time.LocalDateTime.parse(LocalDateTime.java:494)
    at com.xxx.Main.lambda$main$0(Main.java:25)
    at java.base/java.util.Iterator.forEachRemaining(Iterator.java:133)
    at java.base/java.util.Spliterators$IteratorSpliterator.forEachRemaining(Spliterators.java:1845)
    at java.base/java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:762)
    at com.xxx.Main.main(Main.java:21)

Notice that this exception is thrown only when I run this code on Windows. When I moved the alarms.csv file to my WSL2 environment (Ubuntu 20.04) and executed the same code in my WSL box using Eclipse Adoptium 11.0.15.10-hotspot, it worked properly, as expected.

Is there any known problem with parsing of CSV files in Windows that affects the mentioned JVMs? If so, what to do in order to remedy it?


Solution

  • Problem got resolved after I followed @Basil Bourque's suggestion and specified the correct locale to the DateTimeFormatter:

    Specify a Locale appropriate to the input.

    Since my input, Dec 19, 2024 5:20:53 PM, is in English, I need to specify an English-speaking locale, for example:

    DateTimeFormatter.ofPattern(DATE_PATTERN, Locale.of("en"));