packages feed

aeson 2.2.1.0 → 2.3.1.0

raw patch · 36 files changed

Files

LICENSE view
@@ -1,4 +1,4 @@-Copyright (c) 2011, MailRank, Inc. 2014-2021 Aeson project contributors+Copyright (c) 2011, MailRank, Inc. 2014-2026 Aeson project contributors  All rights reserved. 
README.markdown view
@@ -14,14 +14,11 @@  Master [git repository](http://github.com/haskell/aeson): -* `git clone git://github.com/haskell/aeson.git`+* `git clone https://github.com/haskell/aeson.git`  See what's changed in recent (and upcoming) releases:  * https://github.com/haskell/aeson/blob/master/changelog.md--(You can create and contribute changes using either git or Mercurial.)-  # Authors 
aeson.cabal view
@@ -1,29 +1,32 @@+cabal-version:      2.2 name:               aeson-version:            2.2.1.0-license:            BSD3+version:            2.3.1.0+license:            BSD-3-Clause license-file:       LICENSE category:           Text, Web, JSON copyright:-  (c) 2011-2016 Bryan O'Sullivan-  (c) 2011 MailRank, Inc.-+  2014-2026 Aeson project contributors,+  2011-2016 Bryan O'Sullivan,+  2011 MailRank, Inc. author:             Bryan O'Sullivan <bos@serpentine.com>-maintainer:         Adam Bergmark <adam@bergmark.nl>-stability:          experimental+maintainer:+  Li-yao Xia <lysxia@gmail.com>,+  Core Libraries Committee+stability:          stable tested-with:-  GHC ==8.2.2-   || ==8.4.4-   || ==8.6.5+  GHC ==8.6.5    || ==8.8.4    || ==8.10.7    || ==9.0.2    || ==9.2.8-   || ==9.4.7-   || ==9.6.3-   || ==9.8.1+   || ==9.4.8+   || ==9.6.6+   || ==9.8.4+   || ==9.10.3+   || ==9.12.4+   || ==9.14.1  synopsis:           Fast JSON parsing and encoding-cabal-version:      1.12 homepage:           https://github.com/haskell/aeson bug-reports:        https://github.com/haskell/aeson/issues build-type:         Simple@@ -35,12 +38,12 @@   below.   .   (A note on naming: in Greek mythology, Aeson was the father of Jason.)-+extra-doc-files:+  README.markdown+  changelog.md extra-source-files:   *.yaml   benchmarks/json-data/*.json-  changelog.md-  README.markdown   tests/golden/*.expected   tests/JSONTestSuite/results/*.tok   tests/JSONTestSuite/results/*.txt@@ -84,8 +87,6 @@     Data.Aeson.Internal.TH     Data.Aeson.Internal.Unescape     Data.Aeson.Internal.UnescapeFromText-    Data.Aeson.Internal.Word8-    Data.Aeson.Internal.Word16     Data.Aeson.Parser.Time     Data.Aeson.Types.Class     Data.Aeson.Types.FromJSON@@ -95,51 +96,50 @@    -- GHC bundled libs   build-depends:-      base              >=4.10.0.0 && <5+    , base              >=4.12.0.0 && <5     , bytestring        >=0.10.8.2 && <0.13-    , containers        >=0.5.10.2 && <0.7-    , deepseq           >=1.4.3.0  && <1.6+    , containers        >=0.6.0.1  && <0.9+    , deepseq           >=1.4.4.0  && <1.6     , exceptions        >=0.10.4   && <0.11-    , ghc-prim          >=0.5.0.0  && <0.12-    , template-haskell  >=2.12.0.0 && <2.22+    , template-haskell  >=2.14.0.0 && <2.25     , text              >=1.2.3.0  && <1.3  || >=2.0 && <2.2-    , time              >=1.8.0.2  && <1.13+    , time              >=1.8.0.2  && <1.16    -- Compat   build-depends:-      generically  >=0.1   && <0.2     , time-compat  >=1.9.6 && <1.10 -  if !impl(ghc >=8.6)-    build-depends: contravariant >=1.4.1 && <1.6+  if !impl(ghc >=9.4)+    build-depends: generically >=0.1 && <0.2    if !impl(ghc >=9.0)     build-depends: integer-gmp    -- Other dependencies   build-depends:-      data-fix              >=0.3.2    && <0.4-    , dlist                 >=1.0      && <1.1-    , hashable              >=1.4.2.0  && <1.5-    , indexed-traversable   >=0.1.2    && <0.2-    , integer-conversion    >=0.1      && <0.2-    , integer-logarithms    >=1.0.3.1  && <1.1-    , network-uri           >=2.6.4.1  && <2.7-    , OneTuple              >=0.4.1.1  && <0.5-    , primitive             >=0.8.0.0  && <0.9-    , QuickCheck            >=2.14.3   && <2.15-    , scientific            >=0.3.7.0  && <0.4-    , semialign             >=1.3      && <1.4-    , strict                >=0.5      && <0.6-    , tagged                >=0.8.7    && <0.9-    , text-iso8601          >=0.1      && <0.2-    , text-short            >=0.1.5    && <0.2-    , th-abstraction        >=0.5.0.0  && <0.7-    , these                 >=1.2      && <1.3-    , unordered-containers  >=0.2.10.0 && <0.3-    , uuid-types            >=1.0.5    && <1.1-    , vector                >=0.13.0.0 && <0.14-    , witherable            >=0.4.2    && <0.5+    , character-ps          ^>=0.1+    , data-fix              ^>=0.3.2+    , dlist                 ^>=1.0+    , hashable              ^>=1.4.6.0  || ^>=1.5.0.0+    , indexed-traversable   ^>=0.1.2+    , integer-conversion    ^>=0.1+    , integer-logarithms    ^>=1.0.3.1+    , network-uri           ^>=2.6.4.1+    , OneTuple              ^>=0.4.1.1+    , primitive             ^>=0.8.0.0  || ^>=0.9.0.0+    , QuickCheck            ^>=2.14.3   || ^>=2.15    || ^>=2.16.0.0 || ^>=2.17.1.0 || ^>=2.18.0.0+    , scientific            ^>=0.3.7.0+    , semialign             ^>=1.3      || ^>=1.4+    , strict                ^>=0.5+    , tagged                ^>=0.8.7+    , text-iso8601          >=0.1.1 && < 0.3+    , text-short            ^>=0.1.5+    , th-abstraction        ^>=0.5.0.0  || ^>=0.6.0.0 || ^>=0.7.0.0+    , these                 ^>=1.2+    , unordered-containers  ^>=0.2.10.0+    , uuid-types            ^>=1.0.5+    , vector                ^>=0.13.0.0+    , witherable            ^>=0.4.2    || ^>=0.5    ghc-options:      -Wall @@ -179,6 +179,7 @@     Regression.Issue571     Regression.Issue687     Regression.Issue967+    Regression.Issue1138     RFC8785     SerializationFormatSpec     Types@@ -198,7 +199,7 @@     UnitTests.UTCTime    build-depends:-      aeson+    , aeson     , base     , base-compat     , base-orphans          >=0.5.3  && <0.10@@ -206,22 +207,19 @@     , bytestring     , containers     , data-fix-    , deepseq-    , Diff                  >=0.4    && <0.5+    , Diff                  >=0.4    && <0.6  || ^>=1.0.2     , directory     , dlist     , filepath     , generic-deriving      >=1.10   && <1.15     , generically-    , ghc-prim              >=0.2     , hashable     , indexed-traversable     , integer-logarithms    >=1      && <1.1     , network-uri     , OneTuple-    , primitive-    , QuickCheck            >=2.14.2 && <2.15-    , quickcheck-instances  >=0.3.29 && <0.4+    , QuickCheck+    , quickcheck-instances  >=0.3.29 && <0.5     , scientific     , strict     , tagged@@ -229,7 +227,6 @@     , tasty-golden     , tasty-hunit     , tasty-quickcheck-    , template-haskell     , text     , text-short     , these@@ -243,8 +240,8 @@     build-depends: integer-gmp    if impl(ghc >=9.2 && <9.7)-    build-depends: nothunks >=0.1.4 && <0.2+    build-depends: nothunks >=0.1.4 && <0.4  source-repository head   type:     git-  location: git://github.com/haskell/aeson.git+  location: https://github.com/haskell/aeson.git
changelog.md view
@@ -1,5 +1,45 @@ For the latest version of this document, please see [https://github.com/haskell/aeson/blob/master/changelog.md](https://github.com/haskell/aeson/blob/master/changelog.md). +### 2.3.1.0++* Add `FromJSONKey` instance for `Data.Fixed`.+* Add `ToJSON` and `FromJSON` instances for `Data.Complex`.+* Export `isEmptyArray` from `Data.Aeson.Types` module.+* Document that file decoding functions throw an exception when the file is missing.++### 2.3.0.0 - 2026-05-21++* Fix parsing of fractional numbers to reject exponents smaller than -1024.+  This breaking change affects `FromJSON` instances of `Fixed`, `DiffTime`, and `NominalDiffTime`,+  rejecting more inputs. Error messages for `Ratio` and integral types are also slightly different+  due to reusing the same bounding logic.+* Fix typo in error message: "~~Unespected~~ Unexpected control character while parsing string literal".+* Support nothunks 0.3.+* Unset executable permissions in some test files and remove a broken symlink.+* In `text-iso8601-0.2.0.0`:+    - Reject years of more than 15 digits.+    - Accept 24:00:00 time of day.++### 2.2.5.0++* Support `semialign-1.4`++### 2.2.4.0++* Check for control characters in text literals everywhere++### 2.2.3.0++* Support `hashable-1.4.6.0`.+* Fix an issue where `Hashable Key` wasn't newtype instance over underlying `Text`,+  so with `-ordered-keymap` there were correctness issues.+* Add instances for `Data.Semigroup.Sum`, `Product`, `Any`, `All`++### 2.2.2.0++* Support GHC-8.6.5...9.10.1+* Depend on `character-ps` instead of defining own Word8 pattern synonyms+ ### 2.2.1.0  * Add `Data.Aeson.RFC8785`, a JSON Canonicalization Scheme implementation@@ -14,7 +54,7 @@   One gotcha is that internal `Text` values (in `Key`s or `Value` `String`s)   will most likely retain the original input `Text` value (its underlying `Array`).   It shouldn't be an issue if the `Value` is then decoded to something else so these-  `Text` values disapper, but if not (e.g. `Object` keys survive)+  `Text` values disappear, but if not (e.g. `Object` keys survive)   then users might want to use `Data.Text.copy`.  ### 2.2.0.0@@ -34,7 +74,7 @@    In addition to `Maybe` (and `Option`) fields the `Data.Monoid.First` and `Data.Monoid.Last` are also omitted,   as well as the most newtype wrappers, when their wrap omittable type (e.g. newtypes in `Data.Monoid` and `Data.Semigroup`, `Identity`, `Const`, `Tagged`, `Compose`).-  Additionall "boring" types like `()` and `Proxy` are omitted as well.+  Additionally "boring" types like `()` and `Proxy` are omitted as well.   As the omitting is now uniform, type arguments are also omitted (also in `Generic1` derived instance).    Resolves issues:@@ -52,7 +92,7 @@ * Move `Data.Aeson.Parser` module into separate [`attoparsec-aeson`](https://hackage.haskell.org/package/attoparsec-aeson) package, as these parsers are not used by `aeson` itself anymore. * Use [`text-iso8601`](https://hackage.haskell.org/package/text-iso8601) package for parsing `time` types. These are slightly faster than previously used (copy of) `attoparsec-iso8601`.   Formats accepted is slightly changed:-  - The space between time and timezone offset (in `UTCTime` and `ZonedTime`) is disallowed. ISO8601 explictly forbidds it.+  - The space between time and timezone offset (in `UTCTime` and `ZonedTime`) is disallowed. ISO8601 explicitly forbids it.   - The timezone offsets can be in range -23:59..23:59. This is how Python, joda-time etc seems to do. (Previously the range was -12..+14)  * Remove internal `Data.Aeson.Internal` and `Data.Aeson.Internal.Time` modules. Everything from the former is exported elsewhere (`Data.Aeson.Types`), the latter was truly internal.@@ -215,7 +255,7 @@   parseJSON = gParseJSON defaultOptions { rejectUnknownFields = True } ``` -* `FromJSON` instance of `Ratio a` now parses numbers in addtion to+* `FromJSON` instance of `Ratio a` now parses numbers in addition to   standard `{numerator=..., denumerator=...}` encoding. Thanks to   Aleksey Khudyakov. 
src/Data/Aeson.hs view
@@ -199,6 +199,8 @@ -- -- This function parses immediately, but defers conversion.  See -- 'json' for details.+--+-- Throws an 'Exception' when the file is missing. decodeFileStrict :: (FromJSON a) => FilePath -> IO (Maybe a) decodeFileStrict = fmap decodeStrict . B.readFile @@ -226,12 +228,15 @@ -- If this fails due to incomplete or invalid input, 'Nothing' is -- returned. ----- Since @2.2.0.0@ an alias for 'decodeFileStrict'.+-- Throws an 'Exception' when the file is missing. --+-- Since @2.2.0.0@ an alias for 'decodeFileStrict'. decodeFileStrict' :: (FromJSON a) => FilePath -> IO (Maybe a) decodeFileStrict' = decodeFileStrict  -- | Like 'decodeFileStrict' but returns an error message when decoding fails.+--+-- Throws an 'Exception' when the file is missing. eitherDecodeFileStrict :: (FromJSON a) => FilePath -> IO (Either String a) eitherDecodeFileStrict =   fmap eitherDecodeStrict . B.readFile@@ -253,7 +258,9 @@  -- | Like 'decodeFileStrict'' but returns an error message when decoding fails. ----- Since @2.2.0.0@ an alias for 'eitherDecodeFileStrict''.+-- Throws an 'Exception' when the file is missing.+--+-- Since @2.2.0.0@ an alias for 'eitherDecodeFileStrict'. eitherDecodeFileStrict' :: (FromJSON a) => FilePath -> IO (Either String a) eitherDecodeFileStrict' = eitherDecodeFileStrict {-# INLINE eitherDecodeFileStrict' #-}@@ -557,5 +564,5 @@ -- -- For more information, see <https://en.wikipedia.org/wiki/ISO_8601 ISO 8601> -- <https://hackage.haskell.org/package/time time>,--- and <https://hackage.haskell.org/package/attoparsec-iso8601 attoparsec-iso8601>+-- and <https://hackage.haskell.org/package/text-iso8601 text-iso8601> -- (where the relevant parsers are defined).
src/Data/Aeson/Decoding.hs view
@@ -1,6 +1,6 @@ {-# LANGUAGE RankNTypes          #-} {-# LANGUAGE ScopedTypeVariables #-}--- | Convertion to and from @aeson@ 'A.Value'.+-- | Conversion to and from @aeson@ 'A.Value'. --  module Data.Aeson.Decoding (     decode,@@ -96,7 +96,7 @@ -- Decoding: strict text ------------------------------------------------------------------------------- --- | Efficiently deserialize a JSON value from a strict 'B.ByteString'.+-- | Efficiently deserialize a JSON value from a strict 'T.Text'. -- If this fails due to incomplete or invalid input, 'Nothing' is -- returned. --
src/Data/Aeson/Decoding/ByteString.hs view
@@ -18,12 +18,12 @@ import qualified Data.ByteString              as BS import qualified Data.ByteString.Unsafe       as BS.Unsafe import qualified Data.Scientific              as Sci+import qualified Data.Word8.Patterns          as W8  import           Data.Aeson.Decoding.Internal import           Data.Aeson.Decoding.Tokens import           Data.Aeson.Internal.Text     (unsafeDecodeASCII) import           Data.Aeson.Internal.Unescape (unescapeText)-import           Data.Aeson.Internal.Word8  -- | Lex (and parse) strict 'ByteString' into 'Tokens' stream. --@@ -42,17 +42,17 @@         -> ByteString         -- whole input, needed for number parsing         -> (ByteString -> k)  -- continuation         -> Tokens k String-    tokenCase W8_OPEN_CURLY   !bs !_   k      = TkRecordOpen (goR bs k)-    tokenCase W8_OPEN_SQUARE   bs  _   k      = TkArrayOpen (goA bs k)-    tokenCase W8_DOUBLE_QUOTE  bs  _   k      = scanStringLiteral (\t bs' -> TkText t (k bs')) tkErr bs-    tokenCase W8_MINUS         bs  _   k      = scanNumberLiteral (\n bs' -> TkNumber (negateNumber n) (k bs')) tkErr bs+    tokenCase W8.LEFT_CURLY   !bs !_   k      = TkRecordOpen (goR bs k)+    tokenCase W8.LEFT_SQUARE   bs  _   k      = TkArrayOpen (goA bs k)+    tokenCase W8.DOUBLE_QUOTE  bs  _   k      = scanStringLiteral (\t bs' -> TkText t (k bs')) tkErr bs+    tokenCase W8.HYPHEN        bs  _   k      = scanNumberLiteral (\n bs' -> TkNumber (negateNumber n) (k bs')) tkErr bs     tokenCase w                _   wbs k-        | W8_0 <= w, w <= W8_9                = scanNumberLiteral (\n bs' -> TkNumber n (k bs')) tkErr wbs-    tokenCase W8_n             bs  _   k+        | W8.DIGIT_0 <= w, w <= W8.DIGIT_9    = scanNumberLiteral (\n bs' -> TkNumber n (k bs')) tkErr wbs+    tokenCase W8.LOWER_N       bs  _   k         | Just bs1 <- stripPrefix "ull" 3 bs  = TkLit LitNull (k bs1)-    tokenCase W8_t             bs  _   k+    tokenCase W8.LOWER_T       bs  _   k         | Just bs1 <- stripPrefix "rue" 3 bs  = TkLit LitTrue (k bs1)-    tokenCase W8_f             bs  _   k+    tokenCase W8.LOWER_F       bs  _   k         | Just bs1 <- stripPrefix "alse" 4 bs = TkLit LitFalse (k bs1)     tokenCase _                _   wbs _      = tkErr $ "Unexpected " ++ showBeginning wbs ++ ", expecting JSON value" @@ -60,33 +60,33 @@     goA :: Parser TkArray k     goA (skipSpace -> bs) k = case BS.uncons bs of         Nothing         -> tkErrEOF "JSON value or ]"-        Just (W8_CLOSE_SQUARE, !bs1) -> TkArrayEnd (k bs1)+        Just (W8.RIGHT_SQUARE, !bs1) -> TkArrayEnd (k bs1)         Just (w,  !bs1) -> TkItem $ tokenCase w bs1 bs $ \bs2 -> goA1 bs2 k      goA1 :: Parser TkArray k     goA1 (skipSpace -> bs) k = case BS.uncons bs of         Nothing                      -> tkErrEOF ", or ]"-        Just (W8_CLOSE_SQUARE, !bs1) -> TkArrayEnd (k bs1)-        Just (W8_COMMA, !bs1)        -> TkItem $ goT bs1 $ \bs2 -> goA1 bs2 k+        Just (W8.RIGHT_SQUARE, !bs1) -> TkArrayEnd (k bs1)+        Just (W8.COMMA, !bs1)        -> TkItem $ goT bs1 $ \bs2 -> goA1 bs2 k         _                            -> tkErrBS bs ", or ]"      -- Record     goR :: Parser TkRecord k     goR (skipSpace -> bs) k = case BS.uncons bs of         Nothing                       -> tkErrEOF "record key literal or }"-        Just (W8_DOUBLE_QUOTE,  !bs1) -> goRK bs1 k           -- "-        Just (W8_CLOSE_CURLY, !bs1)   -> TkRecordEnd (k bs1)  -- }+        Just (W8.DOUBLE_QUOTE,  !bs1) -> goRK bs1 k           -- "+        Just (W8.RIGHT_CURLY, !bs1)   -> TkRecordEnd (k bs1)  -- }         Just _                        -> tkErrBS bs "record key literal or }"      -- after record pair, expecting ," or }     goR1 :: Parser TkRecord k     goR1 (skipSpace -> bs) k = case BS.uncons bs of         Nothing                           -> tkErr "Unexpected end-of-input, expecting , or }"-        Just (W8_COMMA, !bs1) -> case BS.uncons (skipSpace bs1) of+        Just (W8.COMMA, !bs1) -> case BS.uncons (skipSpace bs1) of             Nothing                      -> tkErrEOF "key literal"-            Just (W8_DOUBLE_QUOTE, !bs2) -> goRK bs2 k+            Just (W8.DOUBLE_QUOTE, !bs2) -> goRK bs2 k             Just _                       -> tkErrBS bs "key literal"-        Just (W8_CLOSE_CURLY, !bs1)       -> TkRecordEnd (k bs1)+        Just (W8.RIGHT_CURLY, !bs1)       -> TkRecordEnd (k bs1)         _                                 -> tkErr $ "Unexpected " ++ showBeginning bs ++ ", expecting , or }"      -- key of record (after double quote)@@ -97,7 +97,7 @@     goRK' :: Text -> Parser TkRecord k     goRK' t (skipSpace -> bs) k = case BS.uncons bs of         Nothing               -> tkErrEOF ":"-        Just (W8_COLON, !bs3) -> TkPair (Key.fromText t) $ goT bs3 $ \bs4 -> goR1 bs4 k+        Just (W8.COLON, !bs3) -> TkPair (Key.fromText t) $ goT bs3 $ \bs4 -> goR1 bs4 k         Just _                -> tkErrBS bs ":"  stripPrefix :: ByteString -> Int -> ByteString -> Maybe ByteString@@ -153,7 +153,9 @@             Right t -> ok t (BS.drop (n + 1) bs0)             Left e  -> err (show e)         Just (92, bs') -> goSlash (n + 1) bs'-        Just (_,  bs') -> goEsc (n + 1) bs'+        Just (w8, bs')+            | w8 < 0x20  -> errCC+            | otherwise  -> goEsc (n + 1) bs'      goSlash :: Int -> ByteString -> r     goSlash !n !bs = case BS.uncons bs of@@ -161,7 +163,7 @@         Just (_, bs') -> goEsc (n + 1) bs'      errEnd = err "Unexpected end-of-input while parsing string literal"-    errCC  = err "Unespected control character while parsing string literal"+    errCC  = err "Unexpected control character while parsing string literal"  ------------------------------------------------------------------------------- -- Number@@ -187,27 +189,27 @@     state_start !bs = case BS.uncons bs of         Nothing                      -> errEnd         Just (w8, bs')-            | W8_0 < w8, w8 <= W8_9  -> state_i1 1 bs'-            | W8_0 == w8             -> state_after0 bs'-            | otherwise              -> err $ "Unexpected " ++ show w8 ++ " while parsing number literal"+            | W8.DIGIT_0 < w8, w8 <= W8.DIGIT_9 -> state_i1 1 bs'+            | W8.DIGIT_0 == w8                  -> state_after0 bs'+            | otherwise                         -> err $ "Unexpected " ++ show w8 ++ " while parsing number literal"      state_after0 :: ByteString -> r     state_after0 !bs = case BS.uncons bs of         Nothing                         -> kont (NumInteger 0) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9    -> err "Number literal with leading zero"-            | W8_DOT == w8              -> go_dec 0 bs'-            | W8_e == w8 || W8_E == w8  -> go_sci 0 0 bs'-            | otherwise                 -> kont (NumInteger 0) bs+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9   -> err "Number literal with leading zero"+            | W8.PERIOD == w8                      -> go_dec 0 bs'+            | W8.LOWER_E == w8 || W8.UPPER_E == w8 -> go_sci 0 0 bs'+            | otherwise                            -> kont (NumInteger 0) bs      state_i1 :: Int -> ByteString -> r     state_i1 !n !bs = case BS.uncons bs of         Nothing                         -> kont (NumInteger int) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9    -> state_i1 (n + 1) bs'-            | W8_DOT == w8              -> go_dec int bs'-            | W8_e == w8 || W8_E == w8  -> go_sci int 0 bs'-            | otherwise                 -> kont (NumInteger int) bs+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9   -> state_i1 (n + 1) bs'+            | W8.PERIOD == w8                      -> go_dec int bs'+            | W8.LOWER_E == w8 || W8.UPPER_E == w8 -> go_sci int 0 bs'+            | otherwise                            -> kont (NumInteger int) bs       where         int = byteStringToInteger (BS.Unsafe.unsafeTake n bs0) @@ -215,16 +217,16 @@     go_dec !int !bs1 = case BS.uncons bs1 of         Nothing                       -> errEnd         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> state_dec 1 bs'-            | otherwise               -> err $ "Unexpected " ++ show w8 ++ " while parsing number literal"+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9 -> state_dec 1 bs'+            | otherwise                          -> err $ "Unexpected " ++ show w8 ++ " while parsing number literal"       where         state_dec :: Int -> ByteString -> r         state_dec !n !bs = case BS.uncons bs of             Nothing                         -> kont (NumDecimal dec) bs             Just (w8, bs')-                | W8_0 <= w8, w8 <= W8_9    -> state_dec (n + 1) bs'-                | W8_e == w8 || W8_E == w8  -> go_sci coef (negate n) bs'-                | otherwise                 -> kont (NumDecimal dec) bs+                | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9    -> state_dec (n + 1) bs'+                | W8.LOWER_E == w8 || W8.UPPER_E == w8  -> go_sci coef (negate n) bs'+                | otherwise                             -> kont (NumDecimal dec) bs           where             frac = byteStringToInteger (BS.Unsafe.unsafeTake n bs1)             coef = int * 10 ^ n + frac@@ -234,25 +236,25 @@     go_sci !coef !exp10 !bs2 = case BS.uncons bs2 of         Nothing                       -> errEnd         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_pos coef exp10 bs2 1 bs'-            | W8_PLUS == w8           -> case BS.uncons bs' of-                Nothing               -> errEnd+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9 -> go_sci_pos coef exp10 bs2 1 bs'+            | W8.PLUS == w8                      -> case BS.uncons bs' of+                Nothing                          -> errEnd                 Just (w8', bs'')-                    | W8_0 <= w8', w8' <= W8_9  -> go_sci_pos coef exp10 bs' 1 bs''-                    | otherwise       ->  errUnx w8'-            | W8_MINUS == w8          -> case BS.uncons bs' of+                    | W8.DIGIT_0 <= w8', w8' <= W8.DIGIT_9 -> go_sci_pos coef exp10 bs' 1 bs''+                    | otherwise                            -> errUnx w8'+            | W8.HYPHEN == w8         -> case BS.uncons bs' of                 Nothing               -> errEnd                 Just (w8', bs'')-                    | W8_0 <= w8', w8' <= W8_9  -> go_sci_neg coef exp10 bs' 1 bs''-                    | otherwise       ->  errUnx w8'-            | otherwise               -> errUnx w8+                    | W8.DIGIT_0 <= w8', w8' <= W8.DIGIT_9 -> go_sci_neg coef exp10 bs' 1 bs''+                    | otherwise                            -> errUnx w8'+            | otherwise                                    -> errUnx w8      go_sci_pos :: Integer -> Int -> ByteString -> Int -> ByteString -> r     go_sci_pos !coef !exp10 !bs2 !n !bs = case BS.uncons bs of         Nothing                       -> kont (NumScientific sci) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_pos coef exp10 bs2 (n + 1) bs'-            | otherwise               -> kont (NumScientific sci) bs+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9 -> go_sci_pos coef exp10 bs2 (n + 1) bs'+            | otherwise                          -> kont (NumScientific sci) bs       where         exp10' = fromInteger (byteStringToInteger (BS.Unsafe.unsafeTake n bs2))         sci = Sci.scientific coef (exp10 + exp10')@@ -261,7 +263,7 @@     go_sci_neg !coef !exp10 !bs2 !n !bs = case BS.uncons bs of         Nothing                       -> kont (NumScientific sci) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_neg coef exp10 bs2 (n + 1) bs'+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9  -> go_sci_neg coef exp10 bs2 (n + 1) bs'             | otherwise               -> kont (NumScientific sci) bs       where         exp10' = fromInteger (byteStringToInteger (BS.Unsafe.unsafeTake n bs2))
src/Data/Aeson/Decoding/ByteString/Lazy.hs view
@@ -18,12 +18,12 @@ import qualified Data.ByteString              as BS import qualified Data.ByteString.Lazy         as LBS import qualified Data.Scientific              as Sci+import qualified Data.Word8.Patterns          as W8  import           Data.Aeson.Decoding.Internal import           Data.Aeson.Decoding.Tokens import           Data.Aeson.Internal.Text     (unsafeDecodeASCII) import           Data.Aeson.Internal.Unescape (unescapeText)-import           Data.Aeson.Internal.Word8  -- | Lex (and parse) lazy 'ByteString' into 'Tokens' stream. --@@ -42,17 +42,17 @@         -> ByteString         -- whole input, needed for number parsing         -> (ByteString -> k)  -- continuation         -> Tokens k String-    tokenCase W8_OPEN_CURLY   !bs !_   k      = TkRecordOpen (goR bs k)-    tokenCase W8_OPEN_SQUARE   bs  _   k      = TkArrayOpen (goA bs k)-    tokenCase W8_DOUBLE_QUOTE  bs  _   k      = scanStringLiteral (\t bs' -> TkText t (k bs')) tkErr bs-    tokenCase W8_MINUS         bs  _   k      = scanNumberLiteral (\n bs' -> TkNumber (negateNumber n) (k bs')) tkErr bs+    tokenCase W8.LEFT_CURLY   !bs !_   k      = TkRecordOpen (goR bs k)+    tokenCase W8.LEFT_SQUARE   bs  _   k      = TkArrayOpen (goA bs k)+    tokenCase W8.DOUBLE_QUOTE  bs  _   k      = scanStringLiteral (\t bs' -> TkText t (k bs')) tkErr bs+    tokenCase W8.HYPHEN        bs  _   k      = scanNumberLiteral (\n bs' -> TkNumber (negateNumber n) (k bs')) tkErr bs     tokenCase w                _   wbs k-        | W8_0 <= w, w <= W8_9                = scanNumberLiteral (\n bs' -> TkNumber n (k bs')) tkErr wbs-    tokenCase W8_n             bs  _   k+        | W8.DIGIT_0 <= w, w <= W8.DIGIT_9    = scanNumberLiteral (\n bs' -> TkNumber n (k bs')) tkErr wbs+    tokenCase W8.LOWER_N       bs  _   k         | Just bs1 <- stripPrefix "ull" 3 bs  = TkLit LitNull (k bs1)-    tokenCase W8_t             bs  _   k+    tokenCase W8.LOWER_T       bs  _   k         | Just bs1 <- stripPrefix "rue" 3 bs  = TkLit LitTrue (k bs1)-    tokenCase W8_f             bs  _   k+    tokenCase W8.LOWER_F       bs  _   k         | Just bs1 <- stripPrefix "alse" 4 bs = TkLit LitFalse (k bs1)     tokenCase _                _   wbs _      = tkErr $ "Unexpected " ++ showBeginning wbs ++ ", expecting JSON value" @@ -60,33 +60,33 @@     goA :: Parser TkArray k     goA (skipSpace -> bs) k = case LBS.uncons bs of         Nothing         -> tkErrEOF "JSON value or ]"-        Just (W8_CLOSE_SQUARE, !bs1) -> TkArrayEnd (k bs1)+        Just (W8.RIGHT_SQUARE, !bs1) -> TkArrayEnd (k bs1)         Just (w,  !bs1) -> TkItem $ tokenCase w bs1 bs $ \bs2 -> goA1 bs2 k      goA1 :: Parser TkArray k     goA1 (skipSpace -> bs) k = case LBS.uncons bs of         Nothing                      -> tkErrEOF ", or ]"-        Just (W8_CLOSE_SQUARE, !bs1) -> TkArrayEnd (k bs1)-        Just (W8_COMMA, !bs1)        -> TkItem $ goT bs1 $ \bs2 -> goA1 bs2 k+        Just (W8.RIGHT_SQUARE, !bs1) -> TkArrayEnd (k bs1)+        Just (W8.COMMA, !bs1)        -> TkItem $ goT bs1 $ \bs2 -> goA1 bs2 k         _                            -> tkErrBS bs ", or ]"      -- Record     goR :: Parser TkRecord k     goR (skipSpace -> bs) k = case LBS.uncons bs of         Nothing                       -> tkErrEOF "record key literal or }"-        Just (W8_DOUBLE_QUOTE,  !bs1) -> goRK bs1 k           -- "-        Just (W8_CLOSE_CURLY, !bs1)   -> TkRecordEnd (k bs1)  -- }+        Just (W8.DOUBLE_QUOTE,  !bs1) -> goRK bs1 k           -- "+        Just (W8.RIGHT_CURLY, !bs1)   -> TkRecordEnd (k bs1)  -- }         Just _                        -> tkErrBS bs "record key literal or }"      -- after record pair, expecting ," or }     goR1 :: Parser TkRecord k     goR1 (skipSpace -> bs) k = case LBS.uncons bs of         Nothing                           -> tkErr "Unexpected end-of-input, expecting , or }"-        Just (W8_COMMA, !bs1) -> case LBS.uncons (skipSpace bs1) of+        Just (W8.COMMA, !bs1) -> case LBS.uncons (skipSpace bs1) of             Nothing                      -> tkErrEOF "key literal"-            Just (W8_DOUBLE_QUOTE, !bs2) -> goRK bs2 k+            Just (W8.DOUBLE_QUOTE, !bs2) -> goRK bs2 k             Just _                       -> tkErrBS bs "key literal"-        Just (W8_CLOSE_CURLY, !bs1)       -> TkRecordEnd (k bs1)+        Just (W8.RIGHT_CURLY, !bs1)       -> TkRecordEnd (k bs1)         _                                 -> tkErr $ "Unexpected " ++ showBeginning bs ++ ", expecting , or }"      -- key of record (after double quote)@@ -97,7 +97,7 @@     goRK' :: Text -> Parser TkRecord k     goRK' t (skipSpace -> bs) k = case LBS.uncons bs of         Nothing               -> tkErrEOF ":"-        Just (W8_COLON, !bs3) -> TkPair (Key.fromText t) $ goT bs3 $ \bs4 -> goR1 bs4 k+        Just (W8.COLON, !bs3) -> TkPair (Key.fromText t) $ goT bs3 $ \bs4 -> goR1 bs4 k         Just _                -> tkErrBS bs ":"  stripPrefix :: ByteString -> Int -> ByteString -> Maybe ByteString@@ -159,7 +159,9 @@             Right t -> ok t (lbsDrop (n + 1) bs0)             Left e  -> err (show e)         Just (92, bs') -> goSlash (n + 1) bs'-        Just (_,  bs') -> goEsc (n + 1) bs'+        Just (w8, bs')+            | w8 < 0x20  -> errCC+            | otherwise  -> goEsc (n + 1) bs'      goSlash :: Int -> ByteString -> r     goSlash !n !bs = case LBS.uncons bs of@@ -167,7 +169,7 @@         Just (_, bs') -> goEsc (n + 1) bs'      errEnd = err "Unexpected end-of-input while parsing string literal"-    errCC  = err "Unespected control character while parsing string literal"+    errCC  = err "Unexpected control character while parsing string literal"  ------------------------------------------------------------------------------- -- Number@@ -193,27 +195,27 @@     state_start !bs = case LBS.uncons bs of         Nothing                      -> errEnd         Just (w8, bs')-            | W8_0 < w8, w8 <= W8_9  -> state_i1 1 bs'-            | W8_0 == w8             -> state_after0 bs'+            | W8.DIGIT_0 < w8, w8 <= W8.DIGIT_9  -> state_i1 1 bs'+            | W8.DIGIT_0 == w8             -> state_after0 bs'             | otherwise              -> err $ "Unexpected " ++ show w8 ++ " while parsing number literal"      state_after0 :: ByteString -> r     state_after0 !bs = case LBS.uncons bs of         Nothing                         -> kont (NumInteger 0) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9    -> err "Number literal with leading zero"-            | W8_DOT == w8              -> go_dec 0 bs'-            | W8_e == w8 || W8_E == w8  -> go_sci 0 0 bs'-            | otherwise                 -> kont (NumInteger 0) bs+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9   -> err "Number literal with leading zero"+            | W8.PERIOD == w8                      -> go_dec 0 bs'+            | W8.LOWER_E == w8 || W8.UPPER_E == w8 -> go_sci 0 0 bs'+            | otherwise                            -> kont (NumInteger 0) bs      state_i1 :: Int -> ByteString -> r     state_i1 !n !bs = case LBS.uncons bs of         Nothing                         -> kont (NumInteger int) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9    -> state_i1 (n + 1) bs'-            | W8_DOT == w8              -> go_dec int bs'-            | W8_e == w8 || W8_E == w8  -> go_sci int 0 bs'-            | otherwise                 -> kont (NumInteger int) bs+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9   -> state_i1 (n + 1) bs'+            | W8.PERIOD == w8                      -> go_dec int bs'+            | W8.LOWER_E == w8 || W8.UPPER_E == w8 -> go_sci int 0 bs'+            | otherwise                            -> kont (NumInteger int) bs       where         int = byteStringToInteger (lbsTake n bs0) @@ -221,16 +223,16 @@     go_dec !int !bs1 = case LBS.uncons bs1 of         Nothing                       -> errEnd         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> state_dec 1 bs'-            | otherwise               -> err $ "Unexpected " ++ show w8 ++ " while parsing number literal"+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9 -> state_dec 1 bs'+            | otherwise                          -> err $ "Unexpected " ++ show w8 ++ " while parsing number literal"       where         state_dec :: Int -> ByteString -> r         state_dec !n !bs = case LBS.uncons bs of             Nothing                         -> kont (NumDecimal dec) bs             Just (w8, bs')-                | W8_0 <= w8, w8 <= W8_9    -> state_dec (n + 1) bs'-                | W8_e == w8 || W8_E == w8  -> go_sci coef (negate n) bs'-                | otherwise                 -> kont (NumDecimal dec) bs+                | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9   -> state_dec (n + 1) bs'+                | W8.LOWER_E == w8 || W8.UPPER_E == w8 -> go_sci coef (negate n) bs'+                | otherwise                            -> kont (NumDecimal dec) bs           where             frac = byteStringToInteger (lbsTake n bs1)             coef = int * 10 ^ n + frac@@ -240,16 +242,16 @@     go_sci !coef !exp10 !bs2 = case LBS.uncons bs2 of         Nothing                       -> errEnd         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_pos coef exp10 bs2 1 bs'-            | W8_PLUS == w8           -> case LBS.uncons bs' of+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9  -> go_sci_pos coef exp10 bs2 1 bs'+            | W8.PLUS == w8           -> case LBS.uncons bs' of                 Nothing               -> errEnd                 Just (w8', bs'')-                    | W8_0 <= w8', w8' <= W8_9  -> go_sci_pos coef exp10 bs' 1 bs''+                    | W8.DIGIT_0 <= w8', w8' <= W8.DIGIT_9  -> go_sci_pos coef exp10 bs' 1 bs''                     | otherwise       ->  errUnx w8'-            | W8_MINUS == w8          -> case LBS.uncons bs' of+            | W8.HYPHEN == w8         -> case LBS.uncons bs' of                 Nothing               -> errEnd                 Just (w8', bs'')-                    | W8_0 <= w8', w8' <= W8_9  -> go_sci_neg coef exp10 bs' 1 bs''+                    | W8.DIGIT_0 <= w8', w8' <= W8.DIGIT_9  -> go_sci_neg coef exp10 bs' 1 bs''                     | otherwise       ->  errUnx w8'             | otherwise               -> errUnx w8 @@ -257,7 +259,7 @@     go_sci_pos !coef !exp10 !bs2 !n !bs = case LBS.uncons bs of         Nothing                       -> kont (NumScientific sci) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_pos coef exp10 bs2 (n + 1) bs'+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9  -> go_sci_pos coef exp10 bs2 (n + 1) bs'             | otherwise               -> kont (NumScientific sci) bs       where         exp10' = fromInteger (byteStringToInteger (lbsTake n bs2))@@ -267,7 +269,7 @@     go_sci_neg !coef !exp10 !bs2 !n !bs = case LBS.uncons bs of         Nothing                       -> kont (NumScientific sci) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_neg coef exp10 bs2 (n + 1) bs'+            | W8.DIGIT_0 <= w8, w8 <= W8.DIGIT_9  -> go_sci_neg coef exp10 bs2 (n + 1) bs'             | otherwise               -> kont (NumScientific sci) bs       where         exp10' = fromInteger (byteStringToInteger (lbsTake n bs2))
src/Data/Aeson/Decoding/Conversion.hs view
@@ -87,7 +87,7 @@         -> (e -> r)         -> ([(Key, A.Value)] -> k -> r)         -> r-    -- here we don't stricly need bang on !v as KM is a Strict (in values) map.+    -- here we don't strictly need bang on !v as KM is a Strict (in values) map.     -- but we force the value sooner.     goR !acc (TkPair t toks) g f = convert toks g $ \ !v k -> goR ((t , v) : acc) k g f     goR !acc (TkRecordEnd k) _ f = f acc k
src/Data/Aeson/Decoding/Text.hs view
@@ -24,9 +24,9 @@ import           Data.Aeson.Internal.UnescapeFromText (unescapeFromText)  #if MIN_VERSION_text(2,0,0)-import           Data.Aeson.Internal.Word8+import qualified Data.Word8.Patterns as W #else-import           Data.Aeson.Internal.Word16+import qualified Data.Word16.Patterns as W #endif  #if MIN_VERSION_text(2,0,0)@@ -36,7 +36,7 @@ #endif  --- | Lex (and parse) strict 'ByteString' into 'Tokens' stream.+-- | Lex (and parse) strict 'Text' into 'Tokens' stream. -- -- @since 2.2.1.0 --@@ -53,51 +53,50 @@         -> Text               -- whole input, needed for number parsing         -> (Text -> k)        -- continuation         -> Tokens k String-    tokenCase W8_OPEN_CURLY   !bs !_   k      = TkRecordOpen (goR bs k)-    tokenCase W8_OPEN_SQUARE   bs  _   k      = TkArrayOpen (goA bs k)-    tokenCase W8_DOUBLE_QUOTE  bs  _   k      = scanStringLiteral (\t bs' -> TkText t (k bs')) tkErr bs-    tokenCase W8_MINUS         bs  _   k      = scanNumberLiteral (\n bs' -> TkNumber (negateNumber n) (k bs')) tkErr bs+    tokenCase W.LEFT_CURLY   !bs !_   k       = TkRecordOpen (goR bs k)+    tokenCase W.LEFT_SQUARE   bs  _   k       = TkArrayOpen (goA bs k)+    tokenCase W.DOUBLE_QUOTE  bs  _   k       = scanStringLiteral (\t bs' -> TkText t (k bs')) tkErr bs+    tokenCase W.HYPHEN        bs  _   k       = scanNumberLiteral (\n bs' -> TkNumber (negateNumber n) (k bs')) tkErr bs     tokenCase w                _   wbs k-        | W8_0 <= w, w <= W8_9                = scanNumberLiteral (\n bs' -> TkNumber n (k bs')) tkErr wbs-    tokenCase W8_n             bs  _   k+        | W.DIGIT_0 <= w, w <= W.DIGIT_9      = scanNumberLiteral (\n bs' -> TkNumber n (k bs')) tkErr wbs+    tokenCase W.LOWER_N       bs  _   k         | Just bs1 <- stripPrefix "ull" 3 bs  = TkLit LitNull (k bs1)-    tokenCase W8_t             bs  _   k+    tokenCase W.LOWER_T       bs  _   k         | Just bs1 <- stripPrefix "rue" 3 bs  = TkLit LitTrue (k bs1)-    tokenCase W8_f             bs  _   k+    tokenCase W.LOWER_F       bs  _   k         | Just bs1 <- stripPrefix "alse" 4 bs = TkLit LitFalse (k bs1)-    tokenCase _                _   wbs _      = tkErr $ "Unexpected " ++ showBeginning wbs ++ ", expecting JSON value"-+    tokenCase _          _   wbs _            = tkErr $ "Unexpected " ++ showBeginning wbs ++ ", expecting JSON value"     -- Array     goA :: Parser TkArray k     goA (skipSpace -> bs) k = case unconsPoint bs of         Nothing         -> tkErrEOF "JSON value or ]"-        Just (W8_CLOSE_SQUARE, !bs1) -> TkArrayEnd (k bs1)+        Just (W.RIGHT_SQUARE, !bs1) -> TkArrayEnd (k bs1)         Just (w,  !bs1) -> TkItem $ tokenCase w bs1 bs $ \bs2 -> goA1 bs2 k      goA1 :: Parser TkArray k     goA1 (skipSpace -> bs) k = case unconsPoint bs of         Nothing                      -> tkErrEOF ", or ]"-        Just (W8_CLOSE_SQUARE, !bs1) -> TkArrayEnd (k bs1)-        Just (W8_COMMA, !bs1)        -> TkItem $ goT bs1 $ \bs2 -> goA1 bs2 k+        Just (W.RIGHT_SQUARE, !bs1) -> TkArrayEnd (k bs1)+        Just (W.COMMA, !bs1)        -> TkItem $ goT bs1 $ \bs2 -> goA1 bs2 k         _                            -> tkErrBS bs ", or ]"      -- Record     goR :: Parser TkRecord k     goR (skipSpace -> bs) k = case unconsPoint bs of         Nothing                       -> tkErrEOF "record key literal or }"-        Just (W8_DOUBLE_QUOTE,  !bs1) -> goRK bs1 k           -- "-        Just (W8_CLOSE_CURLY, !bs1)   -> TkRecordEnd (k bs1)  -- }+        Just (W.DOUBLE_QUOTE,  !bs1) -> goRK bs1 k           -- "+        Just (W.RIGHT_CURLY, !bs1)   -> TkRecordEnd (k bs1)  -- }         Just _                        -> tkErrBS bs "record key literal or }"      -- after record pair, expecting ," or }     goR1 :: Parser TkRecord k     goR1 (skipSpace -> bs) k = case unconsPoint bs of         Nothing                           -> tkErr "Unexpected end-of-input, expecting , or }"-        Just (W8_COMMA, !bs1) -> case unconsPoint (skipSpace bs1) of+        Just (W.COMMA, !bs1) -> case unconsPoint (skipSpace bs1) of             Nothing                      -> tkErrEOF "key literal"-            Just (W8_DOUBLE_QUOTE, !bs2) -> goRK bs2 k+            Just (W.DOUBLE_QUOTE, !bs2) -> goRK bs2 k             Just _                       -> tkErrBS bs "key literal"-        Just (W8_CLOSE_CURLY, !bs1)       -> TkRecordEnd (k bs1)+        Just (W.RIGHT_CURLY, !bs1)       -> TkRecordEnd (k bs1)         _                                 -> tkErr $ "Unexpected " ++ showBeginning bs ++ ", expecting , or }"      -- key of record (after double quote)@@ -164,7 +163,9 @@             Right t -> ok t (unsafeDropPoints (n + 1) bs0)             Left e  -> err (show e)         Just (92, bs') -> goSlash (n + 1) bs'-        Just (_,  bs') -> goEsc (n + 1) bs'+        Just (w8, bs')+            | w8 < 0x20  -> errCC+            | otherwise  -> goEsc (n + 1) bs'      goSlash :: Int -> Text -> r     goSlash !n !bs = case unconsPoint bs of@@ -172,7 +173,7 @@         Just (_, bs') -> goEsc (n + 1) bs'      errEnd = err "Unexpected end-of-input while parsing string literal"-    errCC  = err "Unespected control character while parsing string literal"+    errCC  = err "Unexpected control character while parsing string literal"  ------------------------------------------------------------------------------- -- Number@@ -196,46 +197,46 @@ scanNumberLiteral kont err bs0 = state_start bs0 where     state_start :: Text -> r     state_start !bs = case unconsPoint bs of-        Nothing                      -> errEnd+        Nothing                                   -> errEnd         Just (w8, bs')-            | W8_0 < w8, w8 <= W8_9  -> state_i1 1 bs'-            | W8_0 == w8             -> state_after0 bs'-            | otherwise              -> errUnx w8+            | W.DIGIT_0 < w8, w8 <= W.DIGIT_9     -> state_i1 1 bs'+            | W.DIGIT_0 == w8                     -> state_after0 bs'+            | otherwise                           -> errUnx w8      state_after0 :: Text -> r     state_after0 !bs = case unconsPoint bs of-        Nothing                         -> kont (NumInteger 0) bs+        Nothing                                   -> kont (NumInteger 0) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9    -> err "Number literal with leading zero"-            | W8_DOT == w8              -> go_dec 0 bs'-            | W8_e == w8 || W8_E == w8  -> go_sci 0 0 bs'-            | otherwise                 -> kont (NumInteger 0) bs+            | W.DIGIT_0 <= w8, w8 <= W.DIGIT_9    -> err "Number literal with leading zero"+            | W.PERIOD == w8                      -> go_dec 0 bs'+            | W.LOWER_E == w8 || W.UPPER_E == w8  -> go_sci 0 0 bs'+            | otherwise                           -> kont (NumInteger 0) bs      state_i1 :: Int -> Text -> r     state_i1 !n !bs = case unconsPoint bs of-        Nothing                         -> kont (NumInteger int) bs+        Nothing                                   -> kont (NumInteger int) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9    -> state_i1 (n + 1) bs'-            | W8_DOT == w8              -> go_dec int bs'-            | W8_e == w8 || W8_E == w8  -> go_sci int 0 bs'-            | otherwise                 -> kont (NumInteger int) bs+            | W.DIGIT_0 <= w8, w8 <= W.DIGIT_9    -> state_i1 (n + 1) bs'+            | W.PERIOD == w8                      -> go_dec int bs'+            | W.LOWER_E == w8 || W.UPPER_E == w8  -> go_sci int 0 bs'+            | otherwise                           -> kont (NumInteger int) bs       where         int = textToInteger (unsafeTakePoints n bs0)      go_dec :: Integer -> Text -> r     go_dec !int !bs1 = case unconsPoint bs1 of-        Nothing                       -> errEnd+        Nothing                                   -> errEnd         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> state_dec 1 bs'-            | otherwise               -> errUnx w8+            | W.DIGIT_0 <= w8, w8 <= W.DIGIT_9    -> state_dec 1 bs'+            | otherwise                           -> errUnx w8       where         state_dec :: Int -> Text -> r         state_dec !n !bs = case unconsPoint bs of-            Nothing                         -> kont (NumDecimal dec) bs+            Nothing                                   -> kont (NumDecimal dec) bs             Just (w8, bs')-                | W8_0 <= w8, w8 <= W8_9    -> state_dec (n + 1) bs'-                | W8_e == w8 || W8_E == w8  -> go_sci coef (negate n) bs'-                | otherwise                 -> kont (NumDecimal dec) bs+                | W.DIGIT_0 <= w8, w8 <= W.DIGIT_9    -> state_dec (n + 1) bs'+                | W.LOWER_E == w8 || W.UPPER_E == w8  -> go_sci coef (negate n) bs'+                | otherwise                           -> kont (NumDecimal dec) bs           where             frac = textToInteger (unsafeTakePoints n bs1)             coef = int * 10 ^ n + frac@@ -243,37 +244,37 @@      go_sci :: Integer -> Int -> Text -> r     go_sci !coef !exp10 !bs2 = case unconsPoint bs2 of-        Nothing                       -> errEnd+        Nothing                                           -> errEnd         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_pos coef exp10 bs2 1 bs'-            | W8_PLUS == w8           -> case unconsPoint bs' of-                Nothing               -> errEnd+            | W.DIGIT_0 <= w8, w8 <= W.DIGIT_9            -> go_sci_pos coef exp10 bs2 1 bs'+            | W.PLUS == w8 -> case unconsPoint bs' of+                Nothing                                   -> errEnd                 Just (w8', bs'')-                    | W8_0 <= w8', w8' <= W8_9  -> go_sci_pos coef exp10 bs' 1 bs''-                    | otherwise       ->  errUnx w8'-            | W8_MINUS == w8          -> case unconsPoint bs' of-                Nothing               -> errEnd+                    | W.DIGIT_0 <= w8', w8' <= W.DIGIT_9  -> go_sci_pos coef exp10 bs' 1 bs''+                    | otherwise                           -> errUnx w8'+            | W.HYPHEN == w8 -> case unconsPoint bs' of+                Nothing                                   -> errEnd                 Just (w8', bs'')-                    | W8_0 <= w8', w8' <= W8_9  -> go_sci_neg coef exp10 bs' 1 bs''-                    | otherwise       ->  errUnx w8'-            | otherwise               -> errUnx w8+                    | W.DIGIT_0 <= w8', w8' <= W.DIGIT_9  -> go_sci_neg coef exp10 bs' 1 bs''+                    | otherwise                           -> errUnx w8'+            | otherwise                                   -> errUnx w8      go_sci_pos :: Integer -> Int -> Text -> Int -> Text -> r     go_sci_pos !coef !exp10 !bs2 !n !bs = case unconsPoint bs of-        Nothing                       -> kont (NumScientific sci) bs+        Nothing                                 -> kont (NumScientific sci) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_pos coef exp10 bs2 (n + 1) bs'-            | otherwise               -> kont (NumScientific sci) bs+            | W.DIGIT_0 <= w8, w8 <= W.DIGIT_9  -> go_sci_pos coef exp10 bs2 (n + 1) bs'+            | otherwise                         -> kont (NumScientific sci) bs       where         exp10' = fromInteger (textToInteger (unsafeTakePoints n bs2))         sci = Sci.scientific coef (exp10 + exp10')      go_sci_neg :: Integer -> Int -> Text -> Int -> Text -> r     go_sci_neg !coef !exp10 !bs2 !n !bs = case unconsPoint bs of-        Nothing                       -> kont (NumScientific sci) bs+        Nothing                                 -> kont (NumScientific sci) bs         Just (w8, bs')-            | W8_0 <= w8, w8 <= W8_9  -> go_sci_neg coef exp10 bs2 (n + 1) bs'-            | otherwise               -> kont (NumScientific sci) bs+            | W.DIGIT_0 <= w8, w8 <= W.DIGIT_9  -> go_sci_neg coef exp10 bs2 (n + 1) bs'+            | otherwise                         -> kont (NumScientific sci) bs       where         exp10' = fromInteger (textToInteger (unsafeTakePoints n bs2))         sci = Sci.scientific coef (exp10 - exp10')
src/Data/Aeson/Encoding/Internal.hs view
@@ -82,7 +82,7 @@ newtype Encoding' tag = Encoding {       fromEncoding :: Builder       -- ^ Acquire the underlying bytestring builder.-    } deriving (Typeable)+    }  -- | Often used synonym for 'Encoding''. type Encoding = Encoding' Value@@ -128,7 +128,6 @@ -- > toEncoding (Person name age) = pairs ("name" .= name <> "age" .= age) data Series = Empty             | Value (Encoding' Series)-            deriving (Typeable)  pair :: Key -> Encoding -> Series pair name val = pair' (key name) val
src/Data/Aeson/Internal/Prelude.hs view
@@ -21,7 +21,6 @@ import Data.String as X (IsString(..)) import Data.Text as X (Text) import Data.Time as X (UTCTime)-import Data.Typeable as X (Typeable) import Data.Vector as X (Vector) import Data.Void as X (Void, absurd) import Data.Word as X (Word8, Word16, Word32, Word64)
src/Data/Aeson/Internal/Unescape.hs view
@@ -29,7 +29,7 @@  -- | Unescape JSON text literal. ----- This function is exporeted mostly for testing and benchmarking purposes.+-- This function is exported mostly for testing and benchmarking purposes. unescapeText :: ByteString -> Either UnicodeException Text unescapeText = unsafeDupablePerformIO . try . unescapeTextIO 
src/Data/Aeson/Internal/UnescapeFromText.hs view
@@ -24,7 +24,7 @@  -- | Unescape JSON text literal. ----- This function is exporeted mostly for testing and benchmarking purposes.+-- This function is exported mostly for testing and benchmarking purposes. unescapeFromText :: Text -> Either UnicodeException Text unescapeFromText = unsafeDupablePerformIO . try . unescapeFromTextIO 
− src/Data/Aeson/Internal/Word16.hs
@@ -1,76 +0,0 @@-{-# LANGUAGE PatternSynonyms #-}--- | This is s/Word8/Word16/g copy of .Word8 module.--- This module is used for low-bit working with text <2 (UTF-16)-module Data.Aeson.Internal.Word16 where--import Data.Word (Word16)------------------------------------------------------------------------------------ Word16 ASCII codes as patterns------------------------------------------------------------------------------------ GHC-8.0 doesn't support giving multiple pattern synonyms type signature at once---- spaces-pattern W8_SPACE :: Word16-pattern W8_NL    :: Word16-pattern W8_CR    :: Word16-pattern W8_TAB   :: Word16--pattern W8_SPACE = 0x20-pattern W8_NL    = 0x0a-pattern W8_CR    = 0x0d-pattern W8_TAB   = 0x09---- punctuation-pattern W8_BACKSLASH    :: Word16-pattern W8_DOUBLE_QUOTE :: Word16-pattern W8_DOT          :: Word16-pattern W8_COMMA        :: Word16-pattern W8_COLON        :: Word16--pattern W8_BACKSLASH    = 92-pattern W8_COMMA        = 44-pattern W8_DOT          = 46-pattern W8_DOUBLE_QUOTE = 34-pattern W8_COLON        = 58---- parentheses-pattern W8_CLOSE_CURLY  :: Word16-pattern W8_CLOSE_SQUARE :: Word16-pattern W8_OPEN_SQUARE  :: Word16-pattern W8_OPEN_CURLY   :: Word16--pattern W8_OPEN_CURLY   = 123-pattern W8_OPEN_SQUARE  = 91-pattern W8_CLOSE_CURLY  = 125-pattern W8_CLOSE_SQUARE = 93---- operators-pattern W8_MINUS :: Word16-pattern W8_PLUS  :: Word16--pattern W8_PLUS  = 43-pattern W8_MINUS = 45---- digits-pattern W8_0 :: Word16-pattern W8_9 :: Word16--pattern W8_0 = 48-pattern W8_9 = 57---- lower case-pattern W8_e :: Word16-pattern W8_f :: Word16-pattern W8_n :: Word16-pattern W8_t :: Word16--pattern W8_e = 101-pattern W8_f = 102-pattern W8_n = 110-pattern W8_t = 116---- upper case-pattern W8_E :: Word16-pattern W8_E = 69
− src/Data/Aeson/Internal/Word8.hs
@@ -1,74 +0,0 @@-{-# LANGUAGE PatternSynonyms #-}-module Data.Aeson.Internal.Word8 where--import Data.Word (Word8)------------------------------------------------------------------------------------ Word8 ASCII codes as patterns------------------------------------------------------------------------------------ GHC-8.0 doesn't support giving multiple pattern synonyms type signature at once---- spaces-pattern W8_SPACE :: Word8-pattern W8_NL    :: Word8-pattern W8_CR    :: Word8-pattern W8_TAB   :: Word8--pattern W8_SPACE = 0x20-pattern W8_NL    = 0x0a-pattern W8_CR    = 0x0d-pattern W8_TAB   = 0x09---- punctuation-pattern W8_BACKSLASH    :: Word8-pattern W8_DOUBLE_QUOTE :: Word8-pattern W8_DOT          :: Word8-pattern W8_COMMA        :: Word8-pattern W8_COLON        :: Word8--pattern W8_BACKSLASH    = 92-pattern W8_COMMA        = 44-pattern W8_DOT          = 46-pattern W8_DOUBLE_QUOTE = 34-pattern W8_COLON        = 58---- parentheses-pattern W8_CLOSE_CURLY  :: Word8-pattern W8_CLOSE_SQUARE :: Word8-pattern W8_OPEN_SQUARE  :: Word8-pattern W8_OPEN_CURLY   :: Word8--pattern W8_OPEN_CURLY   = 123-pattern W8_OPEN_SQUARE  = 91-pattern W8_CLOSE_CURLY  = 125-pattern W8_CLOSE_SQUARE = 93---- operators-pattern W8_MINUS :: Word8-pattern W8_PLUS  :: Word8--pattern W8_PLUS  = 43-pattern W8_MINUS = 45---- digits-pattern W8_0 :: Word8-pattern W8_9 :: Word8--pattern W8_0 = 48-pattern W8_9 = 57---- lower case-pattern W8_e :: Word8-pattern W8_f :: Word8-pattern W8_n :: Word8-pattern W8_t :: Word8--pattern W8_e = 101-pattern W8_f = 102-pattern W8_n = 110-pattern W8_t = 116---- upper case-pattern W8_E :: Word8-pattern W8_E = 69
src/Data/Aeson/Key.hs view
@@ -1,6 +1,9 @@ {-# LANGUAGE CPP #-} {-# LANGUAGE DeriveDataTypeable #-}+{-# LANGUAGE DerivingStrategies #-} {-# LANGUAGE GADTs #-}+{-# LANGUAGE GeneralizedNewtypeDeriving #-}+{-# LANGUAGE StandaloneDeriving #-} {-# LANGUAGE TemplateHaskellQuotes #-}  -- |@@ -29,7 +32,6 @@ import Data.Semigroup (Semigroup((<>))) import Data.Text (Text) import Data.Type.Coercion (Coercion (..))-import Data.Typeable (Typeable) import Text.Read (Read (..))  import qualified Data.String@@ -39,7 +41,7 @@ import qualified Test.QuickCheck as QC  newtype Key = Key { unKey :: Text }-  deriving (Eq, Ord, Typeable, Data)+  deriving (Data)  fromString :: String -> Key fromString = Key . T.pack@@ -58,7 +60,7 @@ -- -- Using 'coercing' we can make more efficient implementations -- when 'Key' is backed up by 'Text' without exposing internals.--- +-- coercionToText :: Maybe (Coercion Key Text) coercionToText = Just Coercion {-# INLINE coercionToText #-}@@ -79,13 +81,14 @@     readPrec = fromString <$> readPrec  instance Show Key where-    showsPrec d (Key k) = showsPrec d k +    showsPrec d (Key k) = showsPrec d k  instance Data.String.IsString Key where     fromString = fromString -instance Hashable Key where-    hashWithSalt salt (Key k) = hashWithSalt salt k+deriving newtype instance Eq Key+deriving newtype instance Ord Key+deriving newtype instance Hashable Key  instance NFData Key where     rnf (Key k) = rnf k
src/Data/Aeson/KeyMap.hs view
@@ -114,7 +114,6 @@ import Data.Text (Text) import Data.These (These (..)) import Data.Type.Coercion (Coercion (..))-import Data.Typeable (Typeable) import Text.Read (Read (..), Lexeme(..), readListPrecDefault, prec, lexP, parens)  import qualified Data.Aeson.Key as Key@@ -141,7 +140,7 @@  -- | A map from JSON key type 'Key' to 'v'. newtype KeyMap v = KeyMap { unKeyMap :: Map Key v }-  deriving (Eq, Ord, Typeable, Data, Functor)+  deriving (Eq, Ord, Data, Functor)   -- | Construct an empty map.@@ -355,7 +354,7 @@  -- | A map from JSON key type 'Key' to 'v'. newtype KeyMap v = KeyMap { unKeyMap :: HashMap Key v }-  deriving (Eq, Ord, Typeable, Data, Functor)+  deriving (Eq, Ord, Data, Functor)  -- | Construct an empty map. empty :: KeyMap v@@ -689,6 +688,12 @@ ------------------------------------------------------------------------------- -- semialign -------------------------------------------------------------------------------++-- |+--+-- @since 2.2.5.0+instance SA.Unzip KeyMap where+    unzip = SA.unzipDefault  instance SA.Zip KeyMap where     zipWith = intersectionWith
src/Data/Aeson/RFC8785.hs view
@@ -13,7 +13,6 @@ import Data.Aeson.Encoding import Data.Aeson.Encoding.Internal import Data.Aeson.Internal.Prelude-import Data.Aeson.Internal.Word8  import qualified Data.Aeson.Key as Key import qualified Data.Aeson.KeyMap as KM@@ -24,6 +23,7 @@ import qualified Data.Scientific as Sci import qualified Data.Text.Encoding as TE import qualified Data.Vector as V+import qualified Data.Word8.Patterns as W8  -- $setup -- >>> import Data.Aeson@@ -94,8 +94,8 @@ -- RFC8785 Appendix D says "don't use bignums". canonicalNumber :: Scientific -> Encoding canonicalNumber m = case compare m 0 of-    EQ -> Encoding (B.word8 W8_0)-    LT -> Encoding (B.word8 W8_MINUS <> fromEncoding (canonicalNumber' (negate m)))+    EQ -> Encoding (B.word8 W8.DIGIT_0)+    LT -> Encoding (B.word8 W8.HYPHEN <> fromEncoding (canonicalNumber' (negate m)))     GT -> canonicalNumber' m  -- input: Positive number@@ -104,36 +104,36 @@     | k <= n, n <= 21     = Encoding $         BP.primMapListFixed BP.word8 ds <>-        BP.primMapListFixed BP.word8 (replicate (n - k) W8_0)+        BP.primMapListFixed BP.word8 (replicate (n - k) W8.DIGIT_0)      | 0 < n, n <= 21     , let (pfx, sfx) = splitAt n ds     = Encoding $         BP.primMapListFixed BP.word8 pfx <>-        B.word8 W8_DOT <>+        B.word8 W8.PERIOD <>         BP.primMapListFixed BP.word8 sfx      | -6 < n, n <= 0     = Encoding $-        B.word8 W8_0 <>-        B.word8 W8_DOT <>-        BP.primMapListFixed BP.word8 (replicate (negate n) W8_0) <>+        B.word8 W8.DIGIT_0 <>+        B.word8 W8.PERIOD <>+        BP.primMapListFixed BP.word8 (replicate (negate n) W8.DIGIT_0) <>         BP.primMapListFixed BP.word8 ds      | k == 1, [d] <- ds     = Encoding $         B.word8 d <>-        B.word8 W8_e <>-        B.word8 (if (n - 1) >= 0 then W8_PLUS else W8_MINUS) <>+        B.word8 W8.LOWER_E <>+        B.word8 (if (n - 1) >= 0 then W8.PLUS else W8.HYPHEN) <>         BP.primMapListFixed BP.word8 (integerToDecimalDigits (abs (toInteger n - 1)))      | (d:ds') <- ds     = Encoding $         B.word8 d <>-        B.word8 W8_DOT <>+        B.word8 W8.PERIOD <>         BP.primMapListFixed BP.word8 ds' <>-        B.word8 W8_e <>-        B.word8 (if (n - 1) >= 0 then W8_PLUS else W8_MINUS) <>+        B.word8 W8.LOWER_E <>+        B.word8 (if (n - 1) >= 0 then W8.PLUS else W8.HYPHEN) <>         BP.primMapListFixed BP.word8 (integerToDecimalDigits (abs (toInteger n - 1)))      | otherwise@@ -166,4 +166,4 @@ integerToDecimalDigits = go [] where     go acc 0 = acc     go acc i = case quotRemInteger i 10 of-        (# q, r #) -> go (d:acc) q where !d = fromIntegral r + W8_0+        (# q, r #) -> go (d:acc) q where !d = fromIntegral r + W8.DIGIT_0
src/Data/Aeson/TH.hs view
@@ -945,7 +945,7 @@                           (appE [|show|] (varE unknownFields)))                       []               ]-      x:xs = [ lookupField argTy+      (x,xs) = nonEmpty [ lookupField argTy                `appE` dispatchParseJSON jc conName tvMap argTy                `appE` litE (stringL $ show tName)                `appE` litE (stringL $ constructorTagModifier opts $ nameBase conName)@@ -955,6 +955,11 @@              | (field, argTy) <- zip fields argTys              ] +-- A hack, as I'm too lazy to change code to not assume fields are non empty.+nonEmpty :: [a] -> (a, [a])+nonEmpty (x:xs) = (x,xs)+nonEmpty []     = error "unexpected empty list"+ getValField :: Name -> String -> [MatchQ] -> Q Exp getValField obj valFieldName matches = do   val <- newName "val"@@ -1056,12 +1061,12 @@              -> [Type] -- ^ The argument types of the constructor.              -> Name -- ^ Name of the type to which the constructor belongs.              -> Name -- ^ 'Con'structor name.-             -> Integer -- ^ 'Con'structor arity.+             -> Integer -- ^ 'Con'structor arity. >= 1              -> [Q Match] parseProduct jc tvMap argTys tName conName numArgs =     [ do arr <- newName "arr"          -- List of: "parseJSON (arr `V.unsafeIndex` <IX>)"-         let x:xs = [ dispatchParseJSON jc conName tvMap argTy+         let (x,xs) = nonEmpty [ dispatchParseJSON jc conName tvMap argTy                       `appE`                       infixApp (varE arr)                                [|V.unsafeIndex|]@@ -1271,7 +1276,7 @@     varE $ case M.lookup tyName tvMap of                 Just (tfjoExp, tfjExp, tfjlExp) -> case list of                     Omit -> tfjoExp-                    Single -> tfjExp +                    Single -> tfjExp                     Plural -> tfjlExp                 Nothing                   -> jsonFunValOrListName list jf Arity0 dispatchFunByType jc jf conName tvMap list (SigT ty _) =
src/Data/Aeson/Types.hs view
@@ -20,6 +20,7 @@     , Series     , Array     , emptyArray+    , isEmptyArray     , Pair     , Object     , emptyObject
src/Data/Aeson/Types/FromJSON.hs view
@@ -1,18 +1,20 @@ {-# LANGUAGE CPP #-} {-# LANGUAGE DataKinds #-} {-# LANGUAGE DefaultSignatures #-}-{-# LANGUAGE InstanceSigs #-}+{-# LANGUAGE DerivingVia #-} {-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE GADTs #-}+{-# LANGUAGE InstanceSigs #-} {-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE OverloadedStrings #-} {-# LANGUAGE PolyKinds #-} {-# LANGUAGE RecordWildCards #-} {-# LANGUAGE ScopedTypeVariables #-}+{-# LANGUAGE StandaloneDeriving #-}+{-# LANGUAGE TupleSections #-} {-# LANGUAGE TypeApplications #-} {-# LANGUAGE TypeOperators #-}-{-# LANGUAGE TupleSections #-} {-# LANGUAGE UndecidableInstances #-} {-# LANGUAGE ViewPatterns #-} @@ -86,13 +88,14 @@ import Data.Aeson.Internal.Prelude  import Control.Monad (zipWithM, guard)+import Data.Aeson.Decoding.ByteString.Lazy+import Data.Aeson.Decoding.Conversion (unResult, toResultValue, lbsSpace) import Data.Aeson.Internal.Functions (mapKey, mapKeyO) import Data.Aeson.Internal.Scientific import Data.Aeson.Types.Generic import Data.Aeson.Types.Internal-import Data.Aeson.Decoding.ByteString.Lazy-import Data.Aeson.Decoding.Conversion (unResult, toResultValue, lbsSpace) import Data.Bits (unsafeShiftR)+import Data.Complex (Complex(..)) import Data.Fixed (Fixed, HasResolution (resolution), Nano) import Data.Functor.Compose (Compose(..)) import Data.Functor.Identity (Identity(..))@@ -100,6 +103,7 @@ import Data.Functor.Sum (Sum(..)) import Data.Functor.These (These1 (..)) import Data.Hashable (Hashable(..))+import Data.Kind (Type) import Data.List.NonEmpty (NonEmpty(..)) import Data.Ord (Down (..)) import Data.Ratio ((%), Ratio)@@ -213,16 +217,22 @@     (\sci rest -> if T.null rest then return sci else fail $ "Expecting end-of-input, got " ++ show (T.take 10 rest))     fail -parseIntegralText :: Integral a => String -> Text -> Parser a-parseIntegralText name t =+parseBoundedScientificTextTo :: (Scientific -> Parser a) -> String -> Text -> Parser a+parseBoundedScientificTextTo toResultType name t =     prependContext name $             parseScientificText t         >>= rejectLargeExponent-        >>= parseIntegralFromScientific+        >>= toResultType   where     rejectLargeExponent :: Scientific -> Parser Scientific     rejectLargeExponent s = withBoundedScientific' pure (Number s) +parseBoundedScientificText :: String -> Text -> Parser Scientific+parseBoundedScientificText = parseBoundedScientificTextTo pure++parseIntegralText :: Integral a => String -> Text -> Parser a+parseIntegralText = parseBoundedScientificTextTo parseIntegralFromScientific+ parseBoundedIntegralText :: (Bounded a, Integral a) => String -> Text -> Parser a parseBoundedIntegralText name t =     prependContext name $@@ -793,11 +803,13 @@ withBoundedScientific_ :: (Parser a -> Parser a) -> (Scientific -> Parser a) -> Value -> Parser a withBoundedScientific_ whenFail f (Number scientific) =     if exp10 > 1024-    then whenFail (fail msg)+    then whenFail (fail (msg "greater than 1024"))+    else if exp10 < -1024+    then whenFail (fail (msg "less than -1024"))     else f scientific   where     exp10 = base10Exponent scientific-    msg = "found a number with exponent " ++ show exp10 ++ ", but it must not be greater than 1024"+    msg req = "found a number with exponent " ++ show exp10 ++ ", but it must not be " ++ req withBoundedScientific_ whenFail _ v =     whenFail (typeMismatch "Number" v) @@ -865,7 +877,7 @@ (.:!) = explicitParseFieldMaybe' parseJSON  -- | Retrieve the value associated with the given key of an 'Object'.--- If the key is not present and the 'omittedField' is @'Just' x@ for some @x@,+-- If the key is not present or the field is @null@ and the 'omittedField' is @'Just' x@ for some @x@, -- the result will be that @x@. -- -- @since 2.2.0.0@@ -873,7 +885,7 @@ (.:?=) = explicitParseFieldOmit omittedField parseJSON  -- | Retrieve the value associated with the given key of an 'Object'.--- If the key is not present or the field is @null@ and the 'omittedField' is @'Just' x@ for some @x@,+-- If the key is not present and the 'omittedField' is @'Just' x@ for some @x@, -- the result will be that @x@. -- -- This differs from '.:?=' by attempting to parse 'Null' the same as any@@ -1703,14 +1715,7 @@         _      -> Scientific.toRealFloat <$> parseScientificText t  instance (FromJSON a, Integral a) => FromJSON (Ratio a) where-    parseJSON (Number x)-      | exp10 <= 1024-      , exp10 >= -1024 = return $! realToFrac x-      | otherwise      = prependContext "Ratio" $ fail msg-      where-        exp10 = base10Exponent x-        msg = "found a number with exponent " ++ show exp10-           ++ ", but it must not be greater than 1024 or less than -1024"+    parseJSON n@(Number _) = withBoundedScientific "Ratio" (($!) pure . realToFrac) n     parseJSON o = objParser o       where         objParser = withObject "Rational" $ \obj -> do@@ -1720,6 +1725,17 @@             then fail "Ratio denominator was 0"             else pure $ numerator % denominator +-- | A complex number @x+iy@ is encoded as an array @[x, y]@.+--+-- @since 2.3.1.0+instance FromJSON a => FromJSON (Complex a) where+    parseJSON = withArray "Complex" $ \c ->+        let n = V.length c+        in if n == 2+           then (:+) <$> parseJSONElemAtIndex parseJSON 0 c+                     <*> parseJSONElemAtIndex parseJSON 1 c+           else fail $ "cannot unpack array of length " ++ show n ++ "into a Complex"+ -- | This instance includes a bounds check to prevent maliciously -- large inputs to fill up the memory of the target system. You can -- newtype 'Scientific' and provide your own instance using@@ -1727,6 +1743,12 @@ instance HasResolution a => FromJSON (Fixed a) where     parseJSON = prependContext "Fixed" . withBoundedScientific' (pure . realToFrac) +-- |+-- @since 2.3.1.0+instance HasResolution a => FromJSONKey (Fixed a) where+  fromJSONKey = FromJSONKeyTextParser $ \t ->+      realToFrac <$> parseBoundedScientificText "Fixed" t+ instance FromJSON Int where     parseJSON = parseBoundedIntegral "Int" @@ -1922,17 +1944,10 @@  instance FromJSON1 Identity where     liftParseJSON _ p _ a = coerce (p a)-     liftParseJSONList _ _ p a = coerce (p a)-     liftOmittedField = coerce -instance (FromJSON a) => FromJSON (Identity a) where-    parseJSON = parseJSON1--    parseJSONList = liftParseJSONList omittedField parseJSON parseJSONList--    omittedField = coerce (omittedField @a)+deriving via (a :: Type) instance FromJSON a => FromJSON (Identity a)  instance (FromJSONKey a) => FromJSONKey (Identity a) where     fromJSONKey = coerceFromJSONKeyFunction (fromJSONKey :: FromJSONKeyFunction a)@@ -2313,114 +2328,58 @@ -------------------------------------------------------------------------------  -- | @since 2.2.0.0-instance FromJSON1 Down where-    liftParseJSON _ p _ = coerce p--    liftOmittedField = coerce+deriving via Identity instance FromJSON1 Down  -- | @since 2.2.0.0-instance FromJSON a => FromJSON (Down a) where-    parseJSON = parseJSON1+deriving via (a :: Type) instance FromJSON a => FromJSON (Down a)  ------------------------------------------------------------------------------- -- base Monoid/Semigroup ------------------------------------------------------------------------------- -instance FromJSON1 Monoid.Dual where-    liftParseJSON _ p _ = coerce p--    liftOmittedField = coerce--instance FromJSON a => FromJSON (Monoid.Dual a) where-    parseJSON = parseJSON1---instance FromJSON1 Monoid.First where-    liftParseJSON o = coerce (liftParseJSON @Maybe o)-    liftOmittedField _ = Just (Monoid.First Nothing)--instance FromJSON a => FromJSON (Monoid.First a) where-    parseJSON = parseJSON1-    omittedField = omittedField1--instance FromJSON1 Monoid.Last where-    liftParseJSON o = coerce (liftParseJSON @Maybe o)-    liftOmittedField _ = Just (Monoid.Last Nothing)--instance FromJSON a => FromJSON (Monoid.Last a) where-    parseJSON = parseJSON1-    omittedField = omittedField1--instance FromJSON1 Semigroup.Min where-    liftParseJSON _ p _ a = coerce (p a)--    liftParseJSONList _ _ p a = coerce (p a)--    liftOmittedField = coerce--instance (FromJSON a) => FromJSON (Semigroup.Min a) where-    parseJSON = parseJSON1--    parseJSONList = liftParseJSONList omittedField parseJSON parseJSONList--    omittedField = omittedField1--instance FromJSON1 Semigroup.Max where-    liftParseJSON _ p _ a = coerce (p a)--    liftParseJSONList _ _ p a = coerce (p a)-    liftOmittedField = coerce--instance (FromJSON a) => FromJSON (Semigroup.Max a) where-    parseJSON = parseJSON1--    parseJSONList = liftParseJSONList omittedField parseJSON parseJSONList-    omittedField = omittedField1--instance FromJSON1 Semigroup.First where-    liftParseJSON _ p _ a = coerce (p a)--    liftParseJSONList _ _ p a = coerce (p a)-    liftOmittedField = coerce+deriving via Identity instance FromJSON1 Monoid.Dual+deriving via (a :: Type) instance FromJSON a => FromJSON (Monoid.Dual a) -instance (FromJSON a) => FromJSON (Semigroup.First a) where-    parseJSON = parseJSON1+deriving via Maybe instance FromJSON1 Monoid.First+deriving via Maybe a instance FromJSON a => FromJSON (Monoid.First a) -    parseJSONList = liftParseJSONList omittedField parseJSON parseJSONList+deriving via Maybe instance FromJSON1 Monoid.Last+deriving via Maybe a instance FromJSON a => FromJSON (Monoid.Last a) +deriving via Identity instance FromJSON1 Semigroup.Min+deriving via (a :: Type) instance FromJSON a => FromJSON (Semigroup.Min a) -instance FromJSON1 Semigroup.Last where-    liftParseJSON _ p _ a = coerce (p a)+deriving via Identity instance FromJSON1 Semigroup.Max+deriving via (a :: Type) instance FromJSON a => FromJSON (Semigroup.Max a) -    liftParseJSONList _ _ p a = coerce (p a)-    liftOmittedField = coerce+deriving via Identity instance FromJSON1 Semigroup.First+deriving via (a :: Type) instance FromJSON a => FromJSON (Semigroup.First a) -instance (FromJSON a) => FromJSON (Semigroup.Last a) where-    parseJSON = parseJSON1+deriving via Identity instance FromJSON1 Semigroup.Last+deriving via (a :: Type) instance FromJSON a => FromJSON (Semigroup.Last a) -    parseJSONList = liftParseJSONList omittedField parseJSON parseJSONList-    omittedField = omittedField1+deriving via Identity instance FromJSON1 Semigroup.WrappedMonoid+deriving via (a :: Type) instance FromJSON a => FromJSON (Semigroup.WrappedMonoid a) -instance FromJSON1 Semigroup.WrappedMonoid where-    liftParseJSON _ p _ a = coerce (p a)+-- | @since 2.2.3.0+deriving via Identity instance FromJSON1 Semigroup.Sum+-- | @since 2.2.3.0+deriving via (a :: Type) instance FromJSON a => FromJSON (Semigroup.Sum a) -    liftParseJSONList _ _ p a = coerce (p a)-    liftOmittedField = coerce+-- | @since 2.2.3.0+deriving via Identity instance FromJSON1 Semigroup.Product+-- | @since 2.2.3.0+deriving via (a :: Type) instance FromJSON a => FromJSON (Semigroup.Product a) -instance (FromJSON a) => FromJSON (Semigroup.WrappedMonoid a) where-    parseJSON = parseJSON1+-- | @since 2.2.3.0+deriving via Bool instance FromJSON Semigroup.All -    parseJSONList = liftParseJSONList omittedField parseJSON parseJSONList-    omittedField = omittedField1+-- | @since 2.2.3.0+deriving via Bool instance FromJSON Semigroup.Any  #if !MIN_VERSION_base(4,16,0)-instance FromJSON1 Semigroup.Option where-    liftParseJSON o = coerce (liftParseJSON @Maybe o)-    liftOmittedField _ = Just (Semigroup.Option Nothing)--instance FromJSON a => FromJSON (Semigroup.Option a) where-    parseJSON = parseJSON1-    omittedField = omittedField1+deriving via Maybe instance FromJSON1 Semigroup.Option+deriving via Maybe a instance FromJSON a => FromJSON (Semigroup.Option a) #endif  -------------------------------------------------------------------------------
src/Data/Aeson/Types/Internal.hs view
@@ -112,18 +112,18 @@                      | Index {-# UNPACK #-} !Int                        -- ^ JSON path element of an index into an                        -- array, \"array[index]\".-                       deriving (Eq, Show, Typeable, Ord)+                       deriving (Eq, Show, Ord) type JSONPath = [JSONPathElement]  -- | The internal result of running a 'Parser'. data IResult a = IError JSONPath String                | ISuccess a-               deriving (Eq, Show, Typeable)+               deriving (Eq, Show)  -- | The result of running a 'Parser'. data Result a = Error String               | Success a-                deriving (Eq, Show, Typeable)+                deriving (Eq, Show)  instance NFData JSONPathElement where   rnf (Key t)   = rnf t@@ -369,7 +369,7 @@            | Number !Scientific            | Bool !Bool            | Null-             deriving (Eq, Read, Typeable, Data, Generic)+             deriving (Eq, Read, Data, Generic)  -- | Since version 1.5.6.0 version object values are printed in lexicographic key order --@@ -505,7 +505,7 @@ newtype DotNetTime = DotNetTime {       fromDotNetTime :: UTCTime       -- ^ Acquire the underlying value.-    } deriving (Eq, Ord, Read, Show, Typeable, FormatTime)+    } deriving (Eq, Ord, Read, Show, FormatTime)  instance NFData Value where     rnf (Object o) = rnf o@@ -552,8 +552,12 @@ emptyArray :: Value emptyArray = Array V.empty --- | Determines if the 'Value' is an empty 'Array'.--- Note that: @isEmptyArray 'emptyArray'@.+-- | Determines whether the 'Value' is an empty 'Array'.+--+-- Do note that if this is `False`, the `Value` may be a non-empty+-- array, or it may not even be an array.+--+-- @since 2.3.1.0 isEmptyArray :: Value -> Bool isEmptyArray (Array arr) = V.null arr isEmptyArray _ = False
src/Data/Aeson/Types/ToJSON.hs view
@@ -1,18 +1,20 @@ {-# LANGUAGE CPP #-} {-# LANGUAGE DefaultSignatures #-}+{-# LANGUAGE DerivingVia #-} {-# LANGUAGE EmptyCase #-} {-# LANGUAGE EmptyDataDecls #-} {-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE FunctionalDependencies #-}-{-# LANGUAGE InstanceSigs #-} {-# LANGUAGE GADTs #-}+{-# LANGUAGE InstanceSigs #-} {-# LANGUAGE OverloadedStrings #-} {-# LANGUAGE PolyKinds #-} {-# LANGUAGE RecordWildCards #-} {-# LANGUAGE ScopedTypeVariables #-}-{-# LANGUAGE TypeOperators #-}+{-# LANGUAGE StandaloneDeriving #-} {-# LANGUAGE TypeApplications #-}+{-# LANGUAGE TypeOperators #-} {-# LANGUAGE UndecidableInstances #-}  module Data.Aeson.Types.ToJSON@@ -67,6 +69,7 @@ import qualified Data.Aeson.Key as Key import qualified Data.Aeson.KeyMap as KM import Data.Bits (unsafeShiftR)+import Data.Complex (Complex(..)) import Data.DList (DList) import Data.Fixed (Fixed, HasResolution, Nano) import Data.Foldable (toList)@@ -76,6 +79,7 @@ import Data.Functor.Product (Product(..)) import Data.Functor.Sum (Sum(..)) import Data.Functor.These (These1 (..))+import Data.Kind (Type) import Data.List (intersperse) import Data.List.NonEmpty (NonEmpty(..)) import Data.Maybe (isNothing)@@ -364,11 +368,11 @@ instance value ~ Value => KeyValue Value (KM.KeyMap value) where     (.=) = explicitToField toJSON     {-# INLINE (.=) #-}-    +     explicitToField f name value = KM.singleton name (f value)     {-# INLINE explicitToField #-} --- | An optional key-value pair for envoding to a JSON object+-- | An optional key-value pair for encoding to a JSON object -- -- @since 2.2.0.0 --@@ -1421,6 +1425,19 @@         "numerator" .= numerator r <>         "denominator" .= denominator r +-- | A complex number @x+iy@ is encoded as an array @[x, y]@.+--+-- @since 2.3.1.0+instance ToJSON a => ToJSON (Complex a) where+    toJSON (i :+ q) = Array $ V.create $ do+        mv <- VM.unsafeNew 2+        VM.unsafeWrite mv 0 (toJSON i)+        VM.unsafeWrite mv 1 (toJSON q)+        return mv+    toEncoding (i :+ q) = E.list id+        [ toEncoding i+        , toEncoding q+        ]  instance HasResolution a => ToJSON (Fixed a) where     toJSON = Number . realToFrac@@ -1641,14 +1658,7 @@      liftOmitField o (Identity a) = o a -instance (ToJSON a) => ToJSON (Identity a) where-    toJSON = toJSON1-    toJSONList = liftToJSONList omitField toJSON toJSONList--    toEncoding = toEncoding1-    toEncodingList = liftToEncodingList omitField toEncoding toEncodingList--    omitField (Identity x) = omitField x+deriving via (a :: Type) instance ToJSON a => ToJSON (Identity a)  instance (ToJSONKey a) => ToJSONKey (Identity a) where     toJSONKey = contramapToJSONKeyFunction runIdentity toJSONKey@@ -2075,115 +2085,58 @@ -------------------------------------------------------------------------------  -- | @since 2.2.0.0-instance ToJSON1 Down where-    liftToJSON _ t _ = coerce t-    liftToEncoding _ t _ = coerce t-    liftOmitField = coerce+deriving via Identity instance ToJSON1 Down  -- | @since 2.2.0.0-instance ToJSON a => ToJSON (Down a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+deriving via (a :: Type) instance ToJSON a => ToJSON (Down a)  ------------------------------------------------------------------------------- -- base Monoid/Semigroup ------------------------------------------------------------------------------- -instance ToJSON1 Monoid.Dual where-    liftToJSON _ t _ = t . Monoid.getDual-    liftToEncoding _ t _ = t . Monoid.getDual-    liftOmitField = coerce--instance ToJSON a => ToJSON (Monoid.Dual a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1--instance ToJSON1 Monoid.First where-    liftToJSON o t to' = liftToJSON o t to' . Monoid.getFirst-    liftToEncoding o t to' = liftToEncoding o t to' . Monoid.getFirst-    liftOmitField :: forall a. (a -> Bool) -> Monoid.First a -> Bool-    liftOmitField _ = coerce (isNothing @a)-    -instance ToJSON a => ToJSON (Monoid.First a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1--instance ToJSON1 Monoid.Last where-    liftToJSON o t to' = liftToJSON o t to' . Monoid.getLast-    liftToEncoding o t to' = liftToEncoding o t to' . Monoid.getLast--    liftOmitField :: forall a. (a -> Bool) -> Monoid.Last a -> Bool-    liftOmitField _ = coerce (isNothing @a)+deriving via Identity instance ToJSON1 Monoid.Dual+deriving via (a :: Type) instance ToJSON a => ToJSON (Monoid.Dual a) -instance ToJSON a => ToJSON (Monoid.Last a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+deriving via Maybe instance ToJSON1 Monoid.First+deriving via Maybe a instance ToJSON a => ToJSON (Monoid.First a) -instance ToJSON1 Semigroup.Min where-    liftToJSON _ t _ (Semigroup.Min x) = t x-    liftToEncoding _ t _ (Semigroup.Min x) = t x-    liftOmitField = coerce+deriving via Maybe instance ToJSON1 Monoid.Last+deriving via Maybe a instance ToJSON a => ToJSON (Monoid.Last a) -instance ToJSON a => ToJSON (Semigroup.Min a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+deriving via Identity instance ToJSON1 Semigroup.Min+deriving via (a :: Type) instance ToJSON a => ToJSON (Semigroup.Min a) +deriving via Identity instance ToJSON1 Semigroup.Max+deriving via (a :: Type) instance ToJSON a => ToJSON (Semigroup.Max a) -instance ToJSON1 Semigroup.Max where-    liftToJSON _ t _ (Semigroup.Max x) = t x-    liftToEncoding _ t _ (Semigroup.Max x) = t x-    liftOmitField = coerce+deriving via Identity instance ToJSON1 Semigroup.First+deriving via (a :: Type) instance ToJSON a => ToJSON (Semigroup.First a) -instance ToJSON a => ToJSON (Semigroup.Max a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+deriving via Identity instance ToJSON1 Semigroup.Last+deriving via (a :: Type) instance ToJSON a => ToJSON (Semigroup.Last a) -instance ToJSON1 Semigroup.First where-    liftToJSON _ t _ (Semigroup.First x) = t x-    liftToEncoding _ t _ (Semigroup.First x) = t x-    liftOmitField = coerce+deriving via Identity instance ToJSON1 Semigroup.WrappedMonoid+deriving via (a :: Type) instance ToJSON a => ToJSON (Semigroup.WrappedMonoid a) -instance ToJSON a => ToJSON (Semigroup.First a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+-- | @since 2.2.3.0+deriving via Identity instance ToJSON1 Semigroup.Sum+-- | @since 2.2.3.0+deriving via (a :: Type) instance ToJSON a => ToJSON (Semigroup.Sum a) -instance ToJSON1 Semigroup.Last where-    liftToJSON _ t _ (Semigroup.Last x) = t x-    liftToEncoding _ t _ (Semigroup.Last x) = t x-    liftOmitField = coerce+-- | @since 2.2.3.0+deriving via Identity instance ToJSON1 Semigroup.Product+-- | @since 2.2.3.0+deriving via (a :: Type) instance ToJSON a => ToJSON (Semigroup.Product a) -instance ToJSON a => ToJSON (Semigroup.Last a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+-- | @since 2.2.3.0+deriving via Bool instance ToJSON Semigroup.All -instance ToJSON1 Semigroup.WrappedMonoid where-    liftToJSON _ t _ (Semigroup.WrapMonoid x) = t x-    liftToEncoding _ t _ (Semigroup.WrapMonoid x) = t x-    liftOmitField = coerce-    -instance ToJSON a => ToJSON (Semigroup.WrappedMonoid a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+-- | @since 2.2.3.0+deriving via Bool instance ToJSON Semigroup.Any  #if !MIN_VERSION_base(4,16,0)-instance ToJSON1 Semigroup.Option where-    liftToJSON o t to' = liftToJSON o t to' . Semigroup.getOption-    liftToEncoding o t to' = liftToEncoding o t to' . Semigroup.getOption-    liftOmitField _ = isNothing . Semigroup.getOption--instance ToJSON a => ToJSON (Semigroup.Option a) where-    toJSON = toJSON1-    toEncoding = toEncoding1-    omitField = omitField1+deriving via Maybe instance ToJSON1 Semigroup.Option+deriving via Maybe a instance ToJSON a => ToJSON (Semigroup.Option a) #endif  -------------------------------------------------------------------------------
tests/DoubleToScientific.hs view
@@ -114,7 +114,7 @@     (s, e, lower_boundary_is_closer) = decodeFloat' v     lowerBoundaryCloser' = if lower_boundary_is_closer then lowerBoundaryCloser else id --- | return significant, exponent and whether lower boundery is closer.+-- | return significand, exponent and whether lower boundary is closer. -- -- GHC's decodeFloat does "weird" stuff to denormal doubles, -- that messes up our delta calculation.
tests/Instances.hs view
@@ -28,6 +28,11 @@ import Data.Orphans () import Test.QuickCheck.Instances () +#if !MIN_VERSION_base(4,16,0)+import Data.Semigroup (Option (..))+import Data.Tuple.Solo (Solo (..))+#endif+ -- "System" types.  instance Arbitrary DotNetTime where@@ -157,9 +162,13 @@  #if !MIN_VERSION_base(4,16,0) instance Arbitrary OptionField where-    arbitrary = OptionField <$> arbitrary+    arbitrary = OptionField . Option <$> arbitrary #endif +#if !MIN_VERSION_base(4,16,0) && MIN_VERSION_QuickCheck(2,17,0)+instance Arbitrary a => Arbitrary (Solo a) where+    arbitrary = MkSolo <$> arbitrary+#endif  instance ApproxEq Char where     (=~) = (==)
tests/JSONTestSuite/results/n_array_spaces_vertical_tab_formfeed.tok view
@@ -1,3 +1,3 @@ TkArrayOpen TkItem-TkErr "Unespected control character while parsing string literal"+TkErr "Unexpected control character while parsing string literal"
tests/JSONTestSuite/results/n_string_unescaped_ctrl_char.tok view
@@ -1,3 +1,3 @@ TkArrayOpen TkItem-TkErr "Unespected control character while parsing string literal"+TkErr "Unexpected control character while parsing string literal"
tests/JSONTestSuite/results/n_string_unescaped_newline.tok view
@@ -1,3 +1,3 @@ TkArrayOpen TkItem-TkErr "Unespected control character while parsing string literal"+TkErr "Unexpected control character while parsing string literal"
tests/JSONTestSuite/results/n_string_unescaped_tab.tok view
@@ -1,3 +1,3 @@ TkArrayOpen TkItem-TkErr "Unespected control character while parsing string literal"+TkErr "Unexpected control character while parsing string literal"
tests/PropUtils.hs view
@@ -31,7 +31,7 @@  import Data.Aeson (eitherDecode, encode) import Data.Aeson.Encoding (encodingToLazyByteString)-import Data.Aeson.Types+import Data.Aeson.Types hiding (isEmptyArray) import qualified Data.Aeson.Key as Key import qualified Data.Aeson.KeyMap as KM import Data.HashMap.Strict (HashMap)
tests/PropertyKeys.hs view
@@ -6,6 +6,7 @@ import Prelude.Compat  import Control.Applicative (Const)+import Data.Fixed (Fixed, E3, E6) import Data.Time.Compat (Day, LocalTime, TimeOfDay, UTCTime) import Data.Time.Calendar.Compat (DayOfWeek) import Data.Time.Calendar.Month.Compat (Month)@@ -47,4 +48,6 @@     , testProperty "Lazy Text"     $ roundTripKey @LT.Text     , testProperty "UUID"          $ roundTripKey @UUID.UUID     , testProperty "Const Text"    $ roundTripKey @(Const T.Text ())+    , testProperty "Fixed E3"      $ roundTripKey @(Fixed E3)+    , testProperty "Fixed E6"      $ roundTripKey @(Fixed E6)     ]
tests/PropertyRoundTrip.hs view
@@ -7,6 +7,7 @@  import Control.Applicative (Const) import Data.Aeson.Types+import Data.Complex (Complex(..)) import Data.DList (DList) import Data.List.NonEmpty (NonEmpty) import Data.Map (Map)@@ -29,6 +30,7 @@ import Test.Tasty.QuickCheck (testProperty) import Types import qualified Data.Monoid as Monoid+import qualified Data.Semigroup as Semigroup import qualified Data.Text as T import qualified Data.Text.Lazy as LT import qualified Data.Text.Short as ST@@ -80,6 +82,8 @@     , testProperty "Seq" $ roundTripEq @(Seq Int)     , testProperty "Rational" $ roundTripEq @Rational     , testProperty "Ratio Int" $ roundTripEq @(Ratio Int)+    , testProperty "Complex Float" $ roundTripEq @(Complex Float)+    , testProperty "Complex Double" $ roundTripEq @(Complex Double)     , testProperty "UUID" $ roundTripEq @UUID.UUID     , testProperty "These" $ roundTripEq @(These Char Bool)     , testProperty "Fix" $ roundTripEq @(F.Fix (These Char))@@ -87,6 +91,10 @@     , testProperty "Nu" $ roundTripEq @(F.Nu (These Char))     , testProperty "Maybe" $ roundTripEq @(Maybe Int)     , testProperty "Monoid.First" $ roundTripEq @(Monoid.First Int)+    , testProperty "Semigroup.Sum" $ roundTripEq @(Semigroup.Sum Int)+    , testProperty "Semigroup.Product" $ roundTripEq @(Semigroup.Product Int)+    , testProperty "Semigroup.All" $ roundTripEq @Semigroup.All+    , testProperty "Semigroup.Any" $ roundTripEq @Semigroup.Any     , testProperty "Strict Pair" $ roundTripEq @(S.Pair Int Char)     , testProperty "Strict Either" $ roundTripEq @(S.Either Int Char)     , testProperty "Strict These" $ roundTripEq @(S.These Int Char)
+ tests/Regression/Issue1138.hs view
@@ -0,0 +1,23 @@+{-# LANGUAGE OverloadedStrings #-}+module Regression.Issue1138 (issue1138) where++import Test.Tasty (TestTree, testGroup)+import Test.Tasty.HUnit (testCase, assertFailure)++import Data.Aeson++assertDecodeFailure :: Either String Value -> IO ()+assertDecodeFailure (Right v) = assertFailure $ "Unexpected success: " ++ show v+assertDecodeFailure (Left _)  = return ()++issue1138 :: TestTree+issue1138 = testGroup "Issue #1138" $ map (testCase "-")+  [ assertDecodeFailure $ eitherDecode "\"\t\""+  , assertDecodeFailure $ eitherDecode "\"\\\\\t\""++  , assertDecodeFailure $ eitherDecodeStrict "\"\t\""+  , assertDecodeFailure $ eitherDecodeStrict "\"\\\\\t\""++  , assertDecodeFailure $ eitherDecodeStrictText "\"\t\""+  , assertDecodeFailure $ eitherDecodeStrictText "\"\\\\\t\""+  ]
tests/Types.hs view
@@ -41,32 +41,32 @@     -- This definition causes an infinite loop in genericTo and genericFrom!     -- , fooMap :: Map.Map String Foo     , fooMap :: Map.Map String (Text,Int)-    } deriving (Show, Typeable, Data)+    } deriving (Show, Data)  data UFoo = UFoo {       _UFooInt :: Int     , uFooInt :: Int-    } deriving (Show, Eq, Data, Typeable)+    } deriving (Show, Eq, Data)  data NoConstructors  data OneConstructor = OneConstructor-                      deriving (Show, Eq, Typeable, Data)+                      deriving (Show, Eq, Data)  data Product2 a b = Product2 a b-                    deriving (Show, Eq, Typeable, Data)+                    deriving (Show, Eq, Data)  data Product6 a b c d e f = Product6 a b c d e f-                    deriving (Show, Eq, Typeable, Data)+                    deriving (Show, Eq, Data)  data Sum4 a b c d = Alt1 a | Alt2 b | Alt3 c | Alt4 d-                    deriving (Show, Eq, Typeable, Data)+                    deriving (Show, Eq, Data)  class ApproxEq a where     (=~) :: a -> a -> Bool  newtype Approx a = Approx { fromApprox :: a }-    deriving (Show, Data, Typeable, ApproxEq, Num)+    deriving (Show, Data, ApproxEq, Num)  instance (ApproxEq a) => Eq (Approx a) where     Approx a == Approx b = a =~ b@@ -93,7 +93,6 @@  data GADT a where     GADT :: { gadt :: String } -> GADT String-  deriving Typeable  deriving instance Data (GADT String) deriving instance Eq   (GADT a)
tests/UnitTests.hs view
@@ -38,6 +38,7 @@   , Value(..), camelTo, camelTo2   , defaultOptions, formatPath, formatRelativePath, omitNothingFields, parse) import Data.Char (toUpper, GeneralCategory(Control,Surrogate), generalCategory)+import Data.Fixed (Nano) import Data.HashMap.Strict (HashMap) import Data.Kind (Type) import Data.List (isSuffixOf)@@ -64,6 +65,7 @@ import Regression.Issue571 import Regression.Issue687 import Regression.Issue967+import Regression.Issue1138 import UnitTests.OmitNothingFieldsNote import UnitTests.FromJSONKey import UnitTests.Hashable@@ -86,7 +88,8 @@   _    -> s -- shouldn't happen?   where     split c' s' = map L.unpack $ L.split c' $ L.pack s'-    capitalize t = toUpper (head t) : tail t+    capitalize []     = []+    capitalize (x:xs) = toUpper x : xs   data Wibble = Wibble {@@ -457,17 +460,22 @@     (eitherDecode "1.37" :: Either String Rational)  bigRationalDecoding :: Assertion-bigRationalDecoding =-  assertEqual "Decoding an Integer with a large exponent should fail"-    (Left "Error in $: parsing Ratio failed, found a number with exponent 2000, but it must not be greater than 1024 or less than -1024")+bigRationalDecoding = do+  assertEqual "Decoding a Rational with a large exponent should fail"+    (Left "Error in $: parsing Ratio failed, found a number with exponent 2000, but it must not be greater than 1024")     ((eitherDecode :: L.ByteString -> Either String Rational) "1e2000")--smallRationalDecoding :: Assertion-smallRationalDecoding =-  assertEqual "Decoding an Integer with a large exponent should fail"-    (Left "Error in $: parsing Ratio failed, found a number with exponent -2000, but it must not be greater than 1024 or less than -1024")+  assertEqual "Decoding a Rational with a small exponent should fail"+    (Left "Error in $: parsing Ratio failed, found a number with exponent -2000, but it must not be less than -1024")     ((eitherDecode :: L.ByteString -> Either String Rational) "1e-2000") +bigFixedDecoding :: Assertion+bigFixedDecoding = do+  assertEqual "Decoding a Fixed with a large exponent should fail"+    (Left "Error in $: parsing Fixed failed, found a number with exponent 9999, but it must not be greater than 1024")+    ((eitherDecode :: L.ByteString -> Either String Nano) "1e9999")+  assertEqual "Decoding a Fixed with a small exponent should fail"+    (Left "Error in $: parsing Fixed failed, found a number with exponent -9999, but it must not be less than -1024")+    ((eitherDecode :: L.ByteString -> Either String Nano) "1e-9999")  bigScientificExponent :: Assertion bigScientificExponent =@@ -554,7 +562,7 @@   , testCase "Ratio with denominator 0" ratioDenominator0   , testCase "Rational parses number"   rationalNumber   , testCase "Big rational"             bigRationalDecoding-  , testCase "Small rational"           smallRationalDecoding+  , testCase "Big fixed"                bigFixedDecoding   , testCase "Big scientific exponent" bigScientificExponent   , testCase "Big integer decoding" bigIntegerDecoding   , testCase "Big natural decoding" bigNaturalDecoding@@ -568,6 +576,7 @@   , issue571   , issue687   , issue967+  , issue1138   , keyMapInsertWithTests   , omitNothingFieldsNoteTests   , noThunksTests