@@ -107,8 +107,6 @@ import qualified Data.Set as Set
107107import qualified Data.Text as T
108108import qualified Data.Text.Encoding as T
109109import qualified Data.Text.Lazy as LT
110−import qualified Data.Text.Lazy.Builder as LTB
111−import qualified Data.Text.Lazy.Builder.Int as LTBI
112110import qualified Data.Tree as Tree
113111import qualified Data.Vector as V
114112import qualified Data.Vector.Generic as VG
@@ -134,12 +132,6 @@ realFloatToJSON d
134132 | otherwise = Number $ Scientific.fromFloatDigits d
135133{-# INLINE realFloatToJSON #-}
136134
137−realFloatToEncoding :: RealFloat a => a -> Encoding
138−realFloatToEncoding d
139− | isNaN d || isInfinite d = Encoding EB.null_
140− | otherwise = toEncoding (Scientific.fromFloatDigits d)
141−{-# INLINE realFloatToEncoding #-}
142−
143135-------------------------------------------------------------------------------
144136-- Generics
145137-------------------------------------------------------------------------------
@@ -1139,9 +1131,15 @@ instance ToJSON Bool where
11391131 toJSON = Bool
11401132 {-# INLINE toJSON #-}
11411133
1142− toEncoding = Encoding . EB.bool
1134+ toEncoding = E.bool
11431135 {-# INLINE toEncoding #-}
11441136
1137+instance ToJSONKey Bool where
1138+ toJSONKey = ToJSONKeyText
1139+ ( (\x -> if x then "true" else "false")
1140+ , (\x -> toEncoding $ if x then ("true" :: Text) else "false")
1141+ )
1142+
11451143
11461144instance ToJSON Ordering where
11471145 toJSON = toJSON . orderingToText
@@ -1179,9 +1177,13 @@ instance ToJSON Double where
11791177 toJSON = realFloatToJSON
11801178 {-# INLINE toJSON #-}
11811179
1182− toEncoding = realFloatToEncoding
1180+ toEncoding = E.double
11831181 {-# INLINE toEncoding #-}
11841182
1183+instance ToJSONKey Double where
1184+ toJSONKey = toJSONKeyTextEnc E.doubleText
1185+ {-# INLINE toJSONKey #-}
1186+
11851187
11861188instance ToJSON Number where
11871189 toJSON (D d) = toJSON d
@@ -1197,20 +1199,23 @@ instance ToJSON Float where
11971199 toJSON = realFloatToJSON
11981200 {-# INLINE toJSON #-}
11991201
1200− toEncoding = realFloatToEncoding
1202+ toEncoding = E.float
12011203 {-# INLINE toEncoding #-}
12021204
1205+instance ToJSONKey Float where
1206+ toJSONKey = toJSONKeyTextEnc E.floatText
1207+ {-# INLINE toJSONKey #-}
1208+
12031209
1204−instance ToJSON (Ratio Integer) where
1210+instance (ToJSON a, Integral a) => ToJSON (Ratio a) where
12051211 toJSON r = object [ "numerator" .= numerator r
12061212 , "denominator" .= denominator r
12071213 ]
12081214 {-# INLINE toJSON #-}
12091215
1210− toEncoding r = Encoding $
1211− B.shortByteString "{\"numerator\":" <> builder (numerator r) <>
1212− B.shortByteString ",\"denominator\":" <> builder (denominator r) <>
1213− B.char7 '}'
1216+ toEncoding r = E.pairs $
1217+ "numerator" .= numerator r <>
1218+ "denominator" .= denominator r
12141219 {-# INLINE toEncoding #-}
12151220
12161221
@@ -1218,24 +1223,37 @@ instance HasResolution a => ToJSON (Fixed a) where
12181223 toJSON = Number . realToFrac
12191224 {-# INLINE toJSON #-}
12201225
1221− toEncoding = Encoding . EB.number . realToFrac
1226+ toEncoding = E.scientific . realToFrac
12221227 {-# INLINE toEncoding #-}
12231228
1229+instance HasResolution a => ToJSONKey (Fixed a) where
1230+ toJSONKey = toJSONKeyTextEnc (E.scientificText . realToFrac)
1231+ {-# INLINE toJSONKey #-}
1232+
12241233
12251234instance ToJSON Int where
12261235 toJSON = Number . fromIntegral
12271236 {-# INLINE toJSON #-}
12281237
1229− toEncoding = Encoding . B.intDec
1238+ toEncoding = E.int
12301239 {-# INLINE toEncoding #-}
12311240
1241+instance ToJSONKey Int where
1242+ toJSONKey = toJSONKeyTextEnc E.intText
1243+ {-# INLINE toJSONKey #-}
1244+
1245+
12321246instance ToJSON Integer where
12331247 toJSON = Number . fromInteger
12341248 {-# INLINE toJSON #-}
12351249
1236− toEncoding = Encoding . B.integerDec
1250+ toEncoding = E.integer
12371251 {-# INLINE toEncoding #-}
12381252
1253+instance ToJSONKey Integer where
1254+ toJSONKey = toJSONKeyTextEnc E.integerText
1255+ {-# INLINE toJSONKey #-}
1256+
12391257
12401258instance ToJSON Natural where
12411259 toJSON = toJSON . toInteger
@@ -1244,84 +1262,130 @@ instance ToJSON Natural where
12441262 toEncoding = toEncoding . toInteger
12451263 {-# INLINE toEncoding #-}
12461264
1265+instance ToJSONKey Natural where
1266+ toJSONKey = toJSONKeyTextEnc (E.integerText . toInteger)
1267+ {-# INLINE toJSONKey #-}
1268+
12471269
12481270instance ToJSON Int8 where
12491271 toJSON = Number . fromIntegral
12501272 {-# INLINE toJSON #-}
12511273
1252− toEncoding = Encoding . B.int8Dec
1274+ toEncoding = E.int8
12531275 {-# INLINE toEncoding #-}
12541276
1277+instance ToJSONKey Int8 where
1278+ toJSONKey = toJSONKeyTextEnc E.int8Text
1279+ {-# INLINE toJSONKey #-}
1280+
12551281
12561282instance ToJSON Int16 where
12571283 toJSON = Number . fromIntegral
12581284 {-# INLINE toJSON #-}
12591285
1260− toEncoding = Encoding . B.int16Dec
1286+ toEncoding = E.int16
12611287 {-# INLINE toEncoding #-}
12621288
1289+instance ToJSONKey Int16 where
1290+ toJSONKey = toJSONKeyTextEnc E.int16Text
1291+ {-# INLINE toJSONKey #-}
1292+
12631293
12641294instance ToJSON Int32 where
12651295 toJSON = Number . fromIntegral
12661296 {-# INLINE toJSON #-}
12671297
1268− toEncoding = Encoding . B.int32Dec
1298+ toEncoding = E.int32
12691299 {-# INLINE toEncoding #-}
12701300
1301+instance ToJSONKey Int32 where
1302+ toJSONKey = toJSONKeyTextEnc E.int32Text
1303+ {-# INLINE toJSONKey #-}
1304+
12711305
12721306instance ToJSON Int64 where
12731307 toJSON = Number . fromIntegral
12741308 {-# INLINE toJSON #-}
12751309
1276− toEncoding = Encoding . B.int64Dec
1310+ toEncoding = E.int64
12771311 {-# INLINE toEncoding #-}
12781312
1313+instance ToJSONKey Int64 where
1314+ toJSONKey = toJSONKeyTextEnc E.int64Text
1315+ {-# INLINE toJSONKey #-}
1316+
12791317
12801318instance ToJSON Word where
12811319 toJSON = Number . fromIntegral
12821320 {-# INLINE toJSON #-}
12831321
1284− toEncoding = Encoding . B.wordDec
1322+ toEncoding = E.word
12851323 {-# INLINE toEncoding #-}
12861324
1325+instance ToJSONKey Word where
1326+ toJSONKey = toJSONKeyTextEnc E.wordText
1327+ {-# INLINE toJSONKey #-}
1328+
12871329
12881330instance ToJSON Word8 where
12891331 toJSON = Number . fromIntegral
12901332 {-# INLINE toJSON #-}
12911333
1292− toEncoding = Encoding . B.word8Dec
1334+ toEncoding = E.word8
12931335 {-# INLINE toEncoding #-}
12941336
1337+instance ToJSONKey Word8 where
1338+ toJSONKey = toJSONKeyTextEnc E.word8Text
1339+ {-# INLINE toJSONKey #-}
1340+
12951341
12961342instance ToJSON Word16 where
12971343 toJSON = Number . fromIntegral
12981344 {-# INLINE toJSON #-}
12991345
1300− toEncoding = Encoding . B.word16Dec
1346+ toEncoding = E.word16
13011347 {-# INLINE toEncoding #-}
13021348
1349+instance ToJSONKey Word16 where
1350+ toJSONKey = toJSONKeyTextEnc E.word16Text
1351+ {-# INLINE toJSONKey #-}
1352+
13031353
13041354instance ToJSON Word32 where
13051355 toJSON = Number . fromIntegral
13061356 {-# INLINE toJSON #-}
13071357
1308− toEncoding = Encoding . B.word32Dec
1358+ toEncoding = E.word32
13091359 {-# INLINE toEncoding #-}
13101360
1361+instance ToJSONKey Word32 where
1362+ toJSONKey = toJSONKeyTextEnc E.word32Text
1363+ {-# INLINE toJSONKey #-}
1364+
1365+
13111366instance ToJSON Word64 where
13121367 toJSON = Number . fromIntegral
13131368 {-# INLINE toJSON #-}
13141369
1315− toEncoding = Encoding . B.word64Dec
1370+ toEncoding = E.word64
13161371 {-# INLINE toEncoding #-}
13171372
1373+instance ToJSONKey Word64 where
1374+ toJSONKey = toJSONKeyTextEnc E.word64Text
1375+ {-# INLINE toJSONKey #-}
1376+
1377+
13181378instance ToJSON Text where
13191379 toJSON = String
13201380 {-# INLINE toJSON #-}
13211381
1322− toEncoding = Encoding . EB.text
1382+ toEncoding = E.text
13231383 {-# INLINE toEncoding #-}
13241384
1385+instance ToJSONKey Text where
1386+ toJSONKey = ToJSONKeyText (id, toEncoding)
1387+ {-# INLINE toJSONKey #-}
1388+
13251389instance ToJSON LT.Text where
13261390 toJSON = String . LT.toStrict
13271391 {-# INLINE toJSON #-}
@@ -1365,9 +1429,12 @@ instance ToJSON Scientific where
13651429 toJSON = Number
13661430 {-# INLINE toJSON #-}
13671431
1368− toEncoding = Encoding . EB.number
1432+ toEncoding = E.scientific
13691433 {-# INLINE toEncoding #-}
13701434
1435+instance ToJSONKey Scientific where
1436+ toJSONKey = toJSONKeyTextEnc E.scientificText
1437+
13711438-------------------------------------------------------------------------------
13721439-- DList
13731440-------------------------------------------------------------------------------
@@ -1669,7 +1736,7 @@ instance ToJSON NominalDiffTime where
16691736 toJSON = Number . realToFrac
16701737 {-# INLINE toJSON #-}
16711738
1672− toEncoding = Encoding . EB.number . realToFrac
1739+ toEncoding = Encoding . EB.scientific . realToFrac
16731740 {-# INLINE toEncoding #-}
16741741
16751742-------------------------------------------------------------------------------
@@ -1755,21 +1822,14 @@ instance ToJSONKey b => ToJSONKey (Tagged a b) where
17551822-- Instances for converting t map keys
17561823-------------------------------------------------------------------------------
17571824
1758−instance ToJSONKey Text where
1759− toJSONKey = ToJSONKeyText (id,toEncoding)
1760−
1761−
1762−instance ToJSONKey Bool where
1763− toJSONKey = ToJSONKeyText
1764− ( (\x -> if x then "true" else "false")
1765− , (\x -> Encoding $ if x then "\"true\"" else "\"false\"")
1766− )
1767−
1768−instance ToJSONKey Int where
1769− toJSONKey = ToJSONKeyText
1770− ( LT.toStrict . LTB.toLazyText . LTBI.decimal
1771− , \x -> Encoding $ B.char7 '"' <> fromEncoding (toEncoding x) <> B.char7 '"'
1772− )
1825+-- | TODO: Move ToJSONKEyFunction to .Types(.Internal),
1826+-- export and document this function from there
1827+toJSONKeyTextEnc :: (a -> Encoding) -> ToJSONKeyFunction a
1828+toJSONKeyTextEnc e = ToJSONKeyText
1829+ -- TODO: dropAround is also used in stringEncoding, which is unfortunate atm
1830+ ( T.dropAround (== '"') . T.decodeLatin1 . L.toStrict . B.toLazyByteString . fromEncoding . e
1831+ , e
1832+ )
17731833
17741834instance (ToJSON a, ToJSON b) => ToJSONKey (a,b)
17751835instance (ToJSON a, ToJSON b, ToJSON c) => ToJSONKey (a,b,c)