Ver código fonte

Finish the routing/slugs overhaul.

Brit Butler 10 anos atrás
pai
commit
ef378b9b56

+ 6 - 1
src/content.lisp

@@ -4,7 +4,12 @@
4 4
 
5 5
 (defclass tag ()
6 6
   ((name :initarg :name :reader tag-name)
7
-   (slug :initarg :slug :reader tag-slug)))
7
+   (slug :initarg :slug :reader tag-slug)
8
+   (url  :initarg :url)))
9
+
10
+(defmethod initialize-instance :after ((tag tag) &key)
11
+  (with-slots (url slug) tag
12
+    (setf url (compute-url nil slug 'tag-index))))
8 13
 
9 14
 (defun make-tag (str)
10 15
   "Takes a string and returns a TAG instance with a name and slug."

+ 12 - 11
src/documents.lisp

@@ -28,9 +28,15 @@
28 28
 (defgeneric page-url (document)
29 29
   (:documentation "The relative URL to the DOCUMENT."))
30 30
 
31
-(defun compute-url (document unique-id)
32
-  "Compute the relative URL for a DOCUMENT based on its UNIQUE-ID."
33
-  (let* ((class-name (class-name (class-of document)))
31
+(defgeneric render (document &key &allow-other-keys)
32
+  (:documentation "Render the given DOCUMENT to HTML."))
33
+
34
+;; Helper Functions
35
+
36
+(defun compute-url (document unique-id &optional class)
37
+  "Compute the relative URL for a DOCUMENT based on its UNIQUE-ID. If CLASS
38
+is provided, it overrides the route used."
39
+  (let* ((class-name (or class (class-name (class-of document))))
34 40
          (route (get-route class-name)))
35 41
     (unless route
36 42
       (error "No routing method found for: ~A" class-name))
@@ -38,10 +44,9 @@
38 44
            (type (or (pathname-type result) (page-ext *config*))))
39 45
       (make-pathname :type type :defaults result))))
40 46
 
41
-(defgeneric render (document &key &allow-other-keys)
42
-  (:documentation "Render the given DOCUMENT to HTML."))
43
-
44
-;; Helper Functions
47
+(defun get-route (doc-type)
48
+  "Return the route format string for DOC-TYPE."
49
+  (second (assoc (make-keyword doc-type) (routing *config*))))
45 50
 
46 51
 (defun add-document (document)
47 52
   "Add DOCUMENT to the in-memory database. Error if a matching entry is present."
@@ -63,10 +68,6 @@ use it as the template passing any RENDER-ARGS."
63 68
         (url (namestring (page-url document))))
64 69
     (write-file (rel-path (staging-dir *config*) url) html)))
65 70
 
66
-(defun get-route (doc-type)
67
-  "Return the route format string for DOC-TYPE."
68
-  (second (assoc (make-keyword doc-type) (routing *config*))))
69
-
70 71
 (defun find-all (doc-type)
71 72
   "Return a list of all instances of a given DOC-TYPE."
72 73
   (loop for val being the hash-values in *site*

+ 7 - 6
src/indexes.lisp

@@ -7,6 +7,7 @@
7 7
 
8 8
 (defclass index ()
9 9
   ((url     :initarg :url     :reader page-url)
10
+   (name    :initarg :name    :reader index-name)
10 11
    (title   :initarg :title   :reader title-of)
11 12
    (content :initarg :content :reader index-content)))
12 13
 
@@ -33,7 +34,7 @@
33 34
 
34 35
 (defun index-by-tag (tag content)
35 36
   "Return an index of all CONTENT matching the given TAG."
36
-  (make-instance 'tag-index :slug (tag-slug tag)
37
+  (make-instance 'tag-index :slug (tag-slug tag) :name (tag-name tag)
37 38
                  :content (remove-if-not (lambda (x) (tag-p tag x)) content)
38 39
                  :title (format nil "Content tagged ~a" (tag-name tag))))
39 40
 
@@ -52,7 +53,7 @@
52 53
 
53 54
 (defun index-by-month (month content)
54 55
   "Return an index of all CONTENT matching the given MONTH."
55
-  (make-instance 'month-index :slug month
56
+  (make-instance 'month-index :slug month :name month
56 57
                  :content (remove-if-not (lambda (x) (month-p month x)) content)
57 58
                  :title (format nil "Content from ~a" month)))
58 59
 
@@ -72,15 +73,15 @@
72 73
 (defun index-by-n (i content)
73 74
   "Return the index for the Ith page of CONTENT in reverse chronological order."
74 75
   (let ((content (subseq content (* 10 i))))
75
-    (make-instance 'numeric-index :slug (1+ i)
76
+    (make-instance 'numeric-index :slug (1+ i) :name (1+ i)
76 77
                    :content (take-up-to 10 content)
77 78
                    :title "Recent Content")))
78 79
 
79 80
 (defmethod publish ((doc-type (eql (find-class 'numeric-index))))
80
-  (let ((indexes (sort (find-all 'numeric-index) #'< :key #'index-slug)))
81
+  (let ((indexes (sort (find-all 'numeric-index) #'< :key #'index-name)))
81 82
     (dolist (index indexes)
82
-      (let ((prev (1- (index-slug index)))
83
-            (next (1+ (index-slug index))))
83
+      (let ((prev (1- (index-name index)))
84
+            (next (1+ (index-name index))))
84 85
         (write-document index nil
85 86
                         :prev (when (plusp prev) prev)
86 87
                         :next (when (<= next (length indexes)) next))))))

+ 1 - 1
themes/atom.tmpl

@@ -14,7 +14,7 @@
14 14
 
15 15
   {foreach $post in $content.content}
16 16
   <entry>
17
-    <link type="text/html" rel="alternate" href="{$config.domain}/{$post.path}"/>
17
+    <link type="text/html" rel="alternate" href="{$config.domain}/{$post.url}"/>
18 18
     <title>{$post.title}</title>
19 19
     <published>{$post.date}</published>
20 20
     <updated>{$post.date}</updated>

+ 5 - 5
themes/hyde/index.tmpl

@@ -4,20 +4,20 @@
4 4
 <h1 class="title">{$index.title}</h1>
5 5
 {foreach $obj in $index.content}
6 6
   <div class="article-meta">
7
-    <a class="article-title" href="{$config.domain}/{$obj.path}">{$obj.title}</a>
7
+    <a class="article-title" href="{$config.domain}/{$obj.url}">{$obj.title}</a>
8 8
     <div class="date"> posted on {$obj.date}</div>
9 9
     <div class="article">{$obj.text |noAutoescape}</div>
10 10
   </div>
11 11
 {/foreach}
12 12
 <div id="relative-nav">
13
-  {if $prev} <a href="{$config.domain}/{$prev.path}">Previous</a> {/if}
14
-  {if $next} <a href="{$config.domain}/{$next.path}">Next</a> {/if}
13
+  {if $prev} <a href="{$config.domain}/{$prev.url}">Previous</a> {/if}
14
+  {if $next} <a href="{$config.domain}/{$next.url}">Next</a> {/if}
15 15
 </div>
16 16
 {if $tags}
17 17
 <div id="tagsoup">
18 18
   <p>This blog covers
19 19
     {foreach $tag in $tags}
20
-      <a href="{$config.domain}/${tag.path}">{$tag.name}</a>{nil}
20
+      <a href="{$config.domain}/${tag.url}">{$tag.name}</a>{nil}
21 21
       {if not isLast($tag)},{sp}{/if}
22 22
     {/foreach}
23 23
 </div>
@@ -26,7 +26,7 @@
26 26
 <div id="monthsoup">
27 27
   <p>View content from
28 28
     {foreach $month in $months}
29
-      <a href="{$config.domain}/{$month.path}">{$month}</a>{nil}
29
+      <a href="{$config.domain}/{$month.url}">{$month.name}</a>{nil}
30 30
       {if not isLast($month)},{sp}{/if}
31 31
     {/foreach}
32 32
 </div>

+ 3 - 3
themes/hyde/post.tmpl

@@ -6,7 +6,7 @@
6 6
   <div class="tags">{\n}
7 7
     {if $post.tags}
8 8
       Tagged as {foreach $tag in $post.tags}
9
-        <a href="{$config.domain}/{$tag.path}">{$tag.name}</a>{nil}
9
+        <a href="{$config.domain}/{$tag.url}">{$tag.name}</a>{nil}
10 10
           {if not isLast($tag)},{sp}{/if}
11 11
       {/foreach}
12 12
     {/if}
@@ -21,7 +21,7 @@
21 21
   {$post.text |noAutoescape}
22 22
 </div>{\n}
23 23
 <div class="relative-nav">{\n}
24
-  {if $prev} <a href="{$config.domain}/{$prev.path}">Previous</a><br> {/if}{\n}
25
-  {if $next} <a href="{$config.domain}/{$next.path}">Next</a><br> {/if}{\n}
24
+  {if $prev} <a href="{$config.domain}/{$prev.url}">Previous</a><br> {/if}{\n}
25
+  {if $next} <a href="{$config.domain}/{$next.url}">Next</a><br> {/if}{\n}
26 26
 </div>{\n}
27 27
 {/template}

+ 3 - 3
themes/readable/index.tmpl

@@ -4,7 +4,7 @@
4 4
 <h1 class="page-header">{$index.title}</h1>
5 5
 {foreach $obj in $index.content}
6 6
   <div class="row-fluid">
7
-    <h1><a href="{$config.domain}/{$obj.path}">{$obj.title}</a></h1>
7
+    <h1><a href="{$config.domain}/{$obj.url}">{$obj.title}</a></h1>
8 8
     <p class="date-posted">posted on {$obj.date}</p>
9 9
     {$obj.text |noAutoescape}
10 10
   </div>
@@ -13,7 +13,7 @@
13 13
 <div class="row-fluid">
14 14
   <p>This blog covers
15 15
     {foreach $tag in $tags}
16
-      <a href="{$config.domain}/{$tag.path}">{$tag.name}</a>{nil}
16
+      <a href="{$config.domain}/{$tag.url}">{$tag.name}</a>{nil}
17 17
       {if not isLast($tag)},{sp}{/if}
18 18
     {/foreach}
19 19
   </p>
@@ -23,7 +23,7 @@
23 23
 <div class="row-fluid">
24 24
   <p>View content from
25 25
     {foreach $month in $months}
26
-      <a href="{$config.domain}/{$month.path}">{$month}</a>{nil}
26
+      <a href="{$config.domain}/{$month.url}">{$month.name}</a>{nil}
27 27
       {if not isLast($month)},{sp}{/if}
28 28
     {/foreach}
29 29
   </p>

+ 3 - 3
themes/readable/post.tmpl

@@ -6,7 +6,7 @@
6 6
   <p>
7 7
     {if $post.tags}
8 8
       Tagged as {foreach $tag in $post.tags}
9
-        <a href="{$config.domain}/{$tag.path}">{$tag.name}</a>{nil}
9
+        <a href="{$config.domain}/{$tag.url}">{$tag.name}</a>{nil}
10 10
           {if not isLast($tag)},{sp}{/if}
11 11
       {/foreach}
12 12
     {/if}
@@ -20,8 +20,8 @@
20 20
   {$post.text |noAutoescape}
21 21
   
22 22
   <ul class="pager">
23
-    {if $prev}<li class="previous"><a href="{$config.domain}/{$prev.path}">&larr; Previous</a></li>{/if}{\n}
24
-    {if $next}<li class="next"><a href="{$config.domain}/{$next.path}">Next &rarr;</a></li>{/if}{\n}
23
+    {if $prev}<li class="previous"><a href="{$config.domain}/{$prev.url}">&larr; Previous</a></li>{/if}{\n}
24
+    {if $next}<li class="next"><a href="{$config.domain}/{$next.url}">Next &rarr;</a></li>{/if}{\n}
25 25
   </ul>
26 26
 </div>{\n}
27 27
 {/template}

+ 2 - 2
themes/rss.tmpl

@@ -13,10 +13,10 @@
13 13
     {foreach $post in $content.content}
14 14
     <item>
15 15
       <title>{$post.title}</title>
16
-      <link>{$config.domain}/{$post.path}</link>
16
+      <link>{$config.domain}/{$post.url}</link>
17 17
       <pubDate>{$post.date}</pubDate>
18 18
       <author>{$config.author}</author>
19
-      <guid isPermaLink="true">{$config.domain}/{$post.path}</guid>
19
+      <guid isPermaLink="true">{$config.domain}/{$post.url}</guid>
20 20
       {foreach $tag in $post.tags}
21 21
         <category><![CDATA[ {$tag.name |noAutoescape} ]]></category>
22 22
       {/foreach}