1

Is there any function in joda.time which validates a string whether it represents correct time zone or not and throws a exception if it is not in the correct format?

I am aware of TimeZone.getAvalibaleIDs() but just curious to know if there is any predefined function.

AlexWien
  • 28,470
  • 6
  • 53
  • 83
user1772643
  • 615
  • 3
  • 11
  • 23

3 Answers3

6

DateTimeZone.forID() will throw an exception if the ID isn't recognized.

That's appropriate if you're trying to get the actual zone - if you're just trying to validate whether an ID is valid or not, I'd use getAvailableIDs():

boolean valid = DateTimeZone.getAvailableIDs().contains(id);

That's better in terms of avoiding using exceptions for flow control, IMO. However, they're not equivalent - fixed-offset time zone IDs are valid in DateTimeZone.forID(), but may not be included in the set of available IDs.

Jon Skeet
  • 1,421,763
  • 867
  • 9,128
  • 9,194
  • I found DateTimeZone does not have PST as a Id. But java.util.TimeZone has it. – Harshana Nov 28 '16 at 07:57
  • @Harshana: That makes sense - PST isn't an IANA ID. `java.util.TimeZone` has a bunch of "features" that leave a bit to be desired. You should find the appropriate time zone ID for what you want, e.g. `America/Los_Angeles`. (But not necessarily that one...) – Jon Skeet Nov 28 '16 at 08:04
2

java.time

Quoted below is a notice from the home page of Joda-Time:

Note that from Java SE 8 onwards, users are asked to migrate to java.time (JSR-310) - a core part of the JDK which replaces this project.

Solution using java.time, the modern Date-Time API: Process ZoneId.of under try/catch and catch the exception for the invalid timezone ID.

Demo:

import java.time.ZoneId;
import java.time.zone.ZoneRulesException;
import java.util.stream.Stream;

public class Main {
    public static void main(String[] args) {
        Stream.of(
                "America/New_York",
                "GMT",
                "UTC",
                "UCT",
                "GMT+01:00",
                "UTC+01:00",
                "ABC"
        ).forEach(s -> {
            try {
                System.out.println(ZoneId.of(s));
            } catch (ZoneRulesException e) {
                System.out.println(e.getMessage());
            }
        });
    }
}

Output:

America/New_York
GMT
UTC
UCT
GMT+01:00
UTC+01:00
Unknown time-zone ID: ABC

ONLINE DEMO

I do not recommend ZoneId.getAvailableZoneIds().contains(time-zone-id) because it may fail for some cases as shown below:

import java.time.ZoneId;
import java.util.Arrays;
import java.util.Set;

public class Main {
    public static void main(String[] args) {
        String[] arr = { "America/New_York", "GMT", "UTC", "UCT", "GMT+01:00", "UTC+01:00", "ABC" };

        // Alternatively
        Set<String> allZones = ZoneId.getAvailableZoneIds();
        Arrays.stream(arr).forEach(s -> System.out.println(allZones.contains(s) ? s : ("Unknown time-zone ID: " + s)));
    }
}

Output:

America/New_York
GMT
UTC
UCT
Unknown time-zone ID: GMT+01:00
Unknown time-zone ID: UTC+01:00
Unknown time-zone ID: ABC

ONLINE DEMO

Learn more about the modern Date-Time API from Trail: Date Time.


* For any reason, if you have to stick to Java 6 or Java 7, you can use ThreeTen-Backport which backports most of the java.time functionality to Java 6 & 7. If you are working for an Android project and your Android API level is still not compliant with Java-8, check Java 8+ APIs available through desugaring and How to use ThreeTenABP in Android Project.

Arvind Kumar Avinash
  • 71,965
  • 6
  • 74
  • 110
0

You can write a piece of function like below instead of using Joda:

private boolean isTimeZoneValid(String givenTimeZone) {
    Set timeZoneSet = new HashSet(Arrays.asList(TimeZone.getAvailableIDs()));
    return timeZoneSet.contains(givenTimeZone); 
}
vtokmak
  • 1,496
  • 6
  • 35
  • 66