]> gitweb @ CieloNegro.org - Lucu.git/commitdiff
Parser and co-parser for Data.URI.Scheme
authorPHO <pho@cielonegro.org>
Thu, 12 Jan 2012 22:46:58 +0000 (07:46 +0900)
committerPHO <pho@cielonegro.org>
Thu, 12 Jan 2012 22:46:58 +0000 (07:46 +0900)
Ditz-issue: c80e79a2585ac20cc5ed677d70b6983a2842a81d

Data/URI.hs
Data/URI/Internal.hs [new file with mode: 0644]
Data/URI/Internal/Scheme.hs
Lucu.cabal

index 11618bd5ad028a232e243f103d3bf78f372a3f80..c55a55f8f1df3dd718e2f84d0d5c0a8c7a98d785 100644 (file)
@@ -1,7 +1,6 @@
 -- |FIXME
 module Data.URI
     ( Scheme
-    , unsafeCreateScheme
     )
     where
 import Data.URI.Internal.Scheme
diff --git a/Data/URI/Internal.hs b/Data/URI/Internal.hs
new file mode 100644 (file)
index 0000000..ffb8a7b
--- /dev/null
@@ -0,0 +1,37 @@
+{-# LANGUAGE
+    UnicodeSyntax
+  #-}
+module Data.URI.Internal
+    ( finishOff
+    , parseAttempt
+    , parseAttempt'
+    )
+    where
+import Control.Applicative
+import Control.Exception.Base
+import Control.Monad.Unicode
+import Data.Ascii (Ascii)
+import qualified Data.Ascii as A
+import Data.Attempt
+import Data.Attoparsec.Char8
+import Data.ByteString (ByteString)
+import Prelude.Unicode
+
+finishOff ∷ Parser α → Parser α
+{-# INLINE finishOff #-}
+finishOff = ((endOfInput *>) ∘ return =≪)
+
+parseAttempt ∷ Exception e
+             ⇒ (String → e)
+             → Parser α
+             → ByteString
+             → Attempt α
+{-# INLINEABLE parseAttempt #-}
+parseAttempt f p bs
+    = case parseOnly (finishOff p) bs of
+        Right α → Success α
+        Left  e → Failure $ f e
+
+parseAttempt' ∷ Parser α → Ascii → Attempt α
+{-# INLINE parseAttempt' #-}
+parseAttempt' = (∘ A.toByteString) ∘ parseAttempt StringException
index d77fdb5f184ea333d1aab8049f64ea56c37fa985..2e3ba24efa7ac59a9e2c999910e7275f5713aaf1 100644 (file)
@@ -1,19 +1,30 @@
 {-# LANGUAGE
     DeriveDataTypeable
+  , FlexibleInstances
   , GeneralizedNewtypeDeriving
+  , MultiParamTypeClasses
   , StandaloneDeriving
+  , TemplateHaskell
+  , TypeSynonymInstances
   , UnicodeSyntax
   #-}
 module Data.URI.Internal.Scheme
     ( Scheme
-    , unsafeCreateScheme
     )
     where
 import Data.Ascii (CIAscii)
+import qualified Data.Ascii as A
+import Data.Attoparsec.Char8
+import qualified Data.ByteString.Char8 as BS
 import Data.CaseInsensitive
+import Data.Convertible.Base
+import Data.Default
 import Data.Hashable
 import Data.String
+import Data.URI.Internal
 import Data.Typeable
+import Prelude hiding (takeWhile)
+import Prelude.Unicode
 
 -- |'Scheme' names consist of a non-empty sequence of characters
 -- beginning with a letter and followed by any combination of letters,
@@ -27,14 +38,37 @@ newtype Scheme = Scheme CIAscii
              , Show
              , Typeable
              )
--- scheme = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." )
 
 -- |'isString' is a fast but unsafe way to create 'Scheme' such that
 -- no validation on the string is performed.
 deriving instance IsString Scheme
 
--- |Converts a 'CIAscii' to 'Scheme' without any validation on the
--- string.
-unsafeCreateScheme ∷ CIAscii → Scheme
-{-# INLINE CONLIKE unsafeCreateScheme #-}
-unsafeCreateScheme = Scheme
+instance Default (Parser Scheme) where
+    {-# INLINEABLE def #-}
+    def = do x  ← satisfy first
+             xs ← takeWhile nonFirst
+             return ∘ fromBS $ x `BS.cons` xs
+          <?>
+          "scheme"
+        where
+          {-# INLINE first #-}
+          first = isAlpha_ascii
+          {-# INLINE nonFirst #-}
+          nonFirst c
+              = isAlpha_ascii c ∨
+                c ≡ '+'         ∨
+                c ≡ '-'         ∨
+                c ≡ '.'
+          {-# INLINE fromBS #-}
+          fromBS = Scheme ∘ A.toCIAscii ∘ A.unsafeFromByteString
+
+instance ConvertSuccess Scheme CIAscii where
+    {-# INLINE convertSuccess #-}
+    convertSuccess (Scheme s) = s
+
+instance ConvertAttempt CIAscii Scheme where
+    {-# INLINE convertAttempt #-}
+    convertAttempt = parseAttempt' def ∘ A.fromCIAscii
+
+deriveAttempts [ ([t| Scheme |], [t| CIAscii |])
+               ]
index cff6ae84a9cc42b154f295ba325907ab6418014e..2778a2a2c0201d6df08198e056c9125f5bc083b1 100644 (file)
@@ -122,6 +122,7 @@ Library
         Network.HTTP.Lucu.Utils
 
     Other-Modules:
+        Data.URI.Internal
         Data.URI.Internal.Scheme
         Network.HTTP.Lucu.Abortion.Internal
         Network.HTTP.Lucu.Chunk