~technomancy/fennel-lang.org

ref: c9a7db72fe3fd06b5eec936984713f034acd9511 fennel-lang.org/html.fnl -rw-r--r-- 1.6 KiB
c9a7db72Phil Hagelberg Remove broken contributors link until we can get it fixed. 3 months ago
                                                                                
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
;; A *very* basic HTML generation library.
;; Basic escaping features only; never use this on user input!

(local map (fn [f tbl]
             (let [out {}]
               (each [i v (ipairs tbl)]
                 (tset out i (f v)))
               out)))

(local map-kv (fn [f tbl]
                (let [out {}]
                  (each [k v (pairs tbl)]
                    (table.insert out (f k v)))
                  out)))

(local to-attr (fn [k v]
                 (if (= v true) k
                     (.. k "=\"" v"\""))))

(local tag (fn [tag-name attrs]
             (assert (= (type attrs) "table") "Missing attrs table")
             (let [attr-str (table.concat (map-kv to-attr attrs) " ")]
               (.. "<" tag-name " " attr-str">"))))

(local entity-replacements {"&" "&amp;" ; must be first!
                            "<" "&lt;"
                            ">" "&gt;"
                            "\"" "&quot;"})

(local entity-search (let [result []]
                       (each [k _ (pairs entity-replacements)]
                             (table.insert result k))
                       (.. "[" (table.concat result "") "]")))

(local escape (fn [s]
                  (assert (= (type s) "string"))
                  (: s :gsub entity-search entity-replacements)))

(fn html [document]
  (if (= (type document) "string")
      (escape document)
      (= (. document 1) :NO-ESCAPE)
      (. document 2)
      (let [[tag-name attrs & body] document]
        (.. (tag tag-name attrs)
            (table.concat (map html body) " ")
            "</" tag-name ">"))))