commit
4e6efa9d9e
7 changed files with 70 additions and 34 deletions
8
NEWS.md
8
NEWS.md
|
@ -7,6 +7,14 @@
|
||||||
the old behavior.
|
the old behavior.
|
||||||
* Coleslaw no longer expects a particular repo layout. Use whatever
|
* Coleslaw no longer expects a particular repo layout. Use whatever
|
||||||
directory hierarchy you like.
|
directory hierarchy you like.
|
||||||
|
* New Content Type Plugin: Static Pages, accepting a title, url, and
|
||||||
|
optionally tags and a date. All files with a `.page` extension are
|
||||||
|
compiled as static pages and reuse the POST template.
|
||||||
|
To enable Static Pages, add `(static-pages)` to the `:plugins`
|
||||||
|
section of your config.
|
||||||
|
* Coleslaw now allows content without a date or tags. Note that POSTs
|
||||||
|
without a date will still show up in the reverse chronological
|
||||||
|
indexes at the very end.
|
||||||
|
|
||||||
## Changes for 0.9.3 (2013-04-16):
|
## Changes for 0.9.3 (2013-04-16):
|
||||||
|
|
||||||
|
|
|
@ -168,25 +168,6 @@ freshly built site.
|
||||||
|
|
||||||
## Areas for Improvement
|
## Areas for Improvement
|
||||||
|
|
||||||
### Allow Tagless or Dateless Content
|
|
||||||
|
|
||||||
Several users have expected to be able to not supply tags or a date
|
|
||||||
for their content. This is a reasonable expectation and requires
|
|
||||||
changes to at least the post templates and the `read-content`
|
|
||||||
function. There may be other areas where it was assumed tags/dates
|
|
||||||
will always be present.
|
|
||||||
|
|
||||||
### New Content Type: Pages!
|
|
||||||
|
|
||||||
Many users have requested a content type PAGE, for static pages. It
|
|
||||||
should be a pretty straightforward subclass of CONTENT with the
|
|
||||||
necessary methods: `render`, `page-url` and `publish`. It could have a
|
|
||||||
`url` slot with `page-url` as a reader to allow arbitrary layout on
|
|
||||||
the site. For now, we can be sloppy and reuse the post template and
|
|
||||||
limit static-pages to being written in markdown. If we want to support
|
|
||||||
other formats, consider moving the format slot from POST to CONTENT.
|
|
||||||
This has been implemented on the branch `static-pages`.
|
|
||||||
|
|
||||||
### New Content Type: Shouts!
|
### New Content Type: Shouts!
|
||||||
|
|
||||||
I've also toyed with the idea of a content type called a SHOUT, which
|
I've also toyed with the idea of a content type called a SHOUT, which
|
||||||
|
|
32
plugins/static-pages.lisp
Normal file
32
plugins/static-pages.lisp
Normal file
|
@ -0,0 +1,32 @@
|
||||||
|
(defpackage :coleslaw-static-pages
|
||||||
|
(:use :cl)
|
||||||
|
(:export #:enable)
|
||||||
|
(:import-from :coleslaw #:*config*
|
||||||
|
#:content
|
||||||
|
#:page-url
|
||||||
|
#:find-all
|
||||||
|
#:render
|
||||||
|
#:publish
|
||||||
|
#:write-document))
|
||||||
|
|
||||||
|
(in-package :coleslaw-static-pages)
|
||||||
|
|
||||||
|
(defclass page (content)
|
||||||
|
((title :initarg :title :reader page-title)
|
||||||
|
(url :initarg :url :reader page-url)))
|
||||||
|
|
||||||
|
(defmethod initialize-instance :after ((object page) &key)
|
||||||
|
;; Expect all static-pages to be written in Markdown for now.
|
||||||
|
(with-accessors ((text content-text)) object
|
||||||
|
(setf text (render-text text :md))))
|
||||||
|
|
||||||
|
(defmethod render ((object page) &key next prev)
|
||||||
|
;; For the time being, we'll re-use the normal post theme.
|
||||||
|
(funcall (theme-fn 'post) (list :config *config*
|
||||||
|
:post object)))
|
||||||
|
|
||||||
|
(defmethod publish ((doc-type (eql (find-class 'page))))
|
||||||
|
(dolist (page (find-all 'page))
|
||||||
|
(write-document page)))
|
||||||
|
|
||||||
|
(defun enable ())
|
|
@ -36,6 +36,11 @@
|
||||||
(date :initform nil :initarg :date :accessor content-date)
|
(date :initform nil :initarg :date :accessor content-date)
|
||||||
(text :initform nil :initarg :text :accessor content-text)))
|
(text :initform nil :initarg :text :accessor content-text)))
|
||||||
|
|
||||||
|
(defmethod initialize-instance :after ((object content) &key)
|
||||||
|
(with-accessors ((tags content-tags)) object
|
||||||
|
(when (stringp tags)
|
||||||
|
(setf tags (mapcar #'make-tag (cl-ppcre:split "," tags))))))
|
||||||
|
|
||||||
(defun read-content (file)
|
(defun read-content (file)
|
||||||
"Returns a plist of metadata from FILE with :text holding the content as a string."
|
"Returns a plist of metadata from FILE with :text holding the content as a string."
|
||||||
(flet ((slurp-remainder (stream)
|
(flet ((slurp-remainder (stream)
|
||||||
|
@ -46,9 +51,7 @@
|
||||||
(parse-field (str)
|
(parse-field (str)
|
||||||
(nth-value 1 (cl-ppcre:scan-to-strings "[a-zA-Z]+: (.*)" str)))
|
(nth-value 1 (cl-ppcre:scan-to-strings "[a-zA-Z]+: (.*)" str)))
|
||||||
(field-name (line)
|
(field-name (line)
|
||||||
(make-keyword (string-upcase (subseq line 0 (position #\: line)))))
|
(make-keyword (string-upcase (subseq line 0 (position #\: line))))))
|
||||||
(read-tags (str)
|
|
||||||
(mapcar #'make-tag (cl-ppcre:split "," str))))
|
|
||||||
(with-open-file (in file :external-format '(:utf-8))
|
(with-open-file (in file :external-format '(:utf-8))
|
||||||
(unless (string= (read-line in) (separator *config*))
|
(unless (string= (read-line in) (separator *config*))
|
||||||
(error "The provided file lacks the expected header."))
|
(error "The provided file lacks the expected header."))
|
||||||
|
@ -57,9 +60,10 @@
|
||||||
appending (list (field-name line)
|
appending (list (field-name line)
|
||||||
(aref (parse-field line) 0))))
|
(aref (parse-field line) 0))))
|
||||||
(content (slurp-remainder in)))
|
(content (slurp-remainder in)))
|
||||||
(setf (getf meta :tags) (read-tags (getf meta :tags)))
|
|
||||||
(append meta (list :text content))))))
|
(append meta (list :text content))))))
|
||||||
|
|
||||||
|
;; Helper Functions
|
||||||
|
|
||||||
(defun tag-p (tag obj)
|
(defun tag-p (tag obj)
|
||||||
"Test if OBJ is tagged with TAG."
|
"Test if OBJ is tagged with TAG."
|
||||||
(let ((tag (if (typep tag 'tag) tag (make-tag tag))))
|
(let ((tag (if (typep tag 'tag) tag (make-tag tag))))
|
||||||
|
|
|
@ -15,6 +15,7 @@
|
||||||
#:index
|
#:index
|
||||||
#:render-text
|
#:render-text
|
||||||
#:add-injection
|
#:add-injection
|
||||||
|
#:theme-fn
|
||||||
;; The Document Protocol
|
;; The Document Protocol
|
||||||
#:add-document
|
#:add-document
|
||||||
#:find-all
|
#:find-all
|
||||||
|
|
|
@ -4,13 +4,17 @@
|
||||||
<div class="article-meta">{\n}
|
<div class="article-meta">{\n}
|
||||||
<h1 class="title">{$post.title}</h1>{\n}
|
<h1 class="title">{$post.title}</h1>{\n}
|
||||||
<div class="tags">{\n}
|
<div class="tags">{\n}
|
||||||
Tagged as {foreach $tag in $post.tags}
|
{if $post.tags}
|
||||||
<a href="../tag/{$tag.slug}.{$config.pageExt}">{$tag.name}</a>{nil}
|
Tagged as {foreach $tag in $post.tags}
|
||||||
{if not isLast($tag)},{sp}{/if}
|
<a href="../tag/{$tag.slug}.{$config.pageExt}">{$tag.name}</a>{nil}
|
||||||
{/foreach}
|
{if not isLast($tag)},{sp}{/if}
|
||||||
|
{/foreach}
|
||||||
|
{/if}
|
||||||
</div>{\n}
|
</div>{\n}
|
||||||
<div class="date">{\n}
|
<div class="date">{\n}
|
||||||
Written on {$post.date}
|
{if $post.date}
|
||||||
|
Written on {$post.date}
|
||||||
|
{/if}
|
||||||
</div>{\n}
|
</div>{\n}
|
||||||
</div>{\n}
|
</div>{\n}
|
||||||
<div class="article-content">{\n}
|
<div class="article-content">{\n}
|
||||||
|
|
|
@ -3,13 +3,19 @@
|
||||||
{template post}
|
{template post}
|
||||||
<div class="row-fluid">{\n}
|
<div class="row-fluid">{\n}
|
||||||
<h1 class="page-header">{$post.title}</h1>{\n}
|
<h1 class="page-header">{$post.title}</h1>{\n}
|
||||||
<p>Tagged as
|
<p>
|
||||||
{foreach $tag in $post.tags}
|
{if $post.tags}
|
||||||
<a href="../tag/{$tag.slug}{$config.pageExt}">{$tag.name}</a>{nil}
|
Tagged as {foreach $tag in $post.tags}
|
||||||
{if not isLast($tag)},{sp}{/if}
|
<a href="../tag/{$tag.slug}{$config.pageExt}">{$tag.name}</a>{nil}
|
||||||
{/foreach}
|
{if not isLast($tag)},{sp}{/if}
|
||||||
|
{/foreach}
|
||||||
|
{/if}
|
||||||
|
</p>
|
||||||
|
<p class="date-posted">
|
||||||
|
{if $post.date}
|
||||||
|
Written on {$post.date}
|
||||||
|
{/if}
|
||||||
</p>
|
</p>
|
||||||
<p class="date-posted">Written on {$post.date}</p>
|
|
||||||
|
|
||||||
{$post.text |noAutoescape}
|
{$post.text |noAutoescape}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue