-
-
Notifications
You must be signed in to change notification settings - Fork 86
/
static.lisp
118 lines (96 loc) · 3.08 KB
/
static.lisp
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
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
#|
This file is a part of Clack package.
URL: http://github.com/fukamachi/clack
Copyright (c) 2011 Eitarow Fukamachi <e.arrows@gmail.com>
Clack is freely distributable under the LLGPL License.
|#
(clack.util:namespace clack.middleware.static
(:use :cl
:clack
:anaphora)
(:import-from :clack.app.file
:<clack-app-file>)
(:import-from :alexandria
:starts-with-subseq))
(cl-syntax:use-syntax :annot)
@export
(defclass <clack-middleware-static> (<middleware>)
((path :type (or string function null)
:initarg :path
:accessor static-path)
(root :type pathname
:initarg :root
:initform #p"./"
:accessor static-root))
(:documentation "Clack Middleware to intercept requests for static files."))
(defmethod call ((this <clack-middleware-static>) env)
(let* ((path-info (getf env :path-info))
(path (static-path this)))
(if (null path)
(call-next this env)
(etypecase path
(string
(if (starts-with-subseq path path-info)
;; Serve static file with Clack.App.File
(progn
(setf (getf env :path-info) ; rewrite :PATH-INFO
(subseq path-info (1- (length path))))
(call-app-file this env))
(call-next this env)))
(function
(aif (funcall path path-info)
(progn
(setf (getf env :path-info) it) ; rewrite :PATH-INFO
(call-app-file this env))
(call-next this env)))))))
(defmethod call-app-file ((this <clack-middleware-static>) env)
"Call Clack.App.File."
(clack.component:call
(make-instance '<clack-app-file>
:root (static-root this))
env))
(doc:start)
@doc:NAME "
Clack.Middleware.Static - Middleware to serve static files.
"
@doc:SYNOPSIS "
(run
(builder
(<clack-middleware-static>
:path \"/public/\"
:root #p\"/static-files/\")
app))
"
@doc:DESCRIPTION "
This is a Clack Middleware component for serving static files.
## Slots
* path (Required, String or Function)
<code>path</code> specifies the prefix of URL or a callback to match with requests to serve static files for.
Notice. Don't forget to add slush \"/\" to the end.
* root (Optional, Pathname)
<code>root</code> specifies the root directory to serve static files from.
"
@doc:EXAMPLE "
The following example code would serve */public/foo.jpg* from */static-files/foo.jpg*.
(run
(builder
(<clack-middleware-static>
:path \"/public/\"
:root #p\"/static-files/\")
app))
You can set any function that returns a mapped filename as <code>:path</code>. The above example can be rewritten as following code.
(run
(builder
(<clack-middleware-static>
:path (lambda (path)
(when (ppcre:scan path \"^/public/\")
(subseq path 7)))
:root #p\"/static-files/\")
app))
"
@doc:AUTHOR "
* Eitarow Fukamachi (e.arrows@gmail.com)
"
@doc:SEE "
* Clack.App.File
"