On Feb 26, 2:10 am, Ken Wesson <kwess...@gmail.com> wrote:
> Embedding literal functions in macros "sorta" works. It behaves
> glitchy sometimes, especially if the functions are closures.
>
> If your set of functions is not open-ended, I'd suggest simply
> defn'ing all of them at both client and server sides, sticking them in
> a map, and putting a keyword instead of an actual function object in
> your widget data. The keyword is used to look up the correct function
> at both ends. If any function is a closure over run-time-variable
> parameters, put the keyword and these parameters in the data, e.g.
>
> (server)
>
> (-> widget-data-map
>   (assoc :my-fun the-function-itself)
>   (assoc :my-fun-p1 42))
>
> ...
>
> (client)
>
> (let [f #((:my-fun widget-data-map) p1)]
>   ...)
>

Unfortunately, I'd like it to be a open set, just as I would like the
system's types to be - this was one of the choices driving Clojure
over Java as the implementation language.

I've given the macro route some more thought and realised that I am
also going to have to be very careful with namespaces when redefining
copies of functions in remote jvms...

I've also given a little thought towards using URLClassLoader and an
embedded http server to allow a client to transparently fetch required
classes on demand. I got this working for my own classes, but more
investigation would be required to see if this could be plumbed in at
sufficiently low level as to make Clojure fn classes available in the
same way. I also had some concerns about whether I was likely to find
that I had a class loaded in this way arriving into a jvm in which
that name had already been taken by another class - I could
investigate this as well - or perhaps someone else on the list has
been here before me ? I can post the code if anyone is interested.

> BTW, what did you mean by "I needed to hold
> more metadata than a record definition allows"? AFAIK, records (and
> metadata) are no more capacity-limited than are Clojure maps in
> general, and I'm not sure those are even limited to the 2^31 entries
> that are typically the maximum capacities of java.util collections.

Understood - I just used a bad turn of phrase. What I meant to say was
that, whilst I can sprinkle any amount of metadata around a defrecord,
defrecord itself only makes use of a certain amount of it and, as far
as I can tell (and it would help me if I was wrong on this), once the
new record type has been defined, there is no way to access non-
standard metadata that was present at defrecord time : e.g.

user=> (set! *print-meta* true)
true
user=> (def ^{:my-tag [1 2 3]} foo nil)
^{:ns #<Namespace user>, :name foo, :my-tag [1 2 3], :line 2372, :file
"NO_SOURCE_PATH"} #'user/foo

OK - my metadata preserved and now available to my program - but

user=> (defrecord ^{:my-tag [1 2 3]} Foo [a b ^{:my-other-tag [4 5 6]}
c])
user.Foo
user=>

and

user=> (Foo. 1 2 3)
#:user.Foo{:a 1, :b 2, :c 3}
user=>

If my metadata had been preserved, I would expect it to decorate the
new type or it's instances so my functions could look it up and act on
it at runtime. Hence I am wrapping the defrecord macro with my own and
transforming and stashing my metadata under another variable name.

If there is a better way to do this, then I would be very grateful to
hear about it :-)

thanks again,

Jules

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Reply via email to