Please let me know if you have any comments on the non-backward-compatible changes I'm about to make to "html-template" ("http://www.neilvandyke.org/racket-html-template/";)."

Most of the visible changes to the "html-template" syntax is completely changing all the "%"-something parts of the template syntax, to be the following:

* "(%xexp BODY ...)" and "(%sxml BODY ...)" -- BODY evaluates to an SXML/xexp value, which is output as HTML in the appropriate context (e.g., content context vs. attribute value context).

* "(%format BODY ...)" and "(% BODY ...)" -- BODY evaluates to some value, and this value is formatted for appropriate literal display in HTML. For example, a string value is displayed as text, an integer value is displayed as a number, a date object is displayed as a date, etc. The formatting handler is customizable by the application programmer. Note that "(% BODY ...)" is changing purposes in the new version of "html-template" -- it used to be like the new "%xexp", but now it's a shorthand for "%format" instead.

* "(%verbatim BODY ...)" -- BODY evaluates to bytes, string, or a list of byteses and/or strings, which are output verbatim as bytes.

* "(%void BODY ...)" -- BODY is evaluated, and any value is ignored. This is presumably most useful for side-effects, when "#:ordering" is "evaluation" or "writes-and-evaluation" (not "any").

* "(%write BODY ...)" -- BODY is evaluated, and any writes to "current-output-port" are added verbatim to the output. Note that "%write" and "%write/port" are the only "%"-somethings that permit writing directly to a port the goes to HTML output. (I might even make writing to current-output-port or current-error-port within a "%"-something other than "%write" raise an error.)

* "(%write/port VAR BODY ...)" -- Like "%write", except that writing must be to the output port VAR. Writing to current-output-port within "%write/var" will raise an error, on the assumption that it's most likely a bug (like a missing port parameter in a "display" or a nested "html-template").

Note that there is no "%"-something shorthand for database queries, iteration, etc. I've about decided that the "%"-something forms should only be used for evaluating a block Racket code and determining what happens with the value from that evaluation. Of course, it's possible to create, say, an "html-template/db" syntax that layers over "html-template". Or I could make the "%"-something handlers in "html-template" extensible, but I currently see that as a low priority.

P.S., The examples below show the "response/html-template" form I've been working on, for using "html-template" even more efficiently with "web-server". This gives you an idea of what the current version of "html-template" does, since it's not yet well-documented. If I go with the above changes to "html-template", I'll probably refine "#:ordering" to be sensitive to what "%"-somethings you're using, and default to an appropriate ordering (and warn you if you're explicitly setting an ordering that doesn't make sense for the "%"-somethings you're using). I should also have an efficient way to *guarantee* that no output is written until all dynamic parts are evaluated, for people who want to be able to send an error response on an error, rather than a partial or corrupted response (this already happens incidentally, depending on how "#:ordering" is set, but that's conflating two different options that people might want to specify separately).

P.P.S., "syntax/parse" is great.

Neil V.

;; No dynamic parts, literal #:code, no #:message.

(response/html-template
 #:code 403
 (html (body (p "Name: Voltron")
             (p "Age: 29"))))
;;=expand=>
(response
 403
 #"Forbidden"
 (current-seconds)
 #"text/html; charset=utf-8"
 (cons (make-header #"Content-Length" #"60") '())
 (lambda (out)
   (write-bytes
    #"<html><body><p>Name: Voltron</p><p>Age: 29</p></body></html>"
    out)))

;; No dynamic expressions except #:code, no #:message, literal #:preamble.

(response/html-template
 #:code    (some-code-proc)
 #:preamble #"<!DOCTYPE html>\n"
 (html (body (p "Name: Voltron")
             (p "Age: 29"))))
;;=expand=>
(let ((code (some-code-proc)))
  (response
   code
   (hash-ref %web-server-xexp:http-code-to-message-bytes-hash
             code
             #"Unknown Status Code")
   (current-seconds)
   #"text/html; charset=utf-8"
   (cons (make-header #"Content-Length" #"76") '())
   (lambda (out)
     (write-bytes
#"<!DOCTYPE html>\n<html><body><p>Name: Voltron</p><p>Age: 29</p></body></html>"
      out))))

;; Dynamic parts, #:ordering any, dynamic preamble.

(response/html-template
 #:preamble (some-preamble-proc)
 (html (body (p "Name: " (% (some-name-proc)))
             (p "Age: "  (% (some-age-proc)))))))))
;;=expand=>
(response/full
 200
 #"OK"
 (current-seconds)
 #"text/html; charset=utf-8"
 '()
 (list (some-preamble-proc)
       #"<html><body><p>Name: "
       (html->bytes (some-name-proc))
       #"</p><p>Age: "
       (html->bytes (some-age-proc))
       #"</p></body></html>"))

;; Dynamic parts, #:ordering evaluation, literal preamble.

(response/html-template
 #:ordering evaluation
 #:preamble #"<!DOCTYPE html>\n"
 (html (body (p "Name: " (% (some-name-proc)))
             (p "Age: "  (% (some-age-proc))))))
;;=expand=>
(let ((dynamic-0 (html->bytes (some-name-proc)))
      (dynamic-1 (html->bytes (some-age-proc))))
  (response/full
   200
   #"OK"
   (current-seconds)
   #"text/html; charset=utf-8"
   '()
   (list #"<!DOCTYPE html>\n<html><body><p>Name: "
         dynamic-0
         #"</p><p>Age: "
         dynamic-1
         #"</p></body></html>")))

;; Dynamic parts, #:ordering evaluation, dynamic preamble.

(response/html-template
 #:ordering evaluation
 #:preamble (some-preamble-proc)
 (html (body (p "Name: " (% (some-name-proc)))
             (p "Age: "  (% (some-age-proc))))))
;;=expand=>
(let ((dynamic-0 (some-preamble-proc))
      (dynamic-1 (html->bytes (some-name-proc)))
      (dynamic-2 (html->bytes (some-age-proc))))
  (response/full
   200
   #"OK"
   (current-seconds)
   #"text/html; charset=utf-8"
   '()
   (list dynamic-0
         #"<html><body><p>Name: "
         dynamic-1
         #"</p><p>Age: "
         dynamic-2
         #"</p></body></html>")))

--
http://www.neilvandyke.org/
____________________
 Racket Users list:
 http://lists.racket-lang.org/users

Reply via email to