Obviously you’re welcome to make your own for your own use, but the names of the handlers — rfc3339FromDate: and dateFromRfc3339String: — imply conformance to RFC 3339.
One of the places I think people might want to use these sorts of handlers is in parsing JSON. There’s no standard defined for JSON dates, but many claim to be using RFC3339.
However, many are actually using "yyyy'-'MM'-'dd'T'HH':'mm':'ssXX" rather than "yyyy'-'MM'-'dd'T'HH':'mm':'ssXXX" (the difference is that RFC 3339 specifies time zones other than GMT as -06:00 rather than -0600). But as long as you stick to GMT-based values, the difference doesn’t matter.
Not for ISO 8601 and RFC 3339 formats. The reason for specifying “en_US_POSIX” is that if you leave the user’s locale (which will be the default if you don’t specify a locale), formatters can overrule the format string. In particular, HH can be interpreted differently depending on the locale’s settings.
Normally you can use:
current application's NSLocale's currentLocale()
Use:
current application's NSLocale's availableLocaleIdentifiers()
To get the identifier of the current locale:
current application's NSLocale's currentLocale()'s localeIdentifier()
So:
current application's NSLocale's localeWithLocaleIdentifier:"en_AU" -- for example
Hey Mark @alldritt, how do you use your handlers to get a date string from a custom (not now) date?
Also, how do you convert an AppleScript date to a NSDate in 10.12+, specifically Mojave?
This fails:
use framework "Foundation"
use scripting additions
set dateStr to "6/1/2019"
set myDate to date dateStr
### set theDate to current application's NSDate's |date|() -- now
### This Fails ###
# ERROR: Can’t get myDate of NSDate.
set theDate to current application's NSDate's myDate
set dateString to my rfc3339FromDate:theDate
--> "2017-11-27T06:38:31Z"
on rfc3339FromDate:aDate
set theFormatter to current application's NSDateFormatter's new()
theFormatter's setLocale:(current application's NSLocale's localeWithLocaleIdentifier:"en_US_POSIX")
theFormatter's setTimeZone:(current application's NSTimeZone's timeZoneWithAbbreviation:"GMT") -- skip for local time
theFormatter's setDateFormat:"yyyy'-'MM'-'dd'T'HH':'mm':'ssXXX"
return (theFormatter's stringFromDate:aDate) as text
end rfc3339FromDate:
A variant, using NSISO8601DateFormatter and the NSISO8601DateFormatWithInternetDateTime option.
( Perhaps Shane will know what versions of macOS support this, and what its limitations, if any, might be )
use AppleScript version "2.4"
use framework "Foundation"
use scripting additions
-- iso8601StringFromDate :: Date -> String
on iso8601StringFromDate(dte)
tell current application
set fmt to (its NSISO8601DateFormatWithInternetDateTime as integer)
tell init() of alloc of its NSISO8601DateFormatter
set formatOptions to fmt
stringFromDate_(dte) as string
end tell
end tell
end iso8601StringFromDate
-- dateFromiso8601String :: String -> Date
on dateFromiso8601String(strISO8601)
tell current application
set fmt to (its NSISO8601DateFormatWithInternetDateTime as integer)
tell init() of alloc of its NSISO8601DateFormatter
set formatOptions to fmt
dateFromString_(strISO8601) as date
end tell
end tell
end dateFromiso8601String
on run
dateFromiso8601String(iso8601StringFromDate(current date))
end run
NSISO8601DateFormatter requires 10.12 or later. But there was a glitch in the .bridgesupport file in 10.12 where the enums for it were left out, so you either have to define their values yourself in the script via properties (Script Debugger code-completion includes them in 10.12), or use the raw enums. Otherwise it’s effectively 10.13 or later.
I apologize Shane but under 10.13.6 the code posted by JTMichaelTX fails with error "Il est impossible d’obtenir myDate of NSDate.
If I replace
set theDate to current application’s NSDate’s myDate
by
set theDate to myDate
The script reach its end.
myDate is reported as : (date dimanche 6 janvier 2019 à 00:00:00) which is correct.
The final dateString is set to : “2019-01-05T23:00:00Z” which seems curious from my point of view.
Yvan KOENIG running High Sierra 10.13.6 in French (VALLAURIS, France) jeudi 25 juillet 2019 15:21:40
That’s right — you only need to involve current application’s NSDate for Cocoa dates, not AppleScript dates. Under 10.11 and greater, you can just pass an AppleScript date as-is.
Oops. Now I understand, the result is the Greenwich time.
If JTMichaelTX really need to build an NSDate from as Applescript date,he may use a handler given by Shane in Everyday AppleScriptObjC 3ed
use AppleScript version "2.4"
use framework "Foundation"
use scripting additions
on makeNSDateFrom:theASDate
set {theYear, theMonth, theDay, theSeconds} to theASDate's {year, month, day, time}
set theCalendar to current application's NSCalendar's currentCalendar()
set newDate to theCalendar's dateWithEra:1 |year|:theYear |month|:(theMonth as integer) |day|:theDay hour:0 minute:0 |second|:theSeconds nanosecond:0
--log (newDate's |description|() as text)
return newDate
end makeNSDateFrom:
set dateStr to "6/1/2019"
set theDate to date dateStr
log theDate (*date dimanche 6 janvier 2019 à 00:00:00*)
set theNSDate to its makeNSDateFrom:theDate
log (theNSDate's |description|() as text) (*2019-01-05 23:00:00 +0000*)
It seems that I forgot the correct syntax to encapsulate code here.
Yvan KOENIG running High Sierra 10.13.6 in French (VALLAURIS, France) jeudi 25 juillet 2019 18:54:22
Although there’s no stringWithString: or arrayWithArray: style method for converting dates, as long as you’re running 10.11 or later, you can use this:
set theDate to current application's NSDate's dateWithTimeInterval:0 sinceDate:ASOrNSDate
Just to be sure, are you speaking of the character whose ID is 8216 or the one whose ID is 8217?
I ask because Apple doesn’t use your naming.
character ID 8216 is named LEFT SINGLE QUOTATION MARK
character ID 8217 is named RIGHT SINGLE QUOTATION MARK
Yvan KOENIG running High Sierra 10.13.6 in French (VALLAURIS, France) vendredi 26 juillet 2019 10:37:07
use AppleScript version "2.4"
use framework "Foundation"
use scripting additions
set theDate to ((current date) - 1 * days)
set dateFormat to current application's NSDateFormatter's alloc()'s init()
dateFormat's setDateStyle:(current application's NSDateFormatterLongStyle)
dateFormat's setTimeStyle:(current application's NSDateFormatterMediumStyle)
dateFormat's setDoesRelativeDateFormatting:true
set theDay to (dateFormat's stringFromDate:theDate) as text
In fact, I found it here, but it didn’t show up when I searched SD Forums…