ISO8601 timestamp generators

Share actions you've created here.
Post Reply
Jesse
Posts: 11
Joined: Wed Jul 27, 2011 1:52 pm

ISO8601 timestamp generators

Post by Jesse » Thu Jul 11, 2019 11:38 pm

ISO8601 is a popular standard for writing out dates and times.

The standard has a lot of advantages.
  • When you start a lot of filenames with these timestamps, they will naturally sort into chronological order.
  • When you tag a lot of events with these timestamps, then even when you're working with people in different timezones it's pretty easy to reconcile what happened when relative to one another.
The format has a few different variants, but the one that I use the most looks like this:

YYYY-MM-DDTHH:ii:ss[+-]TH:TI

Where
  • YYYY = four digit year
  • MM = two digit Month number, with leading zero if required.
  • DD = two digit Day of month number, with leading zero if required.
  • T = The literal letter T. This serves only to separate the date from the time.
  • HH = The two digit Hour, in 24 hour format (so 13-23 means 1pm to 11pm and 00 means midnight).
  • ii = minutes
  • ss = seconds (optional, this value and it's colon delimiter can be ommitted)
  • [+-]TH:TI is your timezone offset, or how many hours and minutes away from GMT you are. One can use just a "Z" as a shortcut for GMT itself, but my script doesn't generate that abbreviation.
  • [+-] is either a + or a - indicating your timezone is either ahead of or behind GMT. Hint: all American timezones are - as in behind GMT.
  • TH is hours and TI is minutes.
  • If you observe daylight savings time, then your timezone offset actually changes when daylight savings turns on or off. For example, in Pacific timezone where I live, -08:00 is standard time and -07:00 is daylight savings time.
So it's handy to have a 3dclipboard action that just generate such a timestamp for you on command, and then that can be added to documents or into filenames as required. :)

I have three scripts for this that serve the three variants of time timestamp I frequently use.

ISO8601 seconds with colons [VBScript]
This one is the standard approach.

Code: Select all

' Warning! Does not yet properly handle fractional hour timezones! Hard To test for that from the US. :P
' I do not ordinarily run this action with a keyboard shortcut, as it just seems to be needed less frequently than it's minutes' cousins. :)

Public Function ToIsoDateTime(datetime) 
  ToIsoDateTime = ToIsoDate(datetime) & "T" & ToIsoTime(datetime) & GetTimeZoneOffset()
End Function

Public Function ToIsoDate(datetime)
  ToIsoDate = CStr(Year(datetime)) & "-" & StrN2(Month(datetime),"") & "-" & StrN2(Day(datetime),"")
End Function    

Public Function ToIsoTime(datetime) 
  ToIsoTime = StrN2(Hour(datetime),"") & ":" & StrN2(Minute(datetime),"") & ":" & StrN2(Second(datetime),"")
End Function

Function GetTimeZoneOffset()
  Const sComputer = "."

  Dim oWmiService : Set oWmiService = _
    GetObject("winmgmts:{impersonationLevel=impersonate}!\\" _
      & sComputer & "\root\cimv2")

  Set cItems = oWmiService.ExecQuery("SELECT * FROM Win32_ComputerSystem")

  For Each oItem In cItems
    GetTimeZoneOffset = oItem.CurrentTimeZone / 60
    GetTimeZoneOffset = StrN2(GetTimeZoneOffset,"+") & ":00"
    Exit For
  Next
End Function

Private Function StrN2(n,positiveSign)
  n = CInt(n)
  If n<0 Then
    sign = "-"
    n = -n
  Else
    sign = positiveSign
  End If
  If Len(n) < 2 Then StrN2 = "0" & n Else StrN2 = n
  StrN2 = sign & StrN2
  StrN2 = CStr(StrN2)
End Function

Clipboard.Value = ToIsoDateTime(NOW())
ISO8601 minutes with colons [VBScript]
This is the same but ommitting the seconds, as I do not frequently require that fine of a resolution in my timestamps.

Code: Select all

' Warning! Does not yet properly handle fractional hour timezones! Hard To test for that from the US. :P
' I usually run this action with keyboard shortcut CTRL+ALT+SHIFT + I

Public Function ToIsoDateTime(datetime) 
  ToIsoDateTime = ToIsoDate(datetime) & "T" & ToIsoTime(datetime) & GetTimeZoneOffset()
End Function

Public Function ToIsoDate(datetime)
  ToIsoDate = CStr(Year(datetime)) & "-" & StrN2(Month(datetime),"") & "-" & StrN2(Day(datetime),"")
End Function    

Public Function ToIsoTime(datetime) 
  ToIsoTime = StrN2(Hour(datetime),"") & ":" & StrN2(Minute(datetime),"")
End Function

Function GetTimeZoneOffset()
  Const sComputer = "."

  Dim oWmiService : Set oWmiService = _
    GetObject("winmgmts:{impersonationLevel=impersonate}!\\" _
      & sComputer & "\root\cimv2")

  Set cItems = oWmiService.ExecQuery("SELECT * FROM Win32_ComputerSystem")

  For Each oItem In cItems
    GetTimeZoneOffset = oItem.CurrentTimeZone / 60
    GetTimeZoneOffset = StrN2(GetTimeZoneOffset,"+") & ":00"
    Exit For
  Next
End Function

Private Function StrN2(n,positiveSign)
  n = CInt(n)
  If n<0 Then
    sign = "-"
    n = -n
  Else
    sign = positiveSign
  End If
  If Len(n) < 2 Then StrN2 = "0" & n Else StrN2 = n
  StrN2 = sign & StrN2
  StrN2 = CStr(StrN2)
End Function

Clipboard.Value = ToIsoDateTime(NOW())
ISO8601 no colons [VBScript]
This one I use perhaps the most frequently:
It both ommits the seconds AND mildly breaks with standard by ommitting the colons.
This is important because Windows cannot handle filenames that contain a colon.
Ultimately it's easy for humans to still read this way, and programs that I make can either still parse the time offered or else re-add the colons to the right places to feed into an ISO8601-expecting module.

Code: Select all

' Warning! Does not yet properly handle fractional hour timezones! Hard To test for that from the US. :P
' I usually run this action with keyboard shortcut CTRL+SHIFT + I

Public Function ToIsoDateTime(datetime) 
  ToIsoDateTime = ToIsoDate(datetime) & "T" & ToIsoTime(datetime) & GetTimeZoneOffset()
End Function

Public Function ToIsoDate(datetime)
  ToIsoDate = CStr(Year(datetime)) & "-" & StrN2(Month(datetime),"") & "-" & StrN2(Day(datetime),"")
End Function    

Public Function ToIsoTime(datetime) 
  ToIsoTime = StrN2(Hour(datetime),"") & StrN2(Minute(datetime),"")
End Function

Function GetTimeZoneOffset()
  Const sComputer = "."

  Dim oWmiService : Set oWmiService = _
    GetObject("winmgmts:{impersonationLevel=impersonate}!\\" _
      & sComputer & "\root\cimv2")

  Set cItems = oWmiService.ExecQuery("SELECT * FROM Win32_ComputerSystem")

  For Each oItem In cItems
    GetTimeZoneOffset = oItem.CurrentTimeZone / 60
    GetTimeZoneOffset = StrN2(GetTimeZoneOffset,"+") & "00"
    Exit For
  Next
End Function

Private Function StrN2(n,positiveSign)
  n = CInt(n)
  If n<0 Then
    sign = "-"
    n = -n
  Else
    sign = positiveSign
  End If
  If Len(n) < 2 Then StrN2 = "0" & n Else StrN2 = n
  StrN2 = sign & StrN2
  StrN2 = CStr(StrN2)
End Function

Clipboard.Value = ToIsoDateTime(NOW())
Remember that if you use a keyboard shortcut, it often will not fire off when your presently selected clipboard item (which is otherwise irrelevant to this operation and will not be replaced) is one of your stickies. :/

Post Reply