site.cd 6.03 KB
Newer Older
1
2
3
(* This CDuce script produces CDuce web site. *)


4
5
include "xhtml-strict.cd";;  (* XHTML 1 Strict DTD *)
include "xhtml-categ.cd";;   (* Categories (Inline, ...) from this DTD *)
6

7
8
9
10
11
12
13
14
15
16
17
18
19
20

let fun load_include (String -> [Any*])
 name ->
   let _ = print [ 'Loading ' !name '... \n' ] in
   xtransform [ (load_xml name) ] with 
     <include file=(s & String)>[] -> load_include s;; 


let fun hilight (String -> [ (Char | Xvar)* ] )
 | [ '{{' h ::(Char *?) '}}' ; rest ] -> [ <var class="hilight">h; hilight rest ]
 | [ c; rest ] -> [ c; hilight rest ]
 | [] -> [];;


21
type SitePage = 
22
   Page
23
24
 | <external {|href=String; title=String|}>[];;
type Site = <site>[ SitePage* ];;
25

26
type Page = 
27
  <page output=String>[
28
29
30
    <title>String
    <banner>[InlineText*]
    <navig>[ NavigBox* ] <main>[ Box* ] ];;
31
32
33

type Author = <author>String;;
type Paper = 
34
35
36
37
38
39
  <paper file=?String>[ 
    <title>String 
    Author+ 
    <comment>[InlineText*] 
    <abstract>Content ];;

40
type Slides = 
41
42
43
44
  <slides file=String>[ 
   <title>String 
   Author+ 
   <comment>[InlineText*] ];;
45
46

type Link =
47
  <link url=String; title=String>[ InlineText* ];;
48
49
50
51
52

type Content =      
   [ ( <p {||}>[InlineText*]
     | <ul {||}>[<li {||}>Content +]
     | <section title=String>Content
53
     | <sample>String
54
     | Xtable
55
56
57
     | Paper | Slides | Link 
     | <include-verbatim file=String>[]
     | InlineText )* ];;
58
59
60

type InlineText =
     Char
61
62
   | <(`b|`i|`tt|`em) {||}>[InlineText*]
   | <duce>String
63
   | Xa
64
   | Ximg | Xbr ;;
65
66
67
68
69
70
71
72
73
74

type Box = <box title=String; subtitle=?String; link=String>Content
         | <meta>Content;;
type NavigBox = <box>Content | <toc>[];;

let fun authors ([Author+] -> String)
   | [ <author>a ] -> a
   | [ <author>a1 <author>a2 ] -> a1 @ ", and " @ a2
   | [ <author>a; rem ] -> a @ ", " @ authors rem;;

75
let fun text (t : [InlineText*]) : Inlines =
76
  map t with
77
78
   | <duce>x -> <b>[ <tt>(hilight x) ]
   | <(tag & (`b|`i|`tt|`em))>x -> <(tag)>(text x)
79
   | z -> z;;
80

81
82
let fun content (t : Content) : Flow =
  transform t with
83
84
   | <section title=title>c -> 
         [ <h4>title !(content c) ]
85
   | <paper (r)>[ <title>tit aut::Author* <comment>com <abstract>ab  ]  ->
86
         [ (match r with { file = f } -> <a href=f>tit | _ -> <b>tit) '. '
87
           !(authors aut) '. '
88
	   !(text com)
89
90
91
           <div class="abstract">[ 'Abstract:' !(content ab) ]
         ]
   | <slides file=f>[ <title>tit aut::Author* <comment>com ]  ->
92
        [ <a href=f>tit '. ' !(authors aut) '. ' !(text com) ]
93
   | <include-verbatim file=f>[] ->
94
        [ <div class="code">[ <pre>(load_file f) ] ]
95
96
   | <sample>s ->
        [ <div class="code">[ <pre>(hilight s) ] ]
97
98
99
100
101
102
   | <link url=url; title=title>com -> 
        [ <a href=url>title '. ' !(text com) ]
   | <ul>lis -> 
        [ <ul>(map lis with <li>x -> <li>(content x)) ]
   | Xtable & x -> 
        [ x ]
103
104
   | <p>x -> [ <p>(text x) ]
   | x -> text [ x ];;
105
106
107
108

let fun main2html (Box -> Flow)
  <box (r)>c ->
   [ <div class="box">[
109
       <h2>(r . title)
110
        !(match r with { subtitle = t } -> [<b>t] | _ -> [])
111
       <a name=r . link>[] 
112
113
114
115
       !(content c)  ] ]
| <meta>c -> [ <div class="meta">(content c) ];;


116
117
118
119
120
(* Ugly hack to introduce PHP code ...
   The idea is to produce first an XML document with a distinguished element.
   The function patch_css search for the textual representation of this
   element and replace it with the PHP code. *)

121
122
123
124
let php_css : String =
[' <?php
$browser = getenv("HTTP_USER_AGENT");
if (preg_match("/MSIE/i", "$browser")) {
125
126
        $css = "<link rel=\\"stylesheet\\" href=\\"cduce.css\\"
type=\\"text/css\\">";
127
128
129
} elseif (preg_match("/Mozilla/i", "$browser")) {
        $css = "<blink>For better presentation use a more recent version
of your browser, like Netscape 6</blink>";
130
131
132
} if (preg_match("/Mozilla\\/5.0/i", "$browser")) {
        $css = "<link rel=\\"stylesheet\\" href=\\"cduce.css\\"
type=\\"text/css\\">";
133
} elseif  (preg_match("/opera/i", "$browser")) {
134
135
        $css = "<link rel=\\"stylesheet\\" href=\\"cduce.css\\"
type=\\"text/css\\">";
136
137
138
139
140
141
142
143
144
}
echo "$css";
?> '];;


let fun patch_css (String -> String)
| [ a::_*? '<meta content="css"/>'; rem ] -> a @ php_css @ rem
| s -> s;;

145
146
147
148
149
150
151
152
153
154
155
156
157
let fun page2html (Page -> Xhtml)
<page>[ <title>title <banner>banner <navig>navig <main>main ] ->
 let toc = 
   transform main with <box title=t; link=l>_ -> [ <li>[ <a href=('#',l)>t ] ] in
 let toc = match toc with [] -> [] | lis -> [ <ul>lis ] in
 let navig : Flow = transform navig with
  | <box>c -> [ <div class="box">(content c) ]
  | <toc>[] -> [ <div class="box">toc ]
 in
 <html>[
  <head>[ 
   <title>title
   <meta content="text/html; charset=iso-8859-1"; http-equiv="Content-Type">[]
158
   <meta content="css">[]  (* Placeholder for PHP code *)
159
160
  ]
  <body>[ 
161
   <div class="title">[ <h1>(text banner) ]
162
163
164
165
166
   <div id="Sidelog">navig
   <div id="Content">(transform main with b -> main2html b)
  ]
 ];;

167
type P = (String,<title>String);;
168

169
let fun make_plan (l : [ P+ ]) : Page =
170
<page output="plan.php">[ 
171
172
173
174
175
176
177
178
179
180
  <title>"CDuce site"
  <banner>"CDuce site"
  <navig>[ <box>[ <a href="/">"Home" ] ]
  <main>[ 
    <box title="Pages"; link="pages">[
      <ul>(map l with (file,<title>t) -> <li>[<a href=file>t]) 
    ]
    <meta>[ 'This page was automatically generated by a CDuce program.' ]
  ]
];;
181

182
183
184
let fun do_page(Page -> P)
 <page output=outf>[ tit & <title>_; _ ] & page ->
    let _ = print [ 'Generating html... ' ] in
185
    let html : String = 
186
       [ (* '<?xml version="1.0" encoding="iso-8859-1"?>' *)
187
188
         '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"'
         '  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">'
189
         !(patch_css (print_xml (page2html page))) ] in
190
    let _ = print [ 'Saving to ' !outf '...\n' ] in
191
    let _ = dump_to_file outf html in
192
    (outf, tit);;
193
 
194
let site =     
195
196
 match load_include "site.xml" with
 | [ Site & <site>s ] ->
197
     let ts = map s with 
198
             | Page & p -> do_page p
199
200
             | <external href=url; title=t>_ -> (url,<title>t) in
     let _ = print [ 'Create plan... ' ] in
201
     let plan = make_plan (ts @ [("plan.php", <title>"CDuce site")]) in
202
203
     let _ = do_page plan in
     []
204
 | _ -> raise "Invalid site.xml";;