module Text.AnimalCase
( toCamelCase
, toSnakeCase
, toCamelCaseS
, toSnakeCaseS
, toCamelCaseL
, toSnakeCaseL
, toCamelCaseB8
, toSnakeCaseB8
) where
import Control.Arrow (first)
import Data.Char (isUpper)
import Data.Monoid ((<>))
import Data.Text.Lazy.Encoding (decodeLatin1, encodeUtf8)
import qualified Data.ByteString.Char8 as B8
import qualified Data.ByteString.Lazy as BL
import qualified Data.Text as T
import qualified Data.Text.Lazy as TL
useLazy :: (TL.Text -> TL.Text) -> T.Text -> T.Text
useLazy f = TL.toStrict . f . TL.fromStrict
useLazyS :: (TL.Text -> TL.Text) -> String -> String
useLazyS f = TL.unpack . f . TL.pack
useLazyB8 :: (TL.Text -> TL.Text) -> B8.ByteString -> B8.ByteString
useLazyB8 f = BL.toStrict . encodeUtf8 . f . decodeLatin1 . BL.fromStrict
onFirstLetter :: (Char -> TL.Text) -> TL.Text -> TL.Text
onFirstLetter f = maybe "" (uncurry (<>) . first f) . TL.uncons
toCamelCase :: T.Text -> T.Text
toCamelCase = useLazy toCamelCaseL
toCamelCaseL :: TL.Text -> TL.Text
toCamelCaseL = TL.concat . map capitalizeWord . TL.splitOn "_"
where capitalizeWord = onFirstLetter (TL.toUpper . TL.singleton)
toCamelCaseS :: String -> String
toCamelCaseS = useLazyS toCamelCaseL
toCamelCaseB8 :: B8.ByteString -> B8.ByteString
toCamelCaseB8 = useLazyB8 toCamelCaseL
toSnakeCase :: T.Text -> T.Text
toSnakeCase = useLazy toSnakeCaseL
toSnakeCaseL :: TL.Text -> TL.Text
toSnakeCaseL = TL.concatMap f
where f c
| isUpper c = "_" <> TL.toLower (TL.singleton c)
| otherwise = TL.singleton c
toSnakeCaseS :: String -> String
toSnakeCaseS = useLazyS toSnakeCaseL
toSnakeCaseB8 :: B8.ByteString -> B8.ByteString
toSnakeCaseB8 = useLazyB8 toSnakeCaseL