You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

365 lines
9.6 KiB

9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
  1. 'use strict'
  2. const test = require('tape')
  3. const request = require('req-then')
  4. const localWebServer = require('../')
  5. const http = require('http')
  6. const PassThrough = require('stream').PassThrough
  7. function launchServer (app, options) {
  8. options = options || {}
  9. const path = `http://localhost:8100${options.path || '/'}`
  10. const server = http.createServer(app.callback())
  11. return server.listen(options.port || 8100, () => {
  12. const req = request(path, options.reqOptions)
  13. if (options.onSuccess) req.then(options.onSuccess)
  14. if (!options.leaveOpen) req.then(() => server.close())
  15. req.catch(err => console.error('LAUNCH ERROR', err.stack))
  16. })
  17. }
  18. function checkResponse (t, status, body) {
  19. return function (response) {
  20. if (status) t.strictEqual(response.res.statusCode, status)
  21. if (body) t.ok(body.test(response.data))
  22. }
  23. }
  24. test('static', function (t) {
  25. t.plan(1)
  26. const app = localWebServer({
  27. log: { format: 'none' },
  28. static: {
  29. root: __dirname + '/fixture',
  30. options: {
  31. index: 'file.txt'
  32. }
  33. }
  34. })
  35. launchServer(app, { onSuccess: response => {
  36. t.ok(/test/.test(response.data))
  37. }})
  38. })
  39. test('serve-index', function (t) {
  40. t.plan(2)
  41. const app = localWebServer({
  42. log: { format: 'none' },
  43. serveIndex: {
  44. path: __dirname + '/fixture',
  45. options: {
  46. icons: true
  47. }
  48. }
  49. })
  50. launchServer(app, { onSuccess: response => {
  51. t.ok(/listing directory/.test(response.data))
  52. t.ok(/class="icon/.test(response.data))
  53. }})
  54. })
  55. test('single page app', function (t) {
  56. t.plan(4)
  57. const app = localWebServer({
  58. log: { format: 'none' },
  59. static: { root: __dirname + '/fixture/spa' },
  60. spa: 'one.txt'
  61. })
  62. const server = launchServer(app, { leaveOpen: true })
  63. request('http://localhost:8100/test').then(response => {
  64. t.strictEqual(response.res.statusCode, 200)
  65. t.ok(/one/.test(response.data))
  66. request('http://localhost:8100/two.txt').then(response => {
  67. t.strictEqual(response.res.statusCode, 200)
  68. t.ok(/two/.test(response.data))
  69. server.close()
  70. })
  71. })
  72. })
  73. test('log: common', function (t) {
  74. t.plan(1)
  75. const stream = PassThrough()
  76. stream.on('readable', () => {
  77. let chunk = stream.read()
  78. if (chunk) t.ok(/GET/.test(chunk.toString()))
  79. })
  80. const app = localWebServer({
  81. log: {
  82. format: 'common',
  83. options: {
  84. stream: stream
  85. }
  86. }
  87. })
  88. launchServer(app)
  89. })
  90. test('compress', function (t) {
  91. t.plan(1)
  92. const app = localWebServer({
  93. compress: true,
  94. log: { format: 'none' },
  95. static: { root: __dirname + '/fixture' }
  96. })
  97. launchServer(
  98. app,
  99. {
  100. reqOptions: { headers: { 'Accept-Encoding': 'gzip' } },
  101. path: '/big-file.txt',
  102. onSuccess: response => {
  103. t.strictEqual(response.res.headers['content-encoding'], 'gzip')
  104. }
  105. }
  106. )
  107. })
  108. test('mime', function (t) {
  109. t.plan(2)
  110. const app = localWebServer({
  111. log: { format: 'none' },
  112. static: { root: __dirname + '/fixture' },
  113. mime: { 'text/plain': [ 'php' ] }
  114. })
  115. launchServer(app, { path: '/something.php', onSuccess: response => {
  116. t.strictEqual(response.res.statusCode, 200)
  117. t.ok(/text\/plain/.test(response.res.headers['content-type']))
  118. }})
  119. })
  120. test('forbid', function (t) {
  121. t.plan(2)
  122. const app = localWebServer({
  123. log: { format: 'none' },
  124. static: { root: __dirname + '/fixture/forbid' },
  125. forbid: [ '*.php', '*.html' ]
  126. })
  127. const server = launchServer(app, { leaveOpen: true })
  128. request('http://localhost:8100/two.php')
  129. .then(response => {
  130. t.strictEqual(response.res.statusCode, 403)
  131. request('http://localhost:8100/one.html')
  132. .then(response => {
  133. t.strictEqual(response.res.statusCode, 403)
  134. server.close()
  135. })
  136. })
  137. })
  138. test('rewrite: local', function (t) {
  139. t.plan(1)
  140. const app = localWebServer({
  141. log: { format: 'none' },
  142. static: { root: __dirname + '/fixture/rewrite' },
  143. rewrite: [ { from: '/two.html', to: '/one.html' } ]
  144. })
  145. launchServer(app, { path: '/two.html', onSuccess: response => {
  146. t.ok(/one/.test(response.data))
  147. }})
  148. })
  149. test('rewrite: proxy', function (t) {
  150. t.plan(2)
  151. const app = localWebServer({
  152. log: { format: 'none' },
  153. static: { root: __dirname + '/fixture/rewrite' },
  154. rewrite: [ { from: '/test/*', to: 'http://registry.npmjs.org/$1' } ]
  155. })
  156. launchServer(app, { path: '/test/', onSuccess: response => {
  157. t.strictEqual(response.res.statusCode, 200)
  158. t.ok(/db_name/.test(response.data))
  159. }})
  160. })
  161. test('rewrite: proxy, two url tokens', function (t) {
  162. t.plan(2)
  163. const app = localWebServer({
  164. log: { format: 'none' },
  165. rewrite: [ { from: '/:package/:version', to: 'http://registry.npmjs.org/:package/:version' } ]
  166. })
  167. launchServer(app, { path: '/command-line-args/1.0.0', onSuccess: response => {
  168. t.strictEqual(response.res.statusCode, 200)
  169. t.ok(/command-line-args/.test(response.data))
  170. }})
  171. })
  172. test('rewrite: proxy with port', function (t) {
  173. t.plan(2)
  174. const one = localWebServer({
  175. log: { format: 'none' },
  176. static: { root: __dirname + '/fixture/one' }
  177. })
  178. const two = localWebServer({
  179. log: { format: 'none' },
  180. static: { root: __dirname + '/fixture/spa' },
  181. rewrite: [ { from: '/test/*', to: 'http://localhost:9000/$1' } ]
  182. })
  183. const server1 = http.createServer(one.callback())
  184. const server2 = http.createServer(two.callback())
  185. server1.listen(9000, () => {
  186. server2.listen(8100, () => {
  187. request('http://localhost:8100/test/file.txt').then(response => {
  188. t.strictEqual(response.res.statusCode, 200)
  189. t.ok(/one/.test(response.data))
  190. server1.close()
  191. server2.close()
  192. })
  193. })
  194. })
  195. })
  196. test('mock: simple response', function (t) {
  197. t.plan(2)
  198. const app = localWebServer({
  199. log: { format: 'none' },
  200. mocks: [
  201. { route: '/test', response: { body: 'test' } }
  202. ]
  203. })
  204. launchServer(app, { path: '/test', onSuccess: response => {
  205. t.strictEqual(response.res.statusCode, 200)
  206. t.ok(/test/.test(response.data))
  207. }})
  208. })
  209. test('mock: method request filter', function (t) {
  210. t.plan(3)
  211. const app = localWebServer({
  212. log: { format: 'none' },
  213. mocks: [
  214. {
  215. route: '/test',
  216. request: { method: 'POST' },
  217. response: { body: 'test' }
  218. }
  219. ]
  220. })
  221. const server = http.createServer(app.callback())
  222. server.listen(8100, () => {
  223. request('http://localhost:8100/test')
  224. .then(checkResponse(t, 404))
  225. .then(() => request('http://localhost:8100/test', { data: 'something' }))
  226. .then(checkResponse(t, 200, /test/))
  227. .then(server.close.bind(server))
  228. })
  229. })
  230. test('mock: accepts request filter', function (t) {
  231. t.plan(3)
  232. const app = localWebServer({
  233. log: { format: 'none' },
  234. mocks: [
  235. {
  236. route: '/test',
  237. request: { accepts: 'text' },
  238. response: { body: 'test' }
  239. }
  240. ]
  241. })
  242. const server = http.createServer(app.callback())
  243. server.listen(8100, () => {
  244. request('http://localhost:8100/test', { headers: { Accept: '*/json' }})
  245. .then(checkResponse(t, 404))
  246. .then(() => request('http://localhost:8100/test', { headers: { Accept: 'text/plain' }}))
  247. .then(checkResponse(t, 200, /test/))
  248. .then(server.close.bind(server))
  249. })
  250. })
  251. test('mock: responses array', function (t) {
  252. t.plan(4)
  253. const app = localWebServer({
  254. log: { format: 'none' },
  255. mocks: [
  256. {
  257. route: '/test',
  258. responses: [
  259. { request: { method: 'GET' }, response: { body: 'get' } },
  260. { request: { method: 'POST' }, response: { body: 'post' } }
  261. ]
  262. }
  263. ]
  264. })
  265. const server = http.createServer(app.callback())
  266. server.listen(8100, () => {
  267. request('http://localhost:8100/test')
  268. .then(checkResponse(t, 200, /get/))
  269. .then(() => request('http://localhost:8100/test', { method: 'POST' }))
  270. .then(checkResponse(t, 200, /post/))
  271. .then(server.close.bind(server))
  272. })
  273. })
  274. test('mock: response function', function (t) {
  275. t.plan(4)
  276. const app = localWebServer({
  277. log: { format: 'none' },
  278. mocks: [
  279. {
  280. route: '/test',
  281. responses: [
  282. { request: { method: 'GET' }, response: ctx => ctx.body = 'get' },
  283. { request: { method: 'POST' }, response: ctx => ctx.body = 'post' }
  284. ]
  285. }
  286. ]
  287. })
  288. const server = http.createServer(app.callback())
  289. server.listen(8100, () => {
  290. request('http://localhost:8100/test')
  291. .then(checkResponse(t, 200, /get/))
  292. .then(() => request('http://localhost:8100/test', { method: 'POST' }))
  293. .then(checkResponse(t, 200, /post/))
  294. .then(server.close.bind(server))
  295. })
  296. })
  297. test('mock: response function args', function (t) {
  298. t.plan(2)
  299. const app = localWebServer({
  300. log: { format: 'none' },
  301. mocks: [
  302. {
  303. route: '/test/:one',
  304. responses: [
  305. { request: { method: 'GET' }, response: (ctx, one) => ctx.body = one }
  306. ]
  307. }
  308. ]
  309. })
  310. const server = http.createServer(app.callback())
  311. server.listen(8100, () => {
  312. request('http://localhost:8100/test/yeah')
  313. .then(checkResponse(t, 200, /yeah/))
  314. .then(server.close.bind(server))
  315. })
  316. })
  317. test('mock: async response function', function (t) {
  318. t.plan(2)
  319. const app = localWebServer({
  320. log: { format: 'none' },
  321. mocks: [
  322. {
  323. route: '/test',
  324. responses: {
  325. response: function (ctx) {
  326. return new Promise((resolve, reject) => {
  327. setTimeout(() => {
  328. ctx.body = 'test'
  329. resolve()
  330. }, 10)
  331. })
  332. }
  333. }
  334. }
  335. ]
  336. })
  337. const server = http.createServer(app.callback())
  338. server.listen(8100, () => {
  339. request('http://localhost:8100/test')
  340. .then(checkResponse(t, 200, /test/))
  341. .then(server.close.bind(server))
  342. })
  343. })