Ricerca…


Codifica e decodifica intelligenti con generici

Il modo più semplice e veloce per codificare un tipo di dati Haskell su JSON con Aeson è l'utilizzo di generici.

{-# LANGUAGE DeriveGeneric #-}

import GHC.Generics
import Data.Text
import Data.Aeson
import Data.ByteString.Lazy    

Per prima cosa creiamo un tipo di dati Persona:

data Person = Person { firstName :: Text
                     , lastName  :: Text
                     , age       :: Int 
                     } deriving (Show, Generic)

Per utilizzare la funzione di encode e decode dal pacchetto Data.Aeson , è necessario rendere a Person un'istanza di ToJSON e FromJSON . Dal momento che deriviamo Generic for Person , possiamo creare istanze vuote per queste classi. Le definizioni predefinite dei metodi sono definite in termini di metodi forniti dalla classe di tipi Generic .

instance ToJSON Person
instance FromJSON Person

Fatto! Per migliorare la velocità di codifica, possiamo modificare leggermente l'istanza ToJSON :

instance ToJSON Person where
    toEncoding = genericToEncoding defaultOptions

Ora possiamo usare la funzione di encode per convertire la Person in un Bytestring (pigro):

encodeNewPerson :: Text -> Text -> Int -> ByteString
encodeNewPerson first last age = encode $ Person first last age

E per decodificare possiamo semplicemente usare la decode :

> encodeNewPerson "Hans" "Wurst" 30
"{\"lastName\":\"Wurst\",\"age\":30,\"firstName\":\"Hans\"}"


> decode $ encodeNewPerson "Hans" "Wurst" 30
Just (Person {firstName = "Hans", lastName = "Wurst", age = 30})

Un modo rapido per generare un Data.Aeson.Value

{-# LANGUAGE OverloadedStrings #-}
module Main where

import Data.Aeson

main :: IO ()
main = do
  let example = Data.Aeson.object [ "key" .= (5 :: Integer), "somethingElse" .= (2 :: Integer) ] :: Value
  print . encode $ example

Campi opzionali

A volte, vogliamo che alcuni campi nella stringa JSON siano facoltativi. Per esempio,

data Person = Person { firstName :: Text
                     , lastName  :: Text
                     , age       :: Maybe Int 
                     }

Questo può essere raggiunto da

import Data.Aeson.TH

$(deriveJSON defaultOptions{omitNothingFields = True} ''Person)


Modified text is an extract of the original Stack Overflow Documentation
Autorizzato sotto CC BY-SA 3.0
Non affiliato con Stack Overflow