Projekt

Obecné

Profil

Stáhnout (3.56 KB) Statistiky
| Větev: | Revize:
1
'use strict';
2

    
3
const path = require('path');
4

    
5
const mime = require('mime');
6

    
7
const DevMiddlewareError = require('./DevMiddlewareError');
8
const {
9
  getFilenameFromUrl,
10
  handleRangeHeaders,
11
  handleRequest,
12
  ready,
13
} = require('./util');
14

    
15
// Do not add a charset to the Content-Type header of these file types
16
// otherwise the client will fail to render them correctly.
17
const NonCharsetFileTypes = /\.(wasm|usdz)$/;
18

    
19
module.exports = function wrapper(context) {
20
  return function middleware(req, res, next) {
21
    // fixes #282. credit @cexoso. in certain edge situations res.locals is
22
    // undefined.
23
    // eslint-disable-next-line no-param-reassign
24
    res.locals = res.locals || {};
25

    
26
    function goNext() {
27
      if (!context.options.serverSideRender) {
28
        return next();
29
      }
30

    
31
      return new Promise((resolve) => {
32
        ready(
33
          context,
34
          () => {
35
            // eslint-disable-next-line no-param-reassign
36
            res.locals.webpackStats = context.webpackStats;
37
            // eslint-disable-next-line no-param-reassign
38
            res.locals.fs = context.fs;
39

    
40
            resolve(next());
41
          },
42
          req
43
        );
44
      });
45
    }
46

    
47
    const acceptedMethods = context.options.methods || ['GET', 'HEAD'];
48

    
49
    if (acceptedMethods.indexOf(req.method) === -1) {
50
      return goNext();
51
    }
52

    
53
    let filename = getFilenameFromUrl(
54
      context.options.publicPath,
55
      context.compiler,
56
      req.url
57
    );
58

    
59
    if (filename === false) {
60
      return goNext();
61
    }
62

    
63
    return new Promise((resolve) => {
64
      handleRequest(context, filename, processRequest, req);
65
      // eslint-disable-next-line consistent-return
66
      function processRequest() {
67
        try {
68
          let stat = context.fs.statSync(filename);
69

    
70
          if (!stat.isFile()) {
71
            if (stat.isDirectory()) {
72
              let { index } = context.options;
73

    
74
              // eslint-disable-next-line no-undefined
75
              if (index === undefined || index === true) {
76
                index = 'index.html';
77
              } else if (!index) {
78
                throw new DevMiddlewareError('next');
79
              }
80

    
81
              filename = path.posix.join(filename, index);
82
              stat = context.fs.statSync(filename);
83

    
84
              if (!stat.isFile()) {
85
                throw new DevMiddlewareError('next');
86
              }
87
            } else {
88
              throw new DevMiddlewareError('next');
89
            }
90
          }
91
        } catch (e) {
92
          return resolve(goNext());
93
        }
94

    
95
        // server content
96
        let content = context.fs.readFileSync(filename);
97

    
98
        content = handleRangeHeaders(content, req, res);
99

    
100
        let contentType = mime.getType(filename) || '';
101

    
102
        if (!NonCharsetFileTypes.test(filename)) {
103
          contentType += '; charset=UTF-8';
104
        }
105

    
106
        if (!res.getHeader || !res.getHeader('Content-Type')) {
107
          res.setHeader('Content-Type', contentType);
108
        }
109

    
110
        res.setHeader('Content-Length', content.length);
111

    
112
        const { headers } = context.options;
113

    
114
        if (headers) {
115
          for (const name in headers) {
116
            if ({}.hasOwnProperty.call(headers, name)) {
117
              res.setHeader(name, context.options.headers[name]);
118
            }
119
          }
120
        }
121

    
122
        // Express automatically sets the statusCode to 200, but not all servers do (Koa).
123
        // eslint-disable-next-line no-param-reassign
124
        res.statusCode = res.statusCode || 200;
125

    
126
        if (res.send) {
127
          res.send(content);
128
        } else {
129
          res.end(content);
130
        }
131

    
132
        resolve();
133
      }
134
    });
135
  };
136
};
(4-4/6)