st 1.1.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.travis.yml +13 -0
- package/README.md +36 -22
- package/bin/server.js +95 -60
- package/package.json +12 -10
- package/st.js +504 -445
- package/test/basic.js +57 -49
- package/test/cli/basic-test.js +32 -0
- package/test/cli/common.js +108 -0
- package/test/cli/host-test.js +92 -0
- package/test/common.js +42 -30
- package/test/cors.js +11 -13
- package/test/dot-common.js +25 -19
- package/test/dot-false.js +6 -8
- package/test/dot-true.js +8 -8
- package/test/gzip-after-no-gzip.js +12 -19
- package/test/middleware.js +8 -14
- package/test/multi-mount.js +100 -83
- package/test/no-cache.js +8 -10
- package/test/no-cors.js +4 -5
- package/test/no-gzip-accepted-no-cache.js +18 -25
- package/test/no-gzip-accepted.js +18 -24
- package/test/no-gzip.js +4 -9
- package/test/parent-path.js +1 -1
- package/test/passthrough.js +36 -42
- package/test/preset-cache-control.js +31 -27
- package/.npmignore +0 -1
package/.travis.yml
ADDED
package/README.md
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
# st
|
|
2
2
|
|
|
3
|
+
[](https://travis-ci.org/isaacs/st)
|
|
4
|
+
|
|
3
5
|
A module for serving static files. Does etags, caching, etc.
|
|
4
6
|
|
|
5
7
|
## USAGE
|
|
@@ -9,8 +11,8 @@ Here are some very simple usage examples.
|
|
|
9
11
|
Just serve the files in the cwd at the root of the http server url:
|
|
10
12
|
|
|
11
13
|
```javascript
|
|
12
|
-
|
|
13
|
-
|
|
14
|
+
const st = require('st')
|
|
15
|
+
const http = require('http')
|
|
14
16
|
|
|
15
17
|
http.createServer(
|
|
16
18
|
st(process.cwd())
|
|
@@ -22,9 +24,11 @@ Serve the files in static under the /static url. Otherwise do a
|
|
|
22
24
|
different thing:
|
|
23
25
|
|
|
24
26
|
```javascript
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
27
|
+
const path = require('path')
|
|
28
|
+
const mount = st({ path: path.join(__dirname, '/static'), url: '/static' })
|
|
29
|
+
|
|
30
|
+
http.createServer((req, res) => {
|
|
31
|
+
const stHandled = mount(req, res)
|
|
28
32
|
if (stHandled)
|
|
29
33
|
return
|
|
30
34
|
else
|
|
@@ -35,11 +39,11 @@ http.createServer(function(req, res) {
|
|
|
35
39
|
The same sort of thing, but using an express middleware style:
|
|
36
40
|
|
|
37
41
|
```javascript
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
42
|
+
const path = require('path')
|
|
43
|
+
const mount = st({ path: path.join(__dirname, '/static'), url: '/static' })
|
|
44
|
+
|
|
45
|
+
http.createServer((req, res) => {
|
|
46
|
+
mount(req, res, () => res.end('this is not a static file'))
|
|
43
47
|
}).listen(1339)
|
|
44
48
|
```
|
|
45
49
|
|
|
@@ -48,8 +52,10 @@ Serve the files in static under the / url, but only if not some doing
|
|
|
48
52
|
other thing:
|
|
49
53
|
|
|
50
54
|
```javascript
|
|
51
|
-
|
|
52
|
-
|
|
55
|
+
const path = require('path')
|
|
56
|
+
const mount = st({ path: path.join(__dirname, '/static'), url: '/' })
|
|
57
|
+
|
|
58
|
+
http.createServer((req, res) => {
|
|
53
59
|
if (shouldDoThing(req)) {
|
|
54
60
|
doTheThing(req, res)
|
|
55
61
|
} else {
|
|
@@ -62,12 +68,12 @@ Serve the files in static under the / url, but don't serve a 404 if
|
|
|
62
68
|
the file isn't found, so that the rest of the app can handle it:
|
|
63
69
|
|
|
64
70
|
```javascript
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
}).listen(1341)
|
|
71
|
+
const path = require('path')
|
|
72
|
+
const mount = st({ path: path.join(__dirname, '/static'), url: '/', passthrough: true})
|
|
73
|
+
|
|
74
|
+
http.createServer((req, res) => {
|
|
75
|
+
mount(req, res, () => res.end('this is not a static file'))
|
|
76
|
+
}).listen(1341)
|
|
71
77
|
```
|
|
72
78
|
|
|
73
79
|
Serve the files with
|
|
@@ -106,8 +112,8 @@ Here are all the options described with their defaults values and a
|
|
|
106
112
|
few possible settings you might choose to use:
|
|
107
113
|
|
|
108
114
|
```javascript
|
|
109
|
-
|
|
110
|
-
|
|
115
|
+
const st = require('st')
|
|
116
|
+
const mount = st({
|
|
111
117
|
path: 'resources/static/', // resolved against the process cwd
|
|
112
118
|
url: 'static/', // defaults to '/'
|
|
113
119
|
|
|
@@ -160,7 +166,7 @@ var mount = st({
|
|
|
160
166
|
})
|
|
161
167
|
|
|
162
168
|
// with bare node.js
|
|
163
|
-
http.createServer(
|
|
169
|
+
http.createServer((req, res) => {
|
|
164
170
|
if (mount(req, res)) return // serving a static file
|
|
165
171
|
myCustomLogic(req, res)
|
|
166
172
|
}).listen(PORT)
|
|
@@ -168,7 +174,7 @@ http.createServer(function (req, res) {
|
|
|
168
174
|
// with express
|
|
169
175
|
app.use(mount)
|
|
170
176
|
// or
|
|
171
|
-
app.route('/static/:fooblz',
|
|
177
|
+
app.route('/static/:fooblz', (req, res, next) => {
|
|
172
178
|
mount(req, res, next) // will call next() if it doesn't do anything
|
|
173
179
|
})
|
|
174
180
|
```
|
|
@@ -186,6 +192,10 @@ Options:
|
|
|
186
192
|
|
|
187
193
|
-p --port PORT Listen on PORT (default=1337)
|
|
188
194
|
|
|
195
|
+
-H --host HOST Bind address HOST (default=*)
|
|
196
|
+
|
|
197
|
+
-l --localhost Same as "--host localhost"
|
|
198
|
+
|
|
189
199
|
-d --dir DIRECTORY Serve the contents of DIRECTORY (default=cwd)
|
|
190
200
|
|
|
191
201
|
-u --url MOUNTURL Serve the contents at MOUNTURL mount path (default=/)
|
|
@@ -278,3 +288,7 @@ not, will be replaced with `'/'`. If your application depends on url
|
|
|
278
288
|
traversal, then you are encouraged to please refactor so that you do
|
|
279
289
|
not depend on having `..` in url paths, as this tends to expose data
|
|
280
290
|
that you may be surprised to be exposing.
|
|
291
|
+
|
|
292
|
+
Consider using the `--localhost` setting if you don't want other
|
|
293
|
+
people on your local network to read the files served by the command
|
|
294
|
+
line server. This may become the default in a future major version.
|
package/bin/server.js
CHANGED
|
@@ -1,23 +1,36 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
for (
|
|
2
|
+
const st = require('../st.js')
|
|
3
|
+
const http = require('http')
|
|
4
|
+
let port = +(process.env.PORT || 1337)
|
|
5
|
+
let host
|
|
6
|
+
let dir = ''
|
|
7
|
+
let url = '/'
|
|
8
|
+
let dot = false
|
|
9
|
+
let index = true
|
|
10
|
+
let cache = true
|
|
11
|
+
let age = null
|
|
12
|
+
let cors = false
|
|
13
|
+
|
|
14
|
+
for (let i = 2; i < process.argv.length; i++) {
|
|
15
15
|
switch (process.argv[i]) {
|
|
16
16
|
case '-p':
|
|
17
17
|
case '--port':
|
|
18
18
|
port = +(process.argv[++i])
|
|
19
19
|
break
|
|
20
20
|
|
|
21
|
+
case '-H':
|
|
22
|
+
case '--host':
|
|
23
|
+
host = process.argv[++i]
|
|
24
|
+
if (host === '*') {
|
|
25
|
+
host = undefined
|
|
26
|
+
}
|
|
27
|
+
break
|
|
28
|
+
|
|
29
|
+
case '-l':
|
|
30
|
+
case '--localhost':
|
|
31
|
+
host = 'localhost'
|
|
32
|
+
break
|
|
33
|
+
|
|
21
34
|
case '-d':
|
|
22
35
|
case '--dir':
|
|
23
36
|
dir = process.argv[++i]
|
|
@@ -31,9 +44,11 @@ for (var i = 2; i < process.argv.length; i++) {
|
|
|
31
44
|
case '-.':
|
|
32
45
|
case '--dot':
|
|
33
46
|
dot = process.argv[++i]
|
|
34
|
-
if (dot === undefined || dot === 'true')
|
|
35
|
-
|
|
36
|
-
else if (dot
|
|
47
|
+
if (dot === undefined || dot === 'true') {
|
|
48
|
+
dot = true
|
|
49
|
+
} else if (dot === 'false') {
|
|
50
|
+
dot = false
|
|
51
|
+
} else if (dot.charAt(0) === '-') {
|
|
37
52
|
--i
|
|
38
53
|
dot = true
|
|
39
54
|
}
|
|
@@ -47,9 +62,11 @@ for (var i = 2; i < process.argv.length; i++) {
|
|
|
47
62
|
case '-i':
|
|
48
63
|
case '--index':
|
|
49
64
|
index = process.argv[++i]
|
|
50
|
-
if (index === undefined || index === 'true')
|
|
51
|
-
|
|
52
|
-
if (index
|
|
65
|
+
if (index === undefined || index === 'true') {
|
|
66
|
+
index = true
|
|
67
|
+
} else if (index === 'false') {
|
|
68
|
+
index = false
|
|
69
|
+
} else if (index.charAt(0) === '-') {
|
|
53
70
|
--i
|
|
54
71
|
index = true
|
|
55
72
|
}
|
|
@@ -81,50 +98,56 @@ for (var i = 2; i < process.argv.length; i++) {
|
|
|
81
98
|
|
|
82
99
|
case '-co':
|
|
83
100
|
case '--cors':
|
|
84
|
-
cors = true
|
|
101
|
+
cors = true
|
|
85
102
|
break
|
|
86
103
|
}
|
|
87
104
|
}
|
|
88
105
|
|
|
89
106
|
function help () {
|
|
90
107
|
console.log(
|
|
91
|
-
['st'
|
|
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
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
108
|
+
['st',
|
|
109
|
+
'Static file server in node',
|
|
110
|
+
'',
|
|
111
|
+
'Options:',
|
|
112
|
+
'',
|
|
113
|
+
'-h --help Show this help',
|
|
114
|
+
'',
|
|
115
|
+
'-p --port PORT Listen on PORT (default=1337)',
|
|
116
|
+
'',
|
|
117
|
+
'-H --host HOST Bind address HOST (default=*)',
|
|
118
|
+
'',
|
|
119
|
+
'-l --localhost Same as "--host localhost"',
|
|
120
|
+
'',
|
|
121
|
+
'-d --dir DIRECTORY Serve the contents of DIRECTORY (default=cwd)',
|
|
122
|
+
'',
|
|
123
|
+
'-u --url /url Serve at this mount url (default=/)',
|
|
124
|
+
'',
|
|
125
|
+
'-i --index [INDEX] Use the specified INDEX filename as the result',
|
|
126
|
+
' when a directory is requested. Set to "true"',
|
|
127
|
+
' to turn autoindexing on, or "false" to turn it',
|
|
128
|
+
' off. If no INDEX is provided, then it will turn',
|
|
129
|
+
' autoindexing on. (default=true)',
|
|
130
|
+
'',
|
|
131
|
+
'-ni --no-index Same as "--index false"',
|
|
132
|
+
'',
|
|
133
|
+
'-. --dot [DOT] Allow .files to be served. Set to "false" to',
|
|
134
|
+
' disable.',
|
|
135
|
+
'',
|
|
136
|
+
'-n. --no-dot Same as "--dot false"',
|
|
137
|
+
'',
|
|
138
|
+
'-co --cors Enable CORS to serve files to any domain.',
|
|
139
|
+
'',
|
|
140
|
+
'-nc --no-cache Turn off all caching.',
|
|
141
|
+
'',
|
|
142
|
+
'-a --age AGE Max age (in ms) of cache entries.'
|
|
143
|
+
].join('\n'))
|
|
123
144
|
}
|
|
124
145
|
|
|
125
|
-
if (isNaN(port))
|
|
146
|
+
if (isNaN(port)) {
|
|
147
|
+
throw new Error('invalid port: ' + port)
|
|
148
|
+
}
|
|
126
149
|
|
|
127
|
-
|
|
150
|
+
const opt = {
|
|
128
151
|
path: dir,
|
|
129
152
|
url: url,
|
|
130
153
|
index: index,
|
|
@@ -143,19 +166,31 @@ if (cache === false) {
|
|
|
143
166
|
opt.cache = false
|
|
144
167
|
} else {
|
|
145
168
|
if (age) {
|
|
146
|
-
|
|
169
|
+
for (const k in opt.cache) {
|
|
147
170
|
opt.cache[k].maxAge = age
|
|
148
|
-
}
|
|
171
|
+
}
|
|
149
172
|
}
|
|
150
173
|
// maybe other cache-manipulating CLI flags?
|
|
151
174
|
}
|
|
152
175
|
|
|
153
|
-
|
|
176
|
+
const mount = st(opt)
|
|
154
177
|
|
|
155
178
|
http.createServer(function (q, s) {
|
|
156
|
-
if (mount(q, s))
|
|
179
|
+
if (mount(q, s)) {
|
|
180
|
+
return
|
|
181
|
+
}
|
|
157
182
|
s.statusCode = 404
|
|
158
183
|
s.end('not found')
|
|
159
|
-
}).listen(port)
|
|
184
|
+
}).listen(port, host, function () {
|
|
185
|
+
const addr = this.address()
|
|
186
|
+
const port = addr.port
|
|
187
|
+
|
|
188
|
+
if (!host) {
|
|
189
|
+
host = addr.address
|
|
190
|
+
}
|
|
191
|
+
if (/:/.test(host)) {
|
|
192
|
+
host = '[' + host + ']'
|
|
193
|
+
}
|
|
160
194
|
|
|
161
|
-
console.log('listening at http://
|
|
195
|
+
console.log('listening at http://' + host + ':' + port)
|
|
196
|
+
})
|
package/package.json
CHANGED
|
@@ -1,26 +1,28 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "st",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "2.0.0",
|
|
4
4
|
"description": "A module for serving static files. Does etags, caching, etc.",
|
|
5
5
|
"main": "st.js",
|
|
6
6
|
"bin": "bin/server.js",
|
|
7
7
|
"dependencies": {
|
|
8
|
-
"async-cache": "
|
|
9
|
-
"bl": "
|
|
8
|
+
"async-cache": "^1.1.0",
|
|
9
|
+
"bl": "^4.0.0",
|
|
10
10
|
"fd": "~0.0.2",
|
|
11
|
-
"mime": "
|
|
12
|
-
"negotiator": "~0.6.
|
|
11
|
+
"mime": "^2.4.4",
|
|
12
|
+
"negotiator": "~0.6.2"
|
|
13
13
|
},
|
|
14
14
|
"optionalDependencies": {
|
|
15
|
-
"graceful-fs": "
|
|
15
|
+
"graceful-fs": "^4.2.3"
|
|
16
16
|
},
|
|
17
17
|
"devDependencies": {
|
|
18
|
-
"request": "
|
|
19
|
-
"rimraf": "
|
|
20
|
-
"
|
|
18
|
+
"request": "^2.88.0",
|
|
19
|
+
"rimraf": "^3.0.0",
|
|
20
|
+
"standard": "^14.3.1",
|
|
21
|
+
"tap": "^14.9.2"
|
|
21
22
|
},
|
|
22
23
|
"scripts": {
|
|
23
|
-
"
|
|
24
|
+
"lint": "standard",
|
|
25
|
+
"test": "npm run lint && tap test/*.js test/cli/*-test.js"
|
|
24
26
|
},
|
|
25
27
|
"repository": {
|
|
26
28
|
"type": "git",
|