Scala - Dates and Times



You often need to work with dates and times. Scala provides various ways to work with dates and times. It has various ecosystems and syntax for working with dates and times. We will discuss dates and times in Scala in this post.

Dates and Times in Scala

There are various classes and types in Scala for precise manipulation and calculation of temporal data. Scala provides support for date and time operations through its standard library and external libraries like java.time package in Java. Scala runs on the JVM. Therefore, it has access to all the date and time classes available in the JDK. However, Scala also provides libraries that provide a more idiomatic way of handling date-time calculations.

Importing Libraries

You can use the java.time package to work with dates and times in Scala. You can import the necessary classes at the beginning of your Scala file.

For example,

import java.time.{LocalDate, LocalTime, LocalDateTime, ZonedDateTime, ZoneId}
import java.time.format.DateTimeFormatter

Getting Current Date and Time

You can easily get the current date and time using LocalDate, LocalTime and LocalDateTime.

Example

The following example demonstrates how you can get the current date and time in Scala:

import java.time.{LocalDate, LocalTime, LocalDateTime}

object Demo {
  def main(args: Array[String]): Unit = {
    val currentDate: LocalDate = LocalDate.now()
    val currentTime: LocalTime = LocalTime.now()
    val currentDateTime: LocalDateTime = LocalDateTime.now()
    
    println(s"Current Date: $currentDate")
    println(s"Current Time: $currentTime")
    println(s"Current Date and Time: $currentDateTime")
  }
} 

The output will be current date, current time and current date with time respectively.

Save the above program in Demo.scala. The following commands are used to compile and execute this program.

Command

\>scalac Demo.scala
\>scala Demo

Output

Current Date: 2024-06-21
Current Time: 07:58:41.245340235
Current Date and Time: 2024-06-21T07:58:41.245417866

Formatting Dates and Times

You can format dates and times is straightforward with DateTimeFormatter.

Example

The following example demonstrates the date time formats in Scala:

import java.time.LocalDate
import java.time.LocalTime
import java.time.format.DateTimeFormatter

object DateTimeExample {
  def main(args: Array[String]): Unit = {
    // Get the current date and time
    val currentDate: LocalDate = LocalDate.now()
    val currentTime: LocalTime = LocalTime.now()

    // Format the date
    val dateFormatter: DateTimeFormatter = DateTimeFormatter.ofPattern("dd-MM-yyyy")
    val formattedDate: String = currentDate.format(dateFormatter)

    // Format the time
    val timeFormatter: DateTimeFormatter = DateTimeFormatter.ofPattern("HH:mm:ss")
    val formattedTime: String = currentTime.format(timeFormatter)

    // Print the formatted date and time
    println(s"Formatted Date: $formattedDate")
    println(s"Formatted Time: $formattedTime")
  }
}

The output will be date in format of dd-MM-yyyy and time in format of HH:mm:ss respectively.

Parsing Dates and Times

You can parse a date or time from a string. You can use DateTimeFormatter along with the parse method.

Example

In the following example, we are parsing date and time from the string:

import java.time.LocalDate
import java.time.LocalTime
import java.time.format.DateTimeFormatter

object DateTimeParsingExample {
  def main(args: Array[String]): Unit = {
    // Define formatters for date and time
    val dateFormatter: DateTimeFormatter = DateTimeFormatter.ofPattern("dd-MM-yyyy")
    val timeFormatter: DateTimeFormatter = DateTimeFormatter.ofPattern("HH:mm:ss")

    // Parse a date string
    val dateStr: String = "20-05-2024"
    val parsedDate: LocalDate = LocalDate.parse(dateStr, dateFormatter)

    // Parse a time string
    val timeStr: String = "14:30:00"
    val parsedTime: LocalTime = LocalTime.parse(timeStr, timeFormatter)

    // Print the parsed date and time
    println(s"Parsed Date: $parsedDate")
    println(s"Parsed Time: $parsedTime")
  }
}

Working with ZonedDateTime

You can handle dates and times with time zones using ZonedDateTime.

Example

The following example demonstrates how you can work with ZonedDateTime in Scala:

import java.time.{ZonedDateTime, ZoneId}
import java.time.format.DateTimeFormatter

object ZonedDateTimeExample {
  def main(args: Array[String]): Unit = {
    // Get the current date-time in a specific time zone
    val zonedDateTime: ZonedDateTime = ZonedDateTime.now(ZoneId.of("America/New_York"))

    // Define a formatter with time zone information
    val zonedFormatter: DateTimeFormatter = DateTimeFormatter.ofPattern("dd-MM-yyyy HH:mm:ss z")

    // Format the zoned date-time
    val formattedZonedDateTime: String = zonedDateTime.format(zonedFormatter)

    // Print the formatted zoned date-time
    println(s"Formatted Zoned Date-Time: $formattedZonedDateTime")
  }
}  

The output is 20-05-2024 09:30:00 EDT

Adding and Subtracting Time

You can add and subtract time from a date and time using methods like plusDays, minusHours, etc.

Example

In the following example we are adding and substring the time –

import java.time.{LocalDate, LocalTime}

object DateTimeManipulationExample {
  def main(args: Array[String]): Unit = {
    // Get the current date and time
    val currentDate: LocalDate = LocalDate.now()
    val currentTime: LocalTime = LocalTime.now()

    // Perform date and time manipulations
    val tomorrow: LocalDate = currentDate.plusDays(1)
    val nextHour: LocalTime = currentTime.plusHours(1)
    val lastWeek: LocalDate = currentDate.minusWeeks(1)

    // Print the results
    println(s"Current Date: $currentDate")
    println(s"Tomorrow's Date: $tomorrow")
    println(s"Current Time: $currentTime")
    println(s"Time After One Hour: $nextHour")
    println(s"Date One Week Ago: $lastWeek")
  }
}

The output will be current date, current date, date of previous week.

Best Practices for Using Dates and Times in Scala

1. Use the java.time Package

You can use java.time package which is introduced in Java 8. But you should avoid using the outdated java.util.Date and java.util.Calendar.

import java.time.{LocalDate, LocalTime, LocalDateTime, ZonedDateTime, ZoneId}
import java.time.format.DateTimeFormatter

2. Prefer Immutable Types

There are immutable date and time types in java.time package. You can use these immutable types (LocalDate, LocalTime, LocalDateTime, ZonedDateTime) to avoid unexpected side effects and for thread safety.

3. Use Explicit Time Zones

When you work with date and time in different time zones. You should always use specific time zone explicitly to prevent ambiguity.

val zonedDateTime: ZonedDateTime = ZonedDateTime.now(ZoneId.of("America/New_York"))

4. Formatting and Parsing

You can use DateTimeFormatter for formatting and parsing dates and times. You should format patterns clearly for consistency.

5. Avoid Hardcoding Date Formats

You should not hardcode date formats in multiple places. Instead, you can define them as constants.

6. Use the Appropriate Type

You should use the appropriate type based on the precision you need. You can use LocalDate for dates without time, LocalTime for time without dates, and LocalDateTime and ZonedDateTime for both.

For example,

val dateOnly: LocalDate = LocalDate.now()
val timeOnly: LocalTime = LocalTime.now()
val dateTime: LocalDateTime = LocalDateTime.now()

7. Error Handling

You should use try and catch for error handling errors and exceptions.

For example,

try {
  val date: LocalDate = LocalDate.parse("invalid-date", formatter)
} catch {
  case e: DateTimeParseException => println("Invalid date format")
}
Advertisements