mirror of
https://github.com/vlang/v.git
synced 2025-09-13 14:32:26 +03:00
breaking,time: rewrite parse_rfc3339/1 to improve performance, reject partial timestamps, that miss date info like 22:47:08Z
(#22585)
This commit is contained in:
parent
de46d9d395
commit
c55a75f412
3 changed files with 357 additions and 67 deletions
|
@ -17,6 +17,14 @@ pub const allowed_basic_escape_chars = [`u`, `U`, `b`, `t`, `n`, `f`, `r`, `"`,
|
|||
// utf8_max is the largest inclusive value of the Unicodes scalar value ranges.
|
||||
const utf8_max = 0x10FFFF
|
||||
|
||||
fn toml_parse_time(s string) !time.Time {
|
||||
if s.len > 3 && s[2] == `:` {
|
||||
// complete the partial time, with an arbitrary date:
|
||||
return time.parse_rfc3339('0001-01-01T' + s)
|
||||
}
|
||||
return time.parse_rfc3339(s)!
|
||||
}
|
||||
|
||||
// Checker checks a tree of TOML `ast.Value`'s for common errors.
|
||||
pub struct Checker {
|
||||
pub:
|
||||
|
@ -318,8 +326,21 @@ fn (c &Checker) check_date_time(dt ast.DateTime) ! {
|
|||
col: dt.pos.col + split[0].len
|
||||
}
|
||||
})!
|
||||
// Use V's builtin functionality to validate the string
|
||||
time.parse_rfc3339(lit) or {
|
||||
// Simulate a time offset if it's missing then it can be checked. Already toml supports local time and rfc3339 don't.
|
||||
mut has_time_offset := false
|
||||
for ch in lit#[19..] {
|
||||
if ch in [u8(`-`), `+`, `Z`] {
|
||||
has_time_offset = true
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
mut lit_with_offset := lit
|
||||
if !has_time_offset {
|
||||
lit_with_offset += 'Z'
|
||||
}
|
||||
|
||||
toml_parse_time(lit_with_offset) or {
|
||||
return error(@MOD + '.' + @STRUCT + '.' + @FN +
|
||||
' "${lit}" is not a valid RFC 3339 Date-Time format string "${err}". In ...${c.excerpt(dt.pos)}...')
|
||||
}
|
||||
|
@ -352,8 +373,7 @@ fn (c &Checker) check_date(date ast.Date) ! {
|
|||
return error(@MOD + '.' + @STRUCT + '.' + @FN +
|
||||
' "${lit}" does not have a valid RFC 3339 day indication in ...${c.excerpt(date.pos)}...')
|
||||
}
|
||||
// Use V's builtin functionality to validate the string
|
||||
time.parse_rfc3339(lit) or {
|
||||
toml_parse_time(lit) or {
|
||||
return error(@MOD + '.' + @STRUCT + '.' + @FN +
|
||||
' "${lit}" is not a valid RFC 3339 Date format string "${err}". In ...${c.excerpt(date.pos)}...')
|
||||
}
|
||||
|
@ -380,8 +400,22 @@ fn (c &Checker) check_time(t ast.Time) ! {
|
|||
return error(@MOD + '.' + @STRUCT + '.' + @FN +
|
||||
' "${lit}" is not a valid RFC 3339 Time format string in ...${c.excerpt(t.pos)}...')
|
||||
}
|
||||
// Use V's builtin functionality to validate the time string
|
||||
time.parse_rfc3339(parts[0]) or {
|
||||
|
||||
// Simulate a time offset if it's missing then it can be checked. Already toml supports local time and rfc3339 don't.
|
||||
mut has_time_offset := false
|
||||
for ch in parts[0]#[8..] {
|
||||
if ch in [u8(`-`), `+`, `Z`] {
|
||||
has_time_offset = true
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
mut part_with_offset := parts[0]
|
||||
if !has_time_offset {
|
||||
part_with_offset += 'Z'
|
||||
}
|
||||
|
||||
toml_parse_time(part_with_offset) or {
|
||||
return error(@MOD + '.' + @STRUCT + '.' + @FN +
|
||||
' "${lit}" is not a valid RFC 3339 Time format string "${err}". In ...${c.excerpt(t.pos)}...')
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue