(* Copyright 2015 the Massachusetts Institute of Technology
Licensed under the Apache License, Version 2.0 (the "License"); you may not use
this file except in compliance with the License. You may obtain a copy of the
License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software distributed
under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
CONDITIONS OF ANY KIND, either express or implied. See the License for the
specific language governing permissions and limitations under the License. *)
structure Configuration = struct
val main_page_name = "Main Page"
val wiki_title = "UrWiki demo"
end
type id = int
table commit : { Id : id,
Created : time,
Content : string }
PRIMARY KEY Id
sequence commit_id_next
table article : { Title : string,
Head : id }
PRIMARY KEY Title,
CONSTRAINT Head
FOREIGN KEY Head REFERENCES commit(Id)
datatype mode = View | Edit
val eq_mode =
mkEq (fn x y =>
case (x, y) of
(View, View) => True
| (Edit, Edit) => True
| _ => False)
fun only_in mode_source target_mode =
current_mode <- signal mode_source;
return (if current_mode = target_mode
then null
else Style.invisible)
fun commit_article title text : transaction unit =
id <- nextval commit_id_next;
creation_time <- now;
dml (INSERT INTO commit (Id, Created, Content)
VALUES ({[id]}, {[creation_time]}, {[text]}));
(* TODO(bbaren): This is ugly. Use CAS instead? *)
sql_error <- tryDml (INSERT INTO article (Title, Head)
VALUES ({[title]}, {[id]}));
case sql_error of
None =>
(* We created a new article. *)
return ()
| Some _ =>
(* The article already exists. *)
dml (UPDATE article
SET Head = {[id]}
WHERE Title = {[title]})
fun wiki requested_article_title =
(* Look up the article. *)
extant_articles <-
queryL (SELECT article.Title, commit.Content
FROM article LEFT JOIN commit ON article.Head = commit.Id
WHERE article.Title = {[requested_article_title]});
let
val article =
case extant_articles of
Nil => {Title = requested_article_title, Body = "Not found."}
| art :: Nil => {Title = art.Article.Title,
Body = show art.Commit.Content}
| _ :: _ :: _ => error
{[Configuration.wiki_title]}
(* Editing panel *)