on master help sign in
Add decodeUtf8' for lazy Text.
commitca0c2059070362f6666f5bd529d42f216b4f9d18 authorBryan O'Sullivan <bos@serpentine.com> dateTue 15 Mar 2011, 20:42 (16 years ago) parent3b0634b
1 file changed+28−3
Data/Text/Lazy/Encoding.hs+28−3
Data/Text/Lazy/Encoding.hs+28−3
@@ -25,6 +25,10 @@ module Data.Text.Lazy.Encoding
2525 , decodeUtf16BE
2626 , decodeUtf32LE
2727 , decodeUtf32BE
28+
29+ -- ** Catchable failure
30+ , decodeUtf8'
31+
2832 -- ** Controllable error handling
2933 , decodeUtf8With
3034 , decodeUtf16LEWith
@@ -40,9 +44,11 @@ module Data.Text.Lazy.Encoding
4044 , encodeUtf32BE
4145 ) where
4246
47+import Control.Exception (evaluate, try)
4348import Data.Bits ((.&.))
44−import Data.Text.Encoding.Error (OnDecodeError, strictDecode)
49+import Data.Text.Encoding.Error (OnDecodeError, UnicodeException, strictDecode)
4550import Data.Text.Lazy.Internal (Text(..), chunk, empty, foldrChunks)
51+import System.IO.Unsafe (unsafePerformIO)
4652import qualified Data.ByteString as S
4753import qualified Data.ByteString.Lazy as B
4854import qualified Data.ByteString.Lazy.Internal as B
@@ -108,10 +114,12 @@ decodeUtf8With onErr bs0 = fast bs0
108114 desc = "Data.Text.Lazy.Encoding.decodeUtf8With: Invalid UTF-8 stream"
109115{-# INLINE[0] decodeUtf8With #-}
110116
111−-- | Decode a 'ByteString' containing UTF-8 encoded text.
117+-- | Decode a 'ByteString' containing UTF-8 encoded text that is known
118+-- to be valid.
112119--
113120-- If the input contains any invalid UTF-8 data, an exception will be
114−-- thrown. For more control over the handling of invalid data, use
121+-- thrown that cannot be caught in pure code. For more control over
122+-- the handling of invalid data, use 'decodeUtf8'' or
115123-- 'decodeUtf8With'.
116124decodeUtf8 :: B.ByteString -> Text
117125decodeUtf8 = decodeUtf8With strictDecode
@@ -121,6 +129,23 @@ decodeUtf8 = decodeUtf8With strictDecode
121129{- RULES "LAZY STREAM stream/decodeUtf8' fusion" [1]
122130 forall bs. F.stream (decodeUtf8' bs) = E.streamUtf8 strictDecode bs #-}
123131
132+-- | Decode a 'ByteString' containing UTF-8 encoded text..
133+--
134+-- If the input contains any invalid UTF-8 data, the relevant
135+-- exception will be returned, otherwise the decoded text.
136+--
137+-- /Note/: this function is /not/ lazy, as it must decode its entire
138+-- input before it can return a result. If you need lazy (streaming)
139+-- decoding, use 'decodeUtf8With' in lenient mode.
140+decodeUtf8' :: B.ByteString -> Either UnicodeException Text
141+decodeUtf8' bs = unsafePerformIO $ do
142+ let t = decodeUtf8 bs
143+ try (evaluate (rnf t `seq` t))
144+ where
145+ rnf Empty = ()
146+ rnf (Chunk _ ts) = rnf ts
147+{-# INLINE decodeUtf8' #-}
148+
124149encodeUtf8 :: Text -> B.ByteString
125150encodeUtf8 (Chunk c cs) = B.Chunk (TE.encodeUtf8 c) (encodeUtf8 cs)
126151encodeUtf8 Empty = B.Empty