admin管理员组文章数量:1415664
I recently converted my build process over to using typescript and webpack. Now after resolving most the TS errors, I'm trying to run my site finally.
When I load the site, I'm getting TypeError: res.send is not a function
from my expressjs static server. This code hasn't changed, it's always been the same even when I used gulp and worked fine but for some reason now after using webpack and TS, it's giving me this error now.
The server does indeed start on port 8080 and listens for requests. I start it with "start": "node --trace-warnings dist/server/server.js",
I don't know if it's because I typed the res
param with any
or what it is..
Full Error:
TypeError: res.send is not a function
at dist/server/api.js:58:9
at Layer.handle [as handle_request] (/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/node_modules/express/lib/router/index.js:317:13)
dist (output from TS and webpack)
- TS is outputting my server folder code
- webpack is outputting the rest via copy and bundling
webpack.config.js
const path = require('path');
const { CleanWebpackPlugin } = require('clean-webpack-plugin');
const TerserJSPlugin = require('terser-webpack-plugin');
const HtmlWebPackPlugin = require('html-webpack-plugin');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
const OptimizeCSSAssetsPlugin = require('optimize-css-assets-webpack-plugin');
const CopyPlugin = require('copy-webpack-plugin');
const isProduction = process.env.NODE_ENV === 'production';
const html = () => {
return new HtmlWebPackPlugin({
template: path.resolve(__dirname, 'src/client', 'index.html'),
filename: 'index.html',
hash: true,
});
};
const copyAllOtherDistFiles = () => {
return new CopyPlugin({
patterns: [
{ from: 'src/client/assets', to: 'lib/assets' },
{ from: 'package.json', to: './' },
{ from: 'ext/ink-3.1.10/js/ink-all.min.js', to: 'lib/js' },
{ from: 'ext/ink-3.1.10/js/autoload.min.js', to: 'lib/js' },
{ from: 'ext/js/jquery-2.2.3.min.js', to: 'lib/js' },
{ from: 'ext/ink-3.1.10/css/ink.min.css', to: 'lib/css/ink.min.css' },
{ from: 'feed.xml', to: './' },
{
from: 'src/shared',
to: './shared',
globOptions: {
ignore: ['**/*suppressed.json'],
},
},
],
});
};
module.exports = {
entry: './src/client/index.tsx',
output: {
filename: 'scripts/app.[hash].bundle.js',
publicPath: '/',
path: path.resolve(__dirname, 'dist'),
},
resolve: {
extensions: ['.ts', '.tsx', '.js'],
},
devtool: isProduction ? '' : 'inline-source-map',
devServer: {
writeToDisk: true,
port: 8080,
},
optimization: {
minimizer: [new TerserJSPlugin({}), new OptimizeCSSAssetsPlugin({})],
splitChunks: {
cacheGroups: {
styles: {
name: 'styles',
test: /\.css$/,
chunks: 'all',
enforce: true,
},
},
},
},
module: {
rules: [
{
test: /\.(js)$/,
exclude: /node_modules/,
use: {
loader: 'babel-loader',
},
},
{
test: /\.(tsx|ts)?$/,
use: 'ts-loader',
exclude: /node_modules/,
},
{
test: /\.html$/,
use: [
{
loader: 'html-loader',
},
],
},
{
test: /\.less$/,
use: [MiniCssExtractPlugin.loader, 'css-loader', 'less-loader'],
},
{
test: /\.css$/,
use: [
{
loader: MiniCssExtractPlugin.loader,
options: {
hmr: process.env.NODE_ENV === 'development',
},
},
'css-loader',
],
},
{
test: /\.(woff|woff2|eot|ttf|otf)$/,
loader: 'file-loader',
options: {
outputPath: 'lib/assets/fonts',
},
},
{
test: /\.(png|svg|jpg|gif)$/,
use: ['url-loader'],
},
],
},
plugins: isProduction
? [
new CleanWebpackPlugin(),
new MiniCssExtractPlugin({
filename: isProduction ? 'lib/css/main.[hash].css' : 'main.css',
}),
html(),
copyAllOtherDistFiles(),
]
: [new CleanWebpackPlugin(), html(), copyAllOtherDistFiles()],
};
./tsconfig.json
{
"pilerOptions": {
/* Visit .json to read more about this file */
"target": "ES2015", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', or 'ESNEXT'. */
"module": "es2020", /* Specify module code generation: 'none', 'monjs', 'amd', 'system', 'umd', 'es2015', 'es2020', or 'ESNext'. */
"lib": ["es6", "dom"], /* Specify library files to be included in the pilation. */
"moduleResolution": "node",
"allowJs": true, /* Allow javascript files to be piled. */
"checkJs": true, /* Report errors in .js files. */
"jsx": "react",
"noImplicitAny": true,
"sourceMap": false, /* Generates corresponding '.map' file. */
"rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */
"removeComments": true, /* Do not emit ments to output. */
"strict": true, /* Enable all strict type-checking options. */
"noUnusedLocals": true, /* Report errors on unused locals. */
"noUnusedParameters": true, /* Report errors on unused parameters. */
// "rootDirs": ["."], /* List of root folders whose bined content represents the structure of the project at runtime. */
"typeRoots": [
"node_modules/@types"
], /* List of folders to include type definitions from. */
"esModuleInterop": true,
"allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */
"preserveSymlinks": true, /* Do not resolve the real path of symlinks. */
// "resolveJsonModule": true,
"skipLibCheck": true, /* Skip type checking of declaration files. */
"forceConsistentCasingInFileNames": true
},
"include": [
"src"
],
"exclude": [
"/node_modules",
"/src/server",
"/src/client/js/ink-config.js",
"**/test"
]
}
./client/server/tsconfig.js (where server.ts
and api.ts
live)
{
"extends": "../../tsconfig",
"pilerOptions": {
"outDir": "../../dist/server",
"rootDir": "."
},
"include": ["./*.ts"]
}
./src/server/api.ts
(api.js
is outputted to dist/server)
const pression = require('pression'),
express = require('express'),
historyApi = require('connect-history-api-fallback'),
oneYear = 31536000;
module.exports = express()
.use(pression())
.on('error', function (err: string) {
console.log(err);
})
.use(historyApi())
.use(
express.static('dist', {
maxage: oneYear,
})
)
.use((res: any) => {
res.send('Sorry, Page Not Found');
});
I recently converted my build process over to using typescript and webpack. Now after resolving most the TS errors, I'm trying to run my site finally.
When I load the site, I'm getting TypeError: res.send is not a function
from my expressjs static server. This code hasn't changed, it's always been the same even when I used gulp and worked fine but for some reason now after using webpack and TS, it's giving me this error now.
The server does indeed start on port 8080 and listens for requests. I start it with "start": "node --trace-warnings dist/server/server.js",
I don't know if it's because I typed the res
param with any
or what it is..
Full Error:
TypeError: res.send is not a function
at dist/server/api.js:58:9
at Layer.handle [as handle_request] (/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/node_modules/express/lib/router/index.js:317:13)
dist (output from TS and webpack)
- TS is outputting my server folder code
- webpack is outputting the rest via copy and bundling
webpack.config.js
const path = require('path');
const { CleanWebpackPlugin } = require('clean-webpack-plugin');
const TerserJSPlugin = require('terser-webpack-plugin');
const HtmlWebPackPlugin = require('html-webpack-plugin');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
const OptimizeCSSAssetsPlugin = require('optimize-css-assets-webpack-plugin');
const CopyPlugin = require('copy-webpack-plugin');
const isProduction = process.env.NODE_ENV === 'production';
const html = () => {
return new HtmlWebPackPlugin({
template: path.resolve(__dirname, 'src/client', 'index.html'),
filename: 'index.html',
hash: true,
});
};
const copyAllOtherDistFiles = () => {
return new CopyPlugin({
patterns: [
{ from: 'src/client/assets', to: 'lib/assets' },
{ from: 'package.json', to: './' },
{ from: 'ext/ink-3.1.10/js/ink-all.min.js', to: 'lib/js' },
{ from: 'ext/ink-3.1.10/js/autoload.min.js', to: 'lib/js' },
{ from: 'ext/js/jquery-2.2.3.min.js', to: 'lib/js' },
{ from: 'ext/ink-3.1.10/css/ink.min.css', to: 'lib/css/ink.min.css' },
{ from: 'feed.xml', to: './' },
{
from: 'src/shared',
to: './shared',
globOptions: {
ignore: ['**/*suppressed.json'],
},
},
],
});
};
module.exports = {
entry: './src/client/index.tsx',
output: {
filename: 'scripts/app.[hash].bundle.js',
publicPath: '/',
path: path.resolve(__dirname, 'dist'),
},
resolve: {
extensions: ['.ts', '.tsx', '.js'],
},
devtool: isProduction ? '' : 'inline-source-map',
devServer: {
writeToDisk: true,
port: 8080,
},
optimization: {
minimizer: [new TerserJSPlugin({}), new OptimizeCSSAssetsPlugin({})],
splitChunks: {
cacheGroups: {
styles: {
name: 'styles',
test: /\.css$/,
chunks: 'all',
enforce: true,
},
},
},
},
module: {
rules: [
{
test: /\.(js)$/,
exclude: /node_modules/,
use: {
loader: 'babel-loader',
},
},
{
test: /\.(tsx|ts)?$/,
use: 'ts-loader',
exclude: /node_modules/,
},
{
test: /\.html$/,
use: [
{
loader: 'html-loader',
},
],
},
{
test: /\.less$/,
use: [MiniCssExtractPlugin.loader, 'css-loader', 'less-loader'],
},
{
test: /\.css$/,
use: [
{
loader: MiniCssExtractPlugin.loader,
options: {
hmr: process.env.NODE_ENV === 'development',
},
},
'css-loader',
],
},
{
test: /\.(woff|woff2|eot|ttf|otf)$/,
loader: 'file-loader',
options: {
outputPath: 'lib/assets/fonts',
},
},
{
test: /\.(png|svg|jpg|gif)$/,
use: ['url-loader'],
},
],
},
plugins: isProduction
? [
new CleanWebpackPlugin(),
new MiniCssExtractPlugin({
filename: isProduction ? 'lib/css/main.[hash].css' : 'main.css',
}),
html(),
copyAllOtherDistFiles(),
]
: [new CleanWebpackPlugin(), html(), copyAllOtherDistFiles()],
};
./tsconfig.json
{
"pilerOptions": {
/* Visit https://aka.ms/tsconfig.json to read more about this file */
"target": "ES2015", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', or 'ESNEXT'. */
"module": "es2020", /* Specify module code generation: 'none', 'monjs', 'amd', 'system', 'umd', 'es2015', 'es2020', or 'ESNext'. */
"lib": ["es6", "dom"], /* Specify library files to be included in the pilation. */
"moduleResolution": "node",
"allowJs": true, /* Allow javascript files to be piled. */
"checkJs": true, /* Report errors in .js files. */
"jsx": "react",
"noImplicitAny": true,
"sourceMap": false, /* Generates corresponding '.map' file. */
"rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */
"removeComments": true, /* Do not emit ments to output. */
"strict": true, /* Enable all strict type-checking options. */
"noUnusedLocals": true, /* Report errors on unused locals. */
"noUnusedParameters": true, /* Report errors on unused parameters. */
// "rootDirs": ["."], /* List of root folders whose bined content represents the structure of the project at runtime. */
"typeRoots": [
"node_modules/@types"
], /* List of folders to include type definitions from. */
"esModuleInterop": true,
"allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */
"preserveSymlinks": true, /* Do not resolve the real path of symlinks. */
// "resolveJsonModule": true,
"skipLibCheck": true, /* Skip type checking of declaration files. */
"forceConsistentCasingInFileNames": true
},
"include": [
"src"
],
"exclude": [
"/node_modules",
"/src/server",
"/src/client/js/ink-config.js",
"**/test"
]
}
./client/server/tsconfig.js (where server.ts
and api.ts
live)
{
"extends": "../../tsconfig",
"pilerOptions": {
"outDir": "../../dist/server",
"rootDir": "."
},
"include": ["./*.ts"]
}
./src/server/api.ts
(api.js
is outputted to dist/server)
const pression = require('pression'),
express = require('express'),
historyApi = require('connect-history-api-fallback'),
oneYear = 31536000;
module.exports = express()
.use(pression())
.on('error', function (err: string) {
console.log(err);
})
.use(historyApi())
.use(
express.static('dist', {
maxage: oneYear,
})
)
.use((res: any) => {
res.send('Sorry, Page Not Found');
});
Share
Improve this question
edited Aug 3, 2020 at 3:51
PositiveGuy
asked Aug 3, 2020 at 3:45
PositiveGuyPositiveGuy
20.4k30 gold badges94 silver badges152 bronze badges
1
-
1
replace:
.use((res: any) => {
to:.use((req, res) => {
or:.use((error, req, res, next) => {
– num8er Commented Aug 3, 2020 at 3:52
2 Answers
Reset to default 4As @num8er writes in the ment, you need to correct the signature of the handler you passed to express.use()
. Your code fails because the first parameter in that function is the request object, not the response object. The request object doesn't have a send()
method, so you need to add at least two parameters if you're trying to send a response:
import express from 'express'
const app = express();
app.use((req, res) => {
res.send()
})
The reason Typescript didn't catch this error is because you're using the any
type. To actually get type checking, make sure you don't specify the type of either of those parameters as any
. Instead, either:
- Allow Typescript to correctly infer the type by removing the
any
; or - Specify the type explicitly:
import express from 'express'
const app = express();
app.use((req: express.Request, res: express.Response) => {
})
Finally, make sure @types/express
is installed.
You can check it out here:
https://www.typescriptlang/play/?ssl=1&ssc=1&pln=11&pc=3#code/JYWwDg9gTgLgBAUwB5iggzuuAzKERwDkyqG6hAUBQMYQB268AhmGHALyIpqYAUAlAG4qLMADoArugS9eaAI4AaOD34cAfHADecKgF9+I1pOmyFALi6lMYgEoJ5EjDGU9LJHujsZIDBGvZNHX1+IA
In my case where I have created an express server for my nuxtjs
api
,
res.end({})
works
本文标签: javascriptTypeError ressend is not a function when trying to load siteStack Overflow
版权声明:本文标题:javascript - TypeError: res.send is not a function when trying to load site - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1745170265a2645931.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论