module Ecluse.Core.Version.Token (
VToken (..),
parseNumSeg,
numOr0,
isAsciiAlphaNum,
digitRuns,
classifyRun,
withinVersionLength,
) where
import Data.Char (isAsciiLower, isAsciiUpper, isDigit)
import Data.Text qualified as T
import Ecluse.Core.Text (readDecimalText)
data VToken = VNum Integer | VStr Text
deriving stock (VToken -> VToken -> Bool
(VToken -> VToken -> Bool)
-> (VToken -> VToken -> Bool) -> Eq VToken
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: VToken -> VToken -> Bool
== :: VToken -> VToken -> Bool
$c/= :: VToken -> VToken -> Bool
/= :: VToken -> VToken -> Bool
Eq, Int -> VToken -> ShowS
[VToken] -> ShowS
VToken -> String
(Int -> VToken -> ShowS)
-> (VToken -> String) -> ([VToken] -> ShowS) -> Show VToken
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> VToken -> ShowS
showsPrec :: Int -> VToken -> ShowS
$cshow :: VToken -> String
show :: VToken -> String
$cshowList :: [VToken] -> ShowS
showList :: [VToken] -> ShowS
Show, (forall x. VToken -> Rep VToken x)
-> (forall x. Rep VToken x -> VToken) -> Generic VToken
forall x. Rep VToken x -> VToken
forall x. VToken -> Rep VToken x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. VToken -> Rep VToken x
from :: forall x. VToken -> Rep VToken x
$cto :: forall x. Rep VToken x -> VToken
to :: forall x. Rep VToken x -> VToken
Generic)
instance NFData VToken
instance Ord VToken where
compare :: VToken -> VToken -> Ordering
compare (VNum Integer
m) (VNum Integer
n) = Integer -> Integer -> Ordering
forall a. Ord a => a -> a -> Ordering
compare Integer
m Integer
n
compare (VStr Text
s) (VStr Text
t) = Text -> Text -> Ordering
forall a. Ord a => a -> a -> Ordering
compare Text
s Text
t
compare (VNum Integer
_) (VStr Text
_) = Ordering
GT
compare (VStr Text
_) (VNum Integer
_) = Ordering
LT
maxVersionLength :: Int
maxVersionLength :: Int
maxVersionLength = Int
1024
withinVersionLength :: Text -> Bool
withinVersionLength :: Text -> Bool
withinVersionLength Text
raw = Text -> Int -> Ordering
T.compareLength Text
raw Int
maxVersionLength Ordering -> Ordering -> Bool
forall a. Eq a => a -> a -> Bool
/= Ordering
GT
parseNumSeg :: Text -> Maybe Integer
parseNumSeg :: Text -> Maybe Integer
parseNumSeg = Text -> Maybe Integer
forall a. Integral a => Text -> Maybe a
readDecimalText
numOr0 :: Text -> Integer
numOr0 :: Text -> Integer
numOr0 = Integer -> Maybe Integer -> Integer
forall a. a -> Maybe a -> a
fromMaybe Integer
0 (Maybe Integer -> Integer)
-> (Text -> Maybe Integer) -> Text -> Integer
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Text -> Maybe Integer
forall a. Integral a => Text -> Maybe a
readDecimalText
isAsciiAlphaNum :: Char -> Bool
isAsciiAlphaNum :: Char -> Bool
isAsciiAlphaNum Char
c = Char -> Bool
isAsciiUpper Char
c Bool -> Bool -> Bool
|| Char -> Bool
isAsciiLower Char
c Bool -> Bool -> Bool
|| Char -> Bool
isDigit Char
c
digitRuns :: Text -> [Text]
digitRuns :: Text -> [Text]
digitRuns = (Char -> Char -> Bool) -> Text -> [Text]
T.groupBy (\Char
c1 Char
c2 -> Char -> Bool
isDigit Char
c1 Bool -> Bool -> Bool
forall a. Eq a => a -> a -> Bool
== Char -> Bool
isDigit Char
c2)
classifyRun :: Text -> VToken
classifyRun :: Text -> VToken
classifyRun Text
run = if (Char -> Bool) -> Text -> Bool
T.all Char -> Bool
isDigit Text
run then Integer -> VToken
VNum (Text -> Integer
numOr0 Text
run) else Text -> VToken
VStr Text
run