Hi Esteban,

I have been thinking about you ;-)

On 19 Mar 2013, at 15:26, Sven Van Caekenberghe <[email protected]> wrote:

> I think I understand what you want, and I know that you tried to explain the 
> model (or a minimal version of it), but if you are writing out JSON according 
> to some externally defined format (with the ideas and sharing), would it be 
> possible to give me the specification of that format ? Maybe off list ?

Without knowing exactly what your target is, it is hard for me, below is how I 
understand your problem and how I would solve it.

> In any case, I will think about the issue you raised.

There are book objects, with id, title and author. The first time you write 
them out, you write all the details. If you encounter the same book again in 
the same encoding session, you only write out the id.

To do this, you need a custom writer subclass that can keep track of books 
seen, in the scope of the encoding session (incidentally, this is how you would 
do a writer that knows when it goes into cycles - but again, this has all been 
done in STON).

Furthermore, to dynamically decide the encoding you have to overwrite 
#neoJsonOn: This is done here by delegating to the custom writer. There the 
decision is made to take the normal route (super) or to just write the id. The 
class side of book still have a normal mapping.

Of course, a production quality implementation will be some more work.

I hope that this is more or less what you were looking for. 

Regards,

Sven

----

TestCase subclass: #NeoJSONBookTests
        instanceVariableNames: ''
        classVariableNames: ''
        poolDictionaries: ''
        category: 'Neo-JSON-Example'!

!NeoJSONBookTests methodsFor: 'testing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:52'!
testMultiple
        | book1 book2 |
        (book1 := NeoJSONBook new)
                id: 'B101';
                title: 'The Hobbit';
                author: 'JJR Tolkien'.
        (book2 := NeoJSONBook new)
                id: 'B102';
                title: 'Lord Of The Rings';
                author: 'JJR Tolkien'.
        NeoJSONCustomWriter toString: { book1. book1. book2. book1. book2 }! !

!NeoJSONBookTests methodsFor: 'testing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:44'!
testOne
        | book |
        (book := NeoJSONBook new)
                id: 'B101';
                title: 'The Hobbit';
                author: 'JJR Tolkien'.
        NeoJSONCustomWriter toString: book.! !

Object subclass: #NeoJSONBook
        instanceVariableNames: 'id title author'
        classVariableNames: ''
        poolDictionaries: ''
        category: 'Neo-JSON-Example'!

!NeoJSONBook methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:35'!
author
        ^ author! !

!NeoJSONBook methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:35'!
author: anObject
        author := anObject! !

!NeoJSONBook methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:35'!
id
        ^ id! !

!NeoJSONBook methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:35'!
id: anObject
        id := anObject! !

!NeoJSONBook methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:39'!
neoJsonOn: neoJSONWriter 
        neoJSONWriter writeBook: self! !

!NeoJSONBook methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:35'!
title
        ^ title! !

!NeoJSONBook methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 3/24/2013 
17:35'!
title: anObject
        title := anObject! !

"-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- "!

NeoJSONBook class
        instanceVariableNames: ''!

!NeoJSONBook class methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 
3/24/2013 17:41'!
neoJsonMapping: mapper
        mapper mapAllInstVarsFor: self! !

NeoJSONWriter subclass: #NeoJSONCustomWriter
        instanceVariableNames: 'books'
        classVariableNames: ''
        poolDictionaries: ''
        category: 'Neo-JSON-Example'!

!NeoJSONCustomWriter methodsFor: 'initialize-release' stamp: 
'SvenVanCaekenberghe 3/24/2013 17:52'!
initialize
        super initialize.
        books := Set new! !


!NeoJSONCustomWriter methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 
3/24/2013 17:35'!
books
        ^ books! !

!NeoJSONCustomWriter methodsFor: 'accessing' stamp: 'SvenVanCaekenberghe 
3/24/2013 17:35'!
books: anObject
        books := anObject! !


!NeoJSONCustomWriter methodsFor: 'writing' stamp: 'SvenVanCaekenberghe 
3/24/2013 17:53'!
writeBook: aBook
        (self books includes: aBook id)
                ifTrue: [ 
                        self writeMapStreamingDo: [ :jsonMapWriter | 
                                jsonMapWriter writeKey: 'id' value: aBook id ] ]
                ifFalse: [ 
                        books add: aBook id.
                        super writeObject: aBook ]! !

----

Attachment: Neo-JSON-Example.st
Description: Binary data


--
Sven Van Caekenberghe
http://stfx.eu
Smalltalk is the Red Pill

Reply via email to