You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@shindig.apache.org by John Hjelmstad <fa...@google.com> on 2008/10/16 01:24:45 UTC

Re: default_value not working

Resuscitating this thread, as I'd like to post a patch.
While I understand that it's error-prone to merge in two places, I'm not
sure we have a choice here. Prefs passed on the fragment are by definition
not available to the server, so can't participate in a server-side merge.
 Passing all prefs on the query string obviously kills caching. I see two
options:

1. We could require that anybody who generates rendering URLs manually put
all userprefs on the query string. This allows all prefs merging to happen
in-server, but is inconsistent with prefs on the fragment. That in turn has
client implications, since a container "properly" rendering a gadget would
have to include all userprefs at all times in its URL (pre-merged). True,
that happens with the Java impl today, but it's another somewhat painful
burden. Also, implementation of this mechanism will still need temporarily
to have JS and server-merges, since the JS is shared.
2. Deal with two merges, which is inevitable for a time anyway.

I'll implement the first piece of this (server merge and output, in Java)
and visit the remainder thereafter.

John

2008/9/12 John Hjelmstad <fa...@google.com>

> That's fair. So long as prefs.js doesn't parse the URL but instead accepts
> only the prefs values the server provides, we're golden.
>
>
> 2008/9/12 Kevin Brown <et...@google.com>
>
>> 2008/9/12 John Hjelmstad <fa...@google.com>
>>
>> > I could be misunderstanding, but it sounds like that's what Ben did --
>> pass
>> > (in the server) the defaults to setMessages_ with some special format,
>> and
>> > have prefs.js read them when no up_<key> values are provided on the URL.
>> > Meanwhile, UP substitution is already handled by the server, with a
>> merge
>> > algorithm that presumably mirrors what Ben's does in JS.
>>
>>
>> Yeah, and I think that's error prone. We should be doing the merging in
>> just
>> one place, or we're going to have bugs.
>>
>>
>> >
>> >
>> > -John
>> >
>> > 2008/9/12 Kevin Brown <et...@google.com>
>> >
>> > > That's not a complete solution because it skips user pref
>> substitution.
>> > The
>> > > only thing that completely allows skipping filling in the user pref
>> > > defaults
>> > > in the url is to make the user prefs merge happen server side.
>> > >
>> > > 2008/9/11 ben bonfil <bo...@gmail.com>
>> > >
>> > > > My solution was indeed to pass the default values in the
>> setMessages_
>> > > > array(like iGoogle), and modify prefs.js accordingly.
>> > > > ‎
>> > > > Ben Bonfil
>> > > >
>> > > > On 9/12/08, John Hjelmstad <fa...@google.com> wrote:
>> > > > > Correct me if I'm wrong, but the only server-side code that
>> touches
>> > > > > gadgets.Prefs initializes it with Messages (setMessages_), not
>> Prefs
>> > at
>> > > > all,
>> > > > > all of which are initialized by parsing
>> > > gadgets.util.getUrlParameters().
>> > > > >
>> > > > > I don't have any strong opinion on implementation particulars -
>> > either
>> > > > way
>> > > > > server-side code spits out defaults and some corresponding JS
>> reads
>> > > > them...
>> > > > > assuming we want to support this in the first place.
>> > > > >
>> > > > > -John
>> > > > >
>> > > > > On 9/11/08, Kevin Brown <et...@google.com> wrote:
>> > > > >>
>> > > > >> That's wholly unnecessary. If we want gadgets.Prefs to include
>> > > defaults,
>> > > > >> we
>> > > > >> just need to make the server side code that outputs gadgets.Prefs
>> > > > properly
>> > > > >> merge in the defaults from the spec. There's no reason to add new
>> > > client
>> > > > >> libraries.
>> > > > >>
>> > > > >>
>> > > > >> On Thu, Sep 11, 2008 at 3:01 PM, John Hjelmstad <
>> fargo@google.com>
>> > > > wrote:
>> > > > >>
>> > > > >> > Given that default values for a given gadget fixed in the spec,
>> I
>> > > > think
>> > > > >> the
>> > > > >> > cleaner solution is to inject some kind of defaultPrefs object
>> > into
>> > > > the
>> > > > >> > gadget when rendering it, somewhat like gadgets.config.init()
>> > does.
>> > > > >> >
>> > > > >> > As implemented today (which admittedly isn't the cleanest impl,
>> > but
>> > > > >> that's
>> > > > >> > an orthogonal problem), that would mean modifying
>> > > GadgetRenderingTask
>> > > > to
>> > > > >> do
>> > > > >> > something like:
>> > > > >> >
>> > > > >> >
>> > > > >>
>> > > >
>> > >
>> >
>> js.append("gadgets.Prefs.setDefaults(").append(jsonObjectRepresentingDefaultsOf(gadget.getSpec()).append(");\n");
>> > > > >> >
>> > > > >> > ...then augmenting features/core/prefs.js correspondingly to
>> > > > initialize
>> > > > >> > from
>> > > > >> > defaults when the up_<key> equivalent isn't available.
>> > > > >> >
>> > > > >> > --John
>> > > > >> >
>> > > > >> > On 9/10/08, Cassie <do...@apache.org> wrote:
>> > > > >> > >
>> > > > >> > > (in case you are interested - don't feel pressured though :)
>> > > > >> > >
>> > > > >> > > samplecontainer.js actually already makes calls to the
>> metadata
>> > > > >> servlet.
>> > > > >> > > see
>> > > > >> > > line 167 - the "requestGadgetMetaData" function. This came
>> from
>> > a
>> > > > >> > different
>> > > > >> > > patch which gave the samplecontainer the ability to show
>> gadget
>> > > > >> > > titles.
>> > > > >> > >
>> > > > >> > > - Caszsie
>> > > > >> > >
>> > > > >> > >
>> > > > >> > >
>> > > > >> > > On Wed, Sep 10, 2008 at 6:48 AM, Tamlyn Rhodes <
>> > tamlyn@tamlyn.org
>> > > >
>> > > > >> > wrote:
>> > > > >> > >
>> > > > >> > > > On Tue, Sep 9, 2008 at 6:55 PM, Cassie <do...@apache.org>
>> > wrote:
>> > > > >> > > > > Hey Tamlyn - do you think you could make this into a
>> patch
>> > and
>> > > > >> attach
>> > > > >> > > it
>> > > > >> > > > to
>> > > > >> > > > > a jira issue for Shindig?
>> > > > >> > > >
>> > > > >> > > > The thing is I've done it from outside of gadgets.js so
>> it's
>> > not
>> > > > >> > > > really patchable. Doing it in gadgets.js would mean making
>> an
>> > > ajax
>> > > > >> > > > call to fetch the metadata in the
>> gadgets.container.addGadget
>> > > > method
>> > > > >> > > > and I'm not really sure how that would work since
>> > > gadgets.ioisn't
>> > > > >> > > > available in the container (unless i've misunderstood).
>> > > > >> > > >
>> > > > >> > > > I'm aware that you're keen to maintain clear separation
>> > between
>> > > > >> > > > Shindig and the JavaScript code that manages the
>> layout/chrome
>> > > but
>> > > > >> for
>> > > > >> > > > most people actually using Shindig I suspect this
>> separation
>> > is
>> > > > >> rather
>> > > > >> > > > more theoretical than practical. I've been developing a
>> drag &
>> > > > drop
>> > > > >> > > > layout/framework using jQuery, PHP and MySQL and I hope to
>> > open
>> > > > >> source
>> > > > >> > > > this once I get it working. This should be some time in
>> > > September.
>> > > > >> > > >
>> > > > >> > > >  Tamlyn.
>> > > > >> > > >
>> > > > >> > >
>> > > > >> >
>> > > > >>
>> > > > >
>> > > >
>> > >
>> >
>>
>
>

Re: default_value not working

Posted by John Hjelmstad <fa...@google.com>.
SGTM, code 75% written. Patch soon, applied to SHINDIG-175.

2008/10/15 Kevin Brown <et...@google.com>

> 2008/10/15 John Hjelmstad <fa...@google.com>
>
> > Resuscitating this thread, as I'd like to post a patch.
> > While I understand that it's error-prone to merge in two places, I'm not
> > sure we have a choice here. Prefs passed on the fragment are by
> definition
> > not available to the server, so can't participate in a server-side merge.
> >  Passing all prefs on the query string obviously kills caching. I see two
> > options:
> >
> > 1. We could require that anybody who generates rendering URLs manually
> put
> > all userprefs on the query string. This allows all prefs merging to
> happen
> > in-server, but is inconsistent with prefs on the fragment. That in turn
> has
> > client implications, since a container "properly" rendering a gadget
> would
> > have to include all userprefs at all times in its URL (pre-merged). True,
> > that happens with the Java impl today, but it's another somewhat painful
> > burden. Also, implementation of this mechanism will still need
> temporarily
> > to have JS and server-merges, since the JS is shared.
> > 2. Deal with two merges, which is inevitable for a time anyway.
>
>
> All you need to do is make RenderingContentRewriter add the calls to set
> the
> prefs. The client code may wind up doing an overwrite, but that's
> acceptable.
>
>
> >
> > I'll implement the first piece of this (server merge and output, in Java)
> > and visit the remainder thereafter.
> >
> > John
> >
> > 2008/9/12 John Hjelmstad <fa...@google.com>
> >
> > > That's fair. So long as prefs.js doesn't parse the URL but instead
> > accepts
> > > only the prefs values the server provides, we're golden.
> > >
> > >
> > > 2008/9/12 Kevin Brown <et...@google.com>
> > >
> > >> 2008/9/12 John Hjelmstad <fa...@google.com>
> > >>
> > >> > I could be misunderstanding, but it sounds like that's what Ben did
> --
> > >> pass
> > >> > (in the server) the defaults to setMessages_ with some special
> format,
> > >> and
> > >> > have prefs.js read them when no up_<key> values are provided on the
> > URL.
> > >> > Meanwhile, UP substitution is already handled by the server, with a
> > >> merge
> > >> > algorithm that presumably mirrors what Ben's does in JS.
> > >>
> > >>
> > >> Yeah, and I think that's error prone. We should be doing the merging
> in
> > >> just
> > >> one place, or we're going to have bugs.
> > >>
> > >>
> > >> >
> > >> >
> > >> > -John
> > >> >
> > >> > 2008/9/12 Kevin Brown <et...@google.com>
> > >> >
> > >> > > That's not a complete solution because it skips user pref
> > >> substitution.
> > >> > The
> > >> > > only thing that completely allows skipping filling in the user
> pref
> > >> > > defaults
> > >> > > in the url is to make the user prefs merge happen server side.
> > >> > >
> > >> > > 2008/9/11 ben bonfil <bo...@gmail.com>
> > >> > >
> > >> > > > My solution was indeed to pass the default values in the
> > >> setMessages_
> > >> > > > array(like iGoogle), and modify prefs.js accordingly.
> > >> > > > ‎
> > >> > > > Ben Bonfil
> > >> > > >
> > >> > > > On 9/12/08, John Hjelmstad <fa...@google.com> wrote:
> > >> > > > > Correct me if I'm wrong, but the only server-side code that
> > >> touches
> > >> > > > > gadgets.Prefs initializes it with Messages (setMessages_), not
> > >> Prefs
> > >> > at
> > >> > > > all,
> > >> > > > > all of which are initialized by parsing
> > >> > > gadgets.util.getUrlParameters().
> > >> > > > >
> > >> > > > > I don't have any strong opinion on implementation particulars
> -
> > >> > either
> > >> > > > way
> > >> > > > > server-side code spits out defaults and some corresponding JS
> > >> reads
> > >> > > > them...
> > >> > > > > assuming we want to support this in the first place.
> > >> > > > >
> > >> > > > > -John
> > >> > > > >
> > >> > > > > On 9/11/08, Kevin Brown <et...@google.com> wrote:
> > >> > > > >>
> > >> > > > >> That's wholly unnecessary. If we want gadgets.Prefs to
> include
> > >> > > defaults,
> > >> > > > >> we
> > >> > > > >> just need to make the server side code that outputs
> > gadgets.Prefs
> > >> > > > properly
> > >> > > > >> merge in the defaults from the spec. There's no reason to add
> > new
> > >> > > client
> > >> > > > >> libraries.
> > >> > > > >>
> > >> > > > >>
> > >> > > > >> On Thu, Sep 11, 2008 at 3:01 PM, John Hjelmstad <
> > >> fargo@google.com>
> > >> > > > wrote:
> > >> > > > >>
> > >> > > > >> > Given that default values for a given gadget fixed in the
> > spec,
> > >> I
> > >> > > > think
> > >> > > > >> the
> > >> > > > >> > cleaner solution is to inject some kind of defaultPrefs
> > object
> > >> > into
> > >> > > > the
> > >> > > > >> > gadget when rendering it, somewhat like
> gadgets.config.init()
> > >> > does.
> > >> > > > >> >
> > >> > > > >> > As implemented today (which admittedly isn't the cleanest
> > impl,
> > >> > but
> > >> > > > >> that's
> > >> > > > >> > an orthogonal problem), that would mean modifying
> > >> > > GadgetRenderingTask
> > >> > > > to
> > >> > > > >> do
> > >> > > > >> > something like:
> > >> > > > >> >
> > >> > > > >> >
> > >> > > > >>
> > >> > > >
> > >> > >
> > >> >
> > >>
> >
> js.append("gadgets.Prefs.setDefaults(").append(jsonObjectRepresentingDefaultsOf(gadget.getSpec()).append(");\n");
> > >> > > > >> >
> > >> > > > >> > ...then augmenting features/core/prefs.js correspondingly
> to
> > >> > > > initialize
> > >> > > > >> > from
> > >> > > > >> > defaults when the up_<key> equivalent isn't available.
> > >> > > > >> >
> > >> > > > >> > --John
> > >> > > > >> >
> > >> > > > >> > On 9/10/08, Cassie <do...@apache.org> wrote:
> > >> > > > >> > >
> > >> > > > >> > > (in case you are interested - don't feel pressured though
> > :)
> > >> > > > >> > >
> > >> > > > >> > > samplecontainer.js actually already makes calls to the
> > >> metadata
> > >> > > > >> servlet.
> > >> > > > >> > > see
> > >> > > > >> > > line 167 - the "requestGadgetMetaData" function. This
> came
> > >> from
> > >> > a
> > >> > > > >> > different
> > >> > > > >> > > patch which gave the samplecontainer the ability to show
> > >> gadget
> > >> > > > >> > > titles.
> > >> > > > >> > >
> > >> > > > >> > > - Caszsie
> > >> > > > >> > >
> > >> > > > >> > >
> > >> > > > >> > >
> > >> > > > >> > > On Wed, Sep 10, 2008 at 6:48 AM, Tamlyn Rhodes <
> > >> > tamlyn@tamlyn.org
> > >> > > >
> > >> > > > >> > wrote:
> > >> > > > >> > >
> > >> > > > >> > > > On Tue, Sep 9, 2008 at 6:55 PM, Cassie <
> doll@apache.org>
> > >> > wrote:
> > >> > > > >> > > > > Hey Tamlyn - do you think you could make this into a
> > >> patch
> > >> > and
> > >> > > > >> attach
> > >> > > > >> > > it
> > >> > > > >> > > > to
> > >> > > > >> > > > > a jira issue for Shindig?
> > >> > > > >> > > >
> > >> > > > >> > > > The thing is I've done it from outside of gadgets.js so
> > >> it's
> > >> > not
> > >> > > > >> > > > really patchable. Doing it in gadgets.js would mean
> > making
> > >> an
> > >> > > ajax
> > >> > > > >> > > > call to fetch the metadata in the
> > >> gadgets.container.addGadget
> > >> > > > method
> > >> > > > >> > > > and I'm not really sure how that would work since
> > >> > > gadgets.ioisn't
> > >> > > > >> > > > available in the container (unless i've misunderstood).
> > >> > > > >> > > >
> > >> > > > >> > > > I'm aware that you're keen to maintain clear separation
> > >> > between
> > >> > > > >> > > > Shindig and the JavaScript code that manages the
> > >> layout/chrome
> > >> > > but
> > >> > > > >> for
> > >> > > > >> > > > most people actually using Shindig I suspect this
> > >> separation
> > >> > is
> > >> > > > >> rather
> > >> > > > >> > > > more theoretical than practical. I've been developing a
> > >> drag &
> > >> > > > drop
> > >> > > > >> > > > layout/framework using jQuery, PHP and MySQL and I hope
> > to
> > >> > open
> > >> > > > >> source
> > >> > > > >> > > > this once I get it working. This should be some time in
> > >> > > September.
> > >> > > > >> > > >
> > >> > > > >> > > >  Tamlyn.
> > >> > > > >> > > >
> > >> > > > >> > >
> > >> > > > >> >
> > >> > > > >>
> > >> > > > >
> > >> > > >
> > >> > >
> > >> >
> > >>
> > >
> > >
> >
>

Re: default_value not working

Posted by Kevin Brown <et...@google.com>.
2008/10/15 John Hjelmstad <fa...@google.com>

> Resuscitating this thread, as I'd like to post a patch.
> While I understand that it's error-prone to merge in two places, I'm not
> sure we have a choice here. Prefs passed on the fragment are by definition
> not available to the server, so can't participate in a server-side merge.
>  Passing all prefs on the query string obviously kills caching. I see two
> options:
>
> 1. We could require that anybody who generates rendering URLs manually put
> all userprefs on the query string. This allows all prefs merging to happen
> in-server, but is inconsistent with prefs on the fragment. That in turn has
> client implications, since a container "properly" rendering a gadget would
> have to include all userprefs at all times in its URL (pre-merged). True,
> that happens with the Java impl today, but it's another somewhat painful
> burden. Also, implementation of this mechanism will still need temporarily
> to have JS and server-merges, since the JS is shared.
> 2. Deal with two merges, which is inevitable for a time anyway.


All you need to do is make RenderingContentRewriter add the calls to set the
prefs. The client code may wind up doing an overwrite, but that's
acceptable.


>
> I'll implement the first piece of this (server merge and output, in Java)
> and visit the remainder thereafter.
>
> John
>
> 2008/9/12 John Hjelmstad <fa...@google.com>
>
> > That's fair. So long as prefs.js doesn't parse the URL but instead
> accepts
> > only the prefs values the server provides, we're golden.
> >
> >
> > 2008/9/12 Kevin Brown <et...@google.com>
> >
> >> 2008/9/12 John Hjelmstad <fa...@google.com>
> >>
> >> > I could be misunderstanding, but it sounds like that's what Ben did --
> >> pass
> >> > (in the server) the defaults to setMessages_ with some special format,
> >> and
> >> > have prefs.js read them when no up_<key> values are provided on the
> URL.
> >> > Meanwhile, UP substitution is already handled by the server, with a
> >> merge
> >> > algorithm that presumably mirrors what Ben's does in JS.
> >>
> >>
> >> Yeah, and I think that's error prone. We should be doing the merging in
> >> just
> >> one place, or we're going to have bugs.
> >>
> >>
> >> >
> >> >
> >> > -John
> >> >
> >> > 2008/9/12 Kevin Brown <et...@google.com>
> >> >
> >> > > That's not a complete solution because it skips user pref
> >> substitution.
> >> > The
> >> > > only thing that completely allows skipping filling in the user pref
> >> > > defaults
> >> > > in the url is to make the user prefs merge happen server side.
> >> > >
> >> > > 2008/9/11 ben bonfil <bo...@gmail.com>
> >> > >
> >> > > > My solution was indeed to pass the default values in the
> >> setMessages_
> >> > > > array(like iGoogle), and modify prefs.js accordingly.
> >> > > > ‎
> >> > > > Ben Bonfil
> >> > > >
> >> > > > On 9/12/08, John Hjelmstad <fa...@google.com> wrote:
> >> > > > > Correct me if I'm wrong, but the only server-side code that
> >> touches
> >> > > > > gadgets.Prefs initializes it with Messages (setMessages_), not
> >> Prefs
> >> > at
> >> > > > all,
> >> > > > > all of which are initialized by parsing
> >> > > gadgets.util.getUrlParameters().
> >> > > > >
> >> > > > > I don't have any strong opinion on implementation particulars -
> >> > either
> >> > > > way
> >> > > > > server-side code spits out defaults and some corresponding JS
> >> reads
> >> > > > them...
> >> > > > > assuming we want to support this in the first place.
> >> > > > >
> >> > > > > -John
> >> > > > >
> >> > > > > On 9/11/08, Kevin Brown <et...@google.com> wrote:
> >> > > > >>
> >> > > > >> That's wholly unnecessary. If we want gadgets.Prefs to include
> >> > > defaults,
> >> > > > >> we
> >> > > > >> just need to make the server side code that outputs
> gadgets.Prefs
> >> > > > properly
> >> > > > >> merge in the defaults from the spec. There's no reason to add
> new
> >> > > client
> >> > > > >> libraries.
> >> > > > >>
> >> > > > >>
> >> > > > >> On Thu, Sep 11, 2008 at 3:01 PM, John Hjelmstad <
> >> fargo@google.com>
> >> > > > wrote:
> >> > > > >>
> >> > > > >> > Given that default values for a given gadget fixed in the
> spec,
> >> I
> >> > > > think
> >> > > > >> the
> >> > > > >> > cleaner solution is to inject some kind of defaultPrefs
> object
> >> > into
> >> > > > the
> >> > > > >> > gadget when rendering it, somewhat like gadgets.config.init()
> >> > does.
> >> > > > >> >
> >> > > > >> > As implemented today (which admittedly isn't the cleanest
> impl,
> >> > but
> >> > > > >> that's
> >> > > > >> > an orthogonal problem), that would mean modifying
> >> > > GadgetRenderingTask
> >> > > > to
> >> > > > >> do
> >> > > > >> > something like:
> >> > > > >> >
> >> > > > >> >
> >> > > > >>
> >> > > >
> >> > >
> >> >
> >>
> js.append("gadgets.Prefs.setDefaults(").append(jsonObjectRepresentingDefaultsOf(gadget.getSpec()).append(");\n");
> >> > > > >> >
> >> > > > >> > ...then augmenting features/core/prefs.js correspondingly to
> >> > > > initialize
> >> > > > >> > from
> >> > > > >> > defaults when the up_<key> equivalent isn't available.
> >> > > > >> >
> >> > > > >> > --John
> >> > > > >> >
> >> > > > >> > On 9/10/08, Cassie <do...@apache.org> wrote:
> >> > > > >> > >
> >> > > > >> > > (in case you are interested - don't feel pressured though
> :)
> >> > > > >> > >
> >> > > > >> > > samplecontainer.js actually already makes calls to the
> >> metadata
> >> > > > >> servlet.
> >> > > > >> > > see
> >> > > > >> > > line 167 - the "requestGadgetMetaData" function. This came
> >> from
> >> > a
> >> > > > >> > different
> >> > > > >> > > patch which gave the samplecontainer the ability to show
> >> gadget
> >> > > > >> > > titles.
> >> > > > >> > >
> >> > > > >> > > - Caszsie
> >> > > > >> > >
> >> > > > >> > >
> >> > > > >> > >
> >> > > > >> > > On Wed, Sep 10, 2008 at 6:48 AM, Tamlyn Rhodes <
> >> > tamlyn@tamlyn.org
> >> > > >
> >> > > > >> > wrote:
> >> > > > >> > >
> >> > > > >> > > > On Tue, Sep 9, 2008 at 6:55 PM, Cassie <do...@apache.org>
> >> > wrote:
> >> > > > >> > > > > Hey Tamlyn - do you think you could make this into a
> >> patch
> >> > and
> >> > > > >> attach
> >> > > > >> > > it
> >> > > > >> > > > to
> >> > > > >> > > > > a jira issue for Shindig?
> >> > > > >> > > >
> >> > > > >> > > > The thing is I've done it from outside of gadgets.js so
> >> it's
> >> > not
> >> > > > >> > > > really patchable. Doing it in gadgets.js would mean
> making
> >> an
> >> > > ajax
> >> > > > >> > > > call to fetch the metadata in the
> >> gadgets.container.addGadget
> >> > > > method
> >> > > > >> > > > and I'm not really sure how that would work since
> >> > > gadgets.ioisn't
> >> > > > >> > > > available in the container (unless i've misunderstood).
> >> > > > >> > > >
> >> > > > >> > > > I'm aware that you're keen to maintain clear separation
> >> > between
> >> > > > >> > > > Shindig and the JavaScript code that manages the
> >> layout/chrome
> >> > > but
> >> > > > >> for
> >> > > > >> > > > most people actually using Shindig I suspect this
> >> separation
> >> > is
> >> > > > >> rather
> >> > > > >> > > > more theoretical than practical. I've been developing a
> >> drag &
> >> > > > drop
> >> > > > >> > > > layout/framework using jQuery, PHP and MySQL and I hope
> to
> >> > open
> >> > > > >> source
> >> > > > >> > > > this once I get it working. This should be some time in
> >> > > September.
> >> > > > >> > > >
> >> > > > >> > > >  Tamlyn.
> >> > > > >> > > >
> >> > > > >> > >
> >> > > > >> >
> >> > > > >>
> >> > > > >
> >> > > >
> >> > >
> >> >
> >>
> >
> >
>