[plt-scheme] XML and Programming
Careful, this is long. A better forum would probably be
comp.lang.scheme, but (a) I'm talking about stuff which is implemented
in PLT, (b) I don't want to get dragged to useless flamewars - people
here (I think) are more focused... I am talking about a lot of stuff,
even getting to syntax issues that are related to my own research
which is pretty surprising (at least it was surprising for me).
Anyway...
As part of the new Swindle port that I'm finalizing, I've included the
thing I use to generate HTML, and a question came up about why should
I make yet another package that generates HTML. So besides many other
arguments (btw, mine was there before PLT, SSAX, WebIt!), I tried to
sit and think why exactly I still prefer my thing, and came up with a
few ideas that I though are interesting enough to write about. This
is why it is long, and there is no related implementation issues
(yet?).
So first, a technical representation issue: I found that using
(Lisp-style) keywords is extremely useful, something that I've already
mentioned in
http://list.cs.brown.edu/pipermail/plt-scheme/2002-July/000162.html
This doesn't matter much for what I'm about to write, but genrally
(foo: :x 1 :y 2 bar)
is equivalent to the more PLT-standard
`(foo ((x 1) (y 2)) ,bar)
All information about this can be found at
http://www.cs.cornell.edu/eli/misc/html-doc.txt
There are several things to note here:
1. Some of the keywords are `meta' keywords that are used for
formatting, for example:
> (output-html (b: ::spaces? #t 1 2))
<b>1 2</b>
> (output-html (b: ::spaces? #f 1 2))
<b>12</b>
The convention I use is a `::' prefix, but anything can be used.
2. The representation that is used is actually the same as the syntax
that creates it:
> (b: "foo")
(b: "foo")
> (output-html (b: "foo"))
<b>foo</b>
> (output-html '(b: "foo"))
<b>foo</b>
What just hit me is that this looks very much like what I'm using now
in Nuprl: the problem there is that I want to represent Nuprl syntax,
avoiding fundamental changes to the system. This restriction
disqualifies a Scheme-like solution of a `quote' (or `quasi-quote')
context that prevents evaluation in its scope. Instead, we use
something that we call "operator-shifting" --- every operator has
another which looks similar to the original one except that it
produces a representation of the first. Using the new PLT syntax
system, this can be demonstrated quickly:
> (module opshift mzscheme
(provide (all-from-except mzscheme #%app))
(provide (rename app~ #%app))
(define-syntax app~
(syntax-rules (quote)
((_ 'op . args) (#%app list 'op . args))
((_ . args) (#%app . args)))))
> (require opshift)
> ('+ 1 2)
(+ 1 2)
[One side-note is that in Nuprl, the shifted operator has the same
binding structure which nicely leads to higher order abstract syntax.]
This sounds like just a technical point with one justification: the
fact that most things in an s-expression that should generate HTML are
constants, so this allows me to get an environment similar to the PLT
thing except that variable references are always unquoted. But there
is more to it than that: because it is still a function call, I can
override the default behavior with something else, for example:
> (defwrapper* red: 'font: :color "red")
> (red: "foo")
(red: "foo")
> (output-html (red: "foo"))
<font color="red">foo</font>
or even specify any function to handle the form:
> (defwrapper rev: (lambda args (apply spaces: (reverse args))))
> (rev: 1 2 3)
(rev: 1 2 3)
> (output-html (rev: 1 2 3))
3 2 1
When you think about these things as representations of syntax, then
these functions are actually similar to macro transformers.
Now, when I was trying to compare what I'd get from SSAX (or whatever
is the thing which is the equivalent of XSLT, sorry for not knowing
more about it) to what I have, I realized that this functionality is
something that I prefer over the general pattern transformations since
the way I do it is using standard Scheme code, which gives me an
equivalent power. For example, with an XSLT thing I should be able to
convert XML data to HTML for presentation -- and with my thing, I
could just produce HTML after putting the right definitions that will
convert something like (title: ...) to (i: ...).
But there is some functionality which is more difficult with my thing:
it would be harder to specify that the `title:'->`i:' transformation
should happen inside a `book:' wrapper. For this, the XSLT-style
transformations are easier.
And this is another idea that came out of this: it might be useful to
have these pattern transformations in Scheme even out side the context
of XML: something that will allow to have macro transformations that
will allow specifying rewrites like:
(transform stx (< (length ?x) 1) (or (null? ?x) (null? (cdr ?x))))
in a much more convenient way that can be done now.
That's all, sorry for wasted time if it wasn't interesting.
--
((lambda (x) (x x)) (lambda (x) (x x))) Eli Barzilay:
http://www.barzilay.org/ Maze is Life!