The SDK reaches internal/datetime through settings validation, and that package had only a cgo strftime implementation, so statically linked Tentacle packages could not build. Split the locale-aware cgo formatter into its own file and add a C-locale fallback for builds without cgo. The reader itself still uses the cgo implementation. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
81 lines
1.8 KiB
Go
81 lines
1.8 KiB
Go
// Copyright (c) 2026 Storm Dragon
|
|
// Authors: Storm Dragon, Angus Kola
|
|
// SPDX-License-Identifier: GPL-3.0-or-later
|
|
|
|
//go:build !cgo
|
|
|
|
package datetime
|
|
|
|
import (
|
|
"strconv"
|
|
"strings"
|
|
"time"
|
|
)
|
|
|
|
// format is a C-locale strftime subset for builds without cgo, such as the
|
|
// statically linked Tentacle packages that only validate settings. The reader
|
|
// itself is built with cgo and uses the locale-aware implementation.
|
|
func format(now time.Time, spec string) string {
|
|
var out strings.Builder
|
|
for index := 0; index < len(spec); index++ {
|
|
if spec[index] != '%' || index+1 == len(spec) {
|
|
out.WriteByte(spec[index])
|
|
continue
|
|
}
|
|
index++
|
|
pad := true
|
|
if spec[index] == '-' && index+1 < len(spec) {
|
|
pad = false
|
|
index++
|
|
}
|
|
two := func(value int) string {
|
|
if pad && value < 10 {
|
|
return "0" + strconv.Itoa(value)
|
|
}
|
|
return strconv.Itoa(value)
|
|
}
|
|
switch spec[index] {
|
|
case 'H':
|
|
out.WriteString(two(now.Hour()))
|
|
case 'I':
|
|
hour := now.Hour() % 12
|
|
if hour == 0 {
|
|
hour = 12
|
|
}
|
|
out.WriteString(two(hour))
|
|
case 'M':
|
|
out.WriteString(two(now.Minute()))
|
|
case 'S':
|
|
out.WriteString(two(now.Second()))
|
|
case 'p':
|
|
out.WriteString(now.Format("PM"))
|
|
case 'X':
|
|
out.WriteString(now.Format("15:04:05"))
|
|
case 'x':
|
|
out.WriteString(now.Format("01/02/06"))
|
|
case 'd':
|
|
out.WriteString(two(now.Day()))
|
|
case 'm':
|
|
out.WriteString(two(int(now.Month())))
|
|
case 'Y':
|
|
out.WriteString(strconv.Itoa(now.Year()))
|
|
case 'y':
|
|
out.WriteString(now.Format("06"))
|
|
case 'A':
|
|
out.WriteString(now.Weekday().String())
|
|
case 'a':
|
|
out.WriteString(now.Weekday().String()[:3])
|
|
case 'B':
|
|
out.WriteString(now.Month().String())
|
|
case 'b':
|
|
out.WriteString(now.Month().String()[:3])
|
|
case '%':
|
|
out.WriteByte('%')
|
|
default:
|
|
out.WriteByte('%')
|
|
out.WriteByte(spec[index])
|
|
}
|
|
}
|
|
return out.String()
|
|
}
|