packages feed

ascii-superset-1.2.3.0: test/Main.hs

module Main (main) where

import Test.Hspec

import ASCII.Case (Case (..))
import ASCII.CaseRefinement (ASCII'lower, ASCII'upper, asciiCaseUnsafe)
import ASCII.Char (Char (..))
import ASCII.Refinement (ASCII, asciiUnsafe)

import qualified ASCII.Case as Case
import qualified ASCII.Caseless as CC
import qualified ASCII.CaseRefinement as CaseRefinement
import qualified ASCII.Char as ASCII
import qualified ASCII.Lift as Lift
import qualified ASCII.Refinement as Refinement
import qualified ASCII.Superset as Superset

import qualified Data.Foldable as Foldable

import Data.Function ((&))
import Data.Text (Text)
import Data.Word (Word8)
import Numeric.Natural (Natural)
import Prelude

import qualified Data.Char as Unicode

main :: IO ()
main = hspec $ do

    describe "lift" $ do

        it "letter" $ do
            let f x = Lift.lift x :: Word8
            f CapitalLetterA `shouldBe` 65

        it "to unicode" $ do
            let f = Lift.lift
            f CapitalLetterA `shouldBe` 'A'

        it "list to Text" $ do
            let f x = Lift.lift x :: Text
            f [CapitalLetterH, SmallLetterI, ExclamationMark] `shouldBe` "Hi!"

        it "list to ASCII Text" $ do
            let f x = Lift.lift x :: ASCII Text
            f [CapitalLetterH, SmallLetterI, ExclamationMark] `shouldBe` (asciiUnsafe "Hi!")

        it "ASCII Word8" $ do
            let f x = Lift.lift (x :: ASCII Word8) :: Word8
            f (asciiUnsafe 65) `shouldBe` 65

        it "can be id" $ do
            let f x = Lift.lift (x :: Unicode.Char) :: Unicode.Char
            f 'x' `shouldBe` 'x'

    describe "refinement" $ do

        it "validateChar" $ do
            let f x = Refinement.validateChar x :: Maybe (ASCII Int)
            f (-1) `shouldBe` Nothing
            f 65 `shouldBe` Just (asciiUnsafe 65)
            f 97 `shouldBe` Just (asciiUnsafe 97)
            f 128 `shouldBe` Nothing

        it "fromCharList" $ do
            let f x = Refinement.fromCharList x :: ASCII Text
            f [CapitalLetterH, SmallLetterI, ExclamationMark] `shouldBe` asciiUnsafe "Hi!"

        it "toCharList" $ do
            let f x = Refinement.toCharList
                          (Refinement.substituteString x :: ASCII Text)
            f "Piñata" `shouldBe` [CapitalLetterP, SmallLetterI, Substitute,
                                   SmallLetterA, SmallLetterT, SmallLetterA]

        it "substituteString" $ do
            let f x = Refinement.substituteString x :: ASCII Text
            f "Cristóbal" `shouldBe` asciiUnsafe "Crist\SUBbal"

        it "validateString" $ do
            let f x = Refinement.validateString x :: Maybe (ASCII Text)
            f "Hello" `shouldBe` Just (asciiUnsafe "Hello")
            f "Cristóbal" `shouldBe` Nothing

    describe "case refinement" $ do

        describe "validateChar" $ do

            it "lower" $ do
                let f x = CaseRefinement.validateChar x :: Maybe (ASCII'lower Int)
                f (-1) `shouldBe` Nothing
                f 65 `shouldBe` Nothing
                f 97 `shouldBe` Just (asciiCaseUnsafe 97)
                f 128 `shouldBe` Nothing

            it "upper" $ do
                let f x = CaseRefinement.validateChar x :: Maybe (ASCII'upper Int)
                f (-1) `shouldBe` Nothing
                f 65 `shouldBe` Just (asciiCaseUnsafe 65)
                f 97 `shouldBe` Nothing
                f 128 `shouldBe` Nothing

        describe "fromCaselessCharList" $ do

            it "lower" $ do
                let f x = CaseRefinement.fromCaselessCharList x :: ASCII'lower Text
                f [CC.LetterH, CC.LetterI, CC.ExclamationMark] `shouldBe` asciiCaseUnsafe "hi!"

            it "upper" $ do
                let f x = CaseRefinement.fromCaselessCharList x :: ASCII'upper Text
                f [CC.LetterH, CC.LetterI, CC.ExclamationMark] `shouldBe` asciiCaseUnsafe "HI!"

        describe "toCaselessCharList" $ do

            it "lower" $ do
                let f x = CaseRefinement.toCaselessCharList (x :: ASCII'lower Text)
                f (asciiCaseUnsafe "hi!") `shouldBe` [CC.LetterH, CC.LetterI, CC.ExclamationMark]

            it "upper" $ do
                let f x = CaseRefinement.toCaselessCharList (x :: ASCII'upper Text)
                f (asciiCaseUnsafe "HI!") `shouldBe` [CC.LetterH, CC.LetterI, CC.ExclamationMark]

        describe "substituteString" $ do

            it "lower" $ do
                let f x = CaseRefinement.substituteString x :: ASCII'lower Text
                f "Cób" `shouldBe` asciiCaseUnsafe "\SUB\SUBb"

            it "upper" $ do
                let f x = CaseRefinement.substituteString x :: ASCII'upper Text
                f "Cób" `shouldBe` asciiCaseUnsafe "C\SUB\SUB"

        describe "validateString" $ do

            it "lower" $ do
                let f x = CaseRefinement.validateString x :: Maybe (ASCII'lower Text)
                f "hello" `shouldBe` Just (asciiCaseUnsafe "hello")
                f "Hello" `shouldBe` Nothing

            it "upper" $ do
                let f x = CaseRefinement.validateString x :: Maybe (ASCII'upper Text)
                f "HELLO" `shouldBe` Just (asciiCaseUnsafe "HELLO")
                f "Hello" `shouldBe` Nothing

    describe "case conversion" $ do

        describe "toCaseChar" $ do
            let check :: forall a. Eq a => Superset.CharSuperset a => Expectation
                check =
                    ([UpperCase, LowerCase] & Foldable.all (\c ->
                        ASCII.allCharacters & Foldable.all (\x ->
                            Superset.toCaseChar c (Superset.fromChar @a x)
                                == Superset.fromChar @a (Case.toCase c x)
                    ))) `shouldBe` True
            it "ASCII.Char" $ check @ASCII.Char
            it "Unicode.Char" $ check @Unicode.Char
            it "Natural" $ check @Natural
            it "Int" $ check @Int
            it "Word8" $ check @Word8

        describe "toCaseString" $ do
            it "Text" $ do
                let x = "012 abc DEF ﬓ" :: Text
                Superset.toCaseString UpperCase x `shouldBe` "012 ABC DEF ﬓ"
                Superset.toCaseString LowerCase x `shouldBe` "012 abc def ﬓ"

        describe "refineStringToCase" $ do
            it "Text" $ do
                let x = asciiUnsafe "Hi!" :: ASCII Text
                CaseRefinement.refineStringToCase x `shouldBe` (asciiCaseUnsafe "HI!" :: ASCII'upper Text)
                CaseRefinement.refineStringToCase x `shouldBe` (asciiCaseUnsafe "hi!" :: ASCII'lower Text)