spark-server/internal/module/user/entity/spark_id.go

55 lines
1.2 KiB
Go

package entity
import (
"regexp"
)
const (
SparkIDMin = 8
SparkIDMax = 16
// sparkIDBodyLen is 13: int64 fits in 13 base36 digits (36^13 > 2^63).
sparkIDBodyLen = 13
sparkIDPrefix = 's'
)
var sparkIDRe = regexp.MustCompile(`^[a-zA-Z][a-zA-Z0-9_]{7,15}$`)
// ValidSparkID checks a new or updated handle. Existing rows may still be 6-32.
func ValidSparkID(id string) bool {
n := len(id)
return n >= SparkIDMin && n <= SparkIDMax && sparkIDRe.MatchString(id)
}
// DefaultSparkID maps a Snowflake uid to a unique 14-character handle.
// Format: 's' + 13-digit zero-padded base36(uid). Same uid always yields the same id;
// different uids never collide because the body is a fixed-width encoding of the integer.
func DefaultSparkID(userID int64) string {
if userID < 0 {
userID = -userID
}
body := strconv36(userID)
var b [1 + sparkIDBodyLen]byte
b[0] = sparkIDPrefix
pad := sparkIDBodyLen - len(body)
for i := 1; i <= pad; i++ {
b[i] = '0'
}
copy(b[1+pad:], body)
return string(b[:])
}
func strconv36(n int64) string {
const digits = "0123456789abcdefghijklmnopqrstuvwxyz"
if n == 0 {
return "0"
}
var buf [16]byte
i := len(buf)
for n > 0 {
i--
buf[i] = digits[n%36]
n /= 36
}
return string(buf[i:])
}