Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement unix time and rfc3339 parsing #23

Merged
merged 3 commits into from
Nov 2, 2023

Conversation

colega
Copy link
Contributor

@colega colega commented Oct 31, 2023

This implements time functions toUnixTimestamp that calculates a unix timestamp of a date/time, and parseRFC3339 that does some limited parsing of RFC3339 timestamps.

Signed-off-by: Oleg Zaytsev <[email protected]>
Signed-off-by: Oleg Zaytsev <[email protected]>
@colega colega marked this pull request as ready for review October 31, 2023 12:53
Comment on lines +182 to +184
date + time + {
toUnixTimestamp():: $.toUnixTimestamp(self.year, self.month, self.day, self.hour, self.minute, self.second),
},
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This isn't the most functional approach, but it's easy to use. I'm happy to listen for your suggestions.

Comment on lines +161 to +173
// Sub-second precision isn't implemented yet, warn the user about that instead of returning wrong results.
assert !stringContains(input, '.') : 'the provided RFC3339 input "%s" has a dot, most likely representing a sub-second precision, but this function does not support that' % input;

// We don't support timezones, so string should end with 'Z' or 'z'.
assert std.endsWith(input, 'Z') || std.endsWith(input, 'z') : 'the provided RFC3339 "%s" should end with "Z" or "z". This implementation does not currently support timezones' % input;

// RFC3339 can separate date and time using 'T', 't' or ' '.
// Find out which one it is and use it.
local sep =
if stringContains(input, 'T') then 'T'
else if stringContains(input, 't') then 't'
else if stringContains(input, ' ') then ' '
else error 'the provided RFC3339 input "%s" should contain either a "T", or a "t" or space " " as a separator for date and time parts' % input;
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Duologic as you asked in grafana/jsonnet-libs#1095, I added support for lowercase t/z and also for space separator.

Comment on lines +105 to +112
// isNumeric checks that the input is a non-empty string containing only digit characters.
local isNumeric(input) =
assert std.type(input) == 'string' : 'isNumeric() only operates on string inputs, got %s' % std.type(input);
std.foldl(
function(acc, char) acc && std.codepoint('0') <= std.codepoint(char) && std.codepoint(char) <= std.codepoint('9'),
std.stringChars(input),
std.length(input) > 0,
),
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jdbaldry I borrowed the implementation from your comment here :)

Comment on lines +89 to +103
'#toUnixTimestamp': d.fn(
|||
`toUnixTimestamp` calculates the unix timestamp of a given date.
|||,
[
d.arg('year', d.T.number),
d.arg('month', d.T.number),
d.arg('day', d.T.number),
d.arg('hour', d.T.number),
d.arg('minute', d.T.number),
d.arg('second', d.T.number),
],
),
toUnixTimestamp(year, month, day, hour, minute, second)::
sumYearsSeconds(year) + sumMonthsSeconds(year, month) + sumDaysSeconds(day) + hour * 3600 + minute * 60 + second,
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This was already in github.com/grafana/jsonnet-libs/date, now I'm bringing here as it's useful once we've parsed the RFC3339.

Signed-off-by: Oleg Zaytsev <[email protected]>
Copy link

@malcolmholmes malcolmholmes left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks great to me, very thorough.

```

`parseRFC3339` parses an RFC3339-formatted date & time string into an object containing the 'year', 'month', 'day', 'hour', 'minute' and 'second fields.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would be useful to have an example of an RFC3339 date/time for those of us that know the format but not the RFC number.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, followed up in #24

@jdbaldry jdbaldry merged commit 1aec7d4 into jsonnet-libs:master Nov 2, 2023
2 checks passed
@colega colega deleted the unix-time-and-parse-rfc3339 branch November 2, 2023 10:29
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants