A parser of RFC5646 in Haskell.
- Lens-enabled
- instance of Read class
- use readMaby
- instance of Eq class
- case insensitive equality
- support for common convention formatting
- check if a tag is valid
- check if a tag is private
>>> read "de" :: LanguageTag Normal (Langtag {_language = ISO639 {_primary = "de", _extended = []}, _script = Nothing, _region = Nothing, _variant = [], _extension = [], _privateuse = []})
>>> read "DE" :: LanguageTag Normal (Langtag {_language = ISO639 {_primary = "DE", _extended = []}, _script = Nothing, _region = Nothing, _variant = [], _extension = [], _privateuse = []})
>>> let l1 =read "de" :: LanguageTag >>> let l2 =read "DE" :: LanguageTag >>> l1 == l2 True
>>> let c1 = read "zh-Hant" :: LanguageTag >>> c1 ^. (_Normal . language . primary) "zh" >>> c1 ^. (_Normal . language . extended) [] >>> c1 ^. (_Normal . script) Just "Hant" >>> c1 ^. (_Normal . region) Nothing >>> c1 ^. (_Normal . variant) [] >>> c1 ^. (_Normal . extension) [] >>> c1 ^. (_Normal . privateuse ) []
>>> let c2 = read "zh-cmn-Hans-CN" :: LanguageTag >>> c2 ^. (_Normal . language . primary) "zh" >>> c2 ^. (_Normal . language . extended) ["cmn"] >>> c2 ^. (_Normal . script) Just "Hans" >>> c2 ^. (_Normal . region) Just "CN" >>> c2 ^. (_Normal . variant) [] >>> c2 ^. (_Normal . extension) [] >>> c2 ^. (_Normal . privateuse) []
>>> let c3 = read "sl-rozaj-biske" :: LanguageTag >>> c3 ^. (_Normal . language . primary) "sl" >>> c3 ^. (_Normal . language . extended) [] >>> c3 ^. (_Normal . script) Nothing >>> c3 ^. (_Normal . region) Nothing >>> c3 ^. (_Normal . variant) ["rozaj","biske"] >>> c3 ^. (_Normal . extension) [] >>> c3 ^. (_Normal . privateuse) []
>>> let c4 = read "az-Arab-x-AZE-derbend" :: LanguageTag >>> c4 Normal (Langtag {_language = ISO639 {_primary = "az", _extended = []}, _script = Just "Arab", _region = Nothing, _variant = [], _extension = [], _privateuse = ["x","AZE","derbend"]}) >>> c4 ^. (_Normal . language . primary) "az" >>> c4 ^. (_Normal . language . extended) [] >>> c4 ^. (_Normal . script) Just "Arab" >>> c4 ^. (_Normal . region) Nothing >>> c4 ^. (_Normal . variant) [] >>> c4 ^. (_Normal . extension) [] >>> c4 ^. (_Normal . privateuse) ["x","AZE","derbend"]
>>> let c5 = read "qaa-Qaaa-QM-x-southern" :: LanguageTag >>> c5 & previews _Normal isPrivateOfPrimaryLanguageSubtag Just True >>> c5 & previews _Normal isPrivateOfScript Just True >>> c5 & previews _Normal isPrivateOfPrimaryLanguageSubtag Just True
When you know that you don't use a grandfathered tag nor a private tag at the beginning, use Langtag type insted of LanguageTag.
>>> let c2' = read "zh-cmn-Hans-CN" :: Langtag >>> c2' Langtag {_language = ISO639 {_primary = "zh", _extended = ["cmn"]}, _script = Just "Hans", _region = Just "CN", _variant = [], _extension = [], _privateuse = []} >>> c2' ^. (language . primary) "zh" >>> c2' ^. (language . extended) ["cmn"] >>> c2' ^. script Just "Hans" >>> c2' ^. region Just "CN"
The read function is not safe, so use readMaybe
>>> import Text.Read >>> readMaybe "qaa-Qaaa-QM-x-southern" :: Maybe LanguageTag Just (Normal (Langtag {_language = ISO639 {_primary = "qaa", _extended = []}, _script = Just "Qaaa", _region = Just "QM", _variant = [], _extension = [], _privateuse = ["x","southern"]}))
>>> readMaybe "abcdefg" :: Maybe LanguageTag Nothing
>>> eitherValid "a-b-c" Left "parse error : a-b-c"
>>> isValid $ read "xxx-xxxxx" True >>> isValid $ read "xxx-xxxxx-xxxxx" False
>>> isValid $ read "xxx-a-xxxxx-b-xxxxx" True >>> isValid $ read "xxx-a-xxxxx-a-xxxxx" False