App2015
App2015

Reputation: 993

json to object and object to json

In context of this tutorial on F# snippets http://www.fssnip.net/1l/title/Convert-an-object-to-json-and-json-to-object

Let's say a Person type

type Person = {
    entityName: string; 
    entityType: string; 
}

and the code to call the web service and convert into json.

let internal json<'t> (myObj:'t) =   
    use ms = new MemoryStream() 
    (new DataContractJsonSerializer(typeof<'t>)).WriteObject(ms, myObj) 
    Encoding.Default.GetString(ms.ToArray()) 

let internal unjson<'t> (jsonString:string)  : 't =  
    use ms = new MemoryStream(ASCIIEncoding.Default.GetBytes(jsonString)) 
    let obj = (new DataContractJsonSerializer(typeof<'t>)).ReadObject(ms) 
    obj :?> 't

let requestToken (): Token =        
    let url = "http://example.com"

    let request = WebRequest.Create(url) :?> HttpWebRequest
    request.Method <- "POST"
    request.Accept <- "application/json;charset=UTF-8"

    let response = request.GetResponse() :?> HttpWebResponse
    use reader = new StreamReader(response.GetResponseStream())

    let body = reader.ReadToEnd()
    Console.WriteLine body // result OK
    let result = unjson<Person> body

JSON

{
    "entityName": "john doe",
    "entityType": "client"
}

Error

System.Runtime.Serialization.SerializationException: The data contract type 'Person' cannot be deserialized because the required data members 'entityName@, entityType@' were not found.

  1. if someone can add an example on how to call 'json' function passing result object to convert the object back into the JSON string

  2. Is the Person type required to have all fields as per JSON schema or can I choose to leave out non-required fields?

Upvotes: 1

Views: 721

Answers (1)

s952163
s952163

Reputation: 6324

This will serialize your record to JSON using the DataContractSerializer. You need to add some attributes for this to work.

#r "System.Runtime.Serialization" 
open System.IO
open System.Runtime.Serialization.Json
open System.Runtime.Serialization

[<DataContract>]
[<CLIMutable>]
type Person = {
    [<DataMember(Name="Name") >]
    entityName: string 
    [<DataMember(Name="Type") >]
    entityType: string 
}

let person = {entityName = "ENTITY"; entityType ="TYPE"}


let  toJson<'t> (myObj:'t) =   
    let fs = new FileStream(@"C:\tmp\test.json",FileMode.Create)
    (new DataContractJsonSerializer(typeof<'t>)).WriteObject(fs,myObj)

toJson<Person> person

And this is the output I get in the test.json file:

{"Name":"ENTITY","Type":"TYPE"}

Upvotes: 1

Related Questions