代码之家  ›  专栏  ›  技术社区  ›  Caiz22

如何修复“TypeError:app.use()需要中间件函数”?

  •  1
  • Caiz22  · 技术社区  · 5 年前

    我是新来的 Node.js节点 passport.js signupLogin.js 文件中包含消息,

    app.use()需要一个中间件函数

    我想不出来。我相信这是signupLogin路径,在我添加这个文件之前,应用程序运行良好。

    我的项目文件夹结构及相关文件如下:

    App
    ├── config
    │   ├── database.js
    │   ├── passport.js
    ├── node_modules
    ├── public
    ├── routes
    │   ├── index.js
    │   ├── product_routes.js
    │   ├── signupLogin.js
    ├── views
    ├── app.js
    ├── package-lock.json
    ├── package.json
    

    signupLogin.js:签名

    var express = require('express');
    var router = express.Router();
    module.exports = function(router, passport) {
        router.get('/', function(req, res){
         res.render('index.ejs');
        });
    
        router.get('/login', function(req, res){
         res.render('login.ejs', {message:req.flash('loginMessage')});
        });
    
        router.post('/login', passport.authenticate('local-login', {
         successRedirect: '/profile',
         failureRedirect: '/login',
         failureFlash: true
        }),
         function(req, res){
          if(req.body.remember){
           req.session.cookie.maxAge = 1000 * 60 * 3;
          }else{
           req.session.cookie.expires = false;
          }
          res.redirect('/');
         });
    
         router.get('/signup', function(req, res){
         res.render('signup.ejs', {message: req.flash('signupMessage')});
        });
    
        router.post('/signup', passport.authenticate('local-signup', {
         successRedirect: '/profile',
         failureRedirect: '/signup',
         failureFlash: true
        }));
    
        router.get('/profile', isLoggedIn, function(req, res){
         res.render('profile.ejs', {
          user:req.user
         });
        });
    
        router.get('/logout', function(req,res){
         req.logout();
         res.redirect('/');
        })
       };
    
       function isLoggedIn(req, res, next){
        if(req.isAuthenticated())
         return next();
    
        res.redirect('/');
       }
    

    应用程序js:

    var express = require('express');
    var path = require('path');
    var cookieParser = require('cookie-parser');
    var multer = require('multer');
    var bodyParser = require('body-parser');
    //
    var morgan = require('morgan');
    var session = require('express-session');
    var passport = require('passport');
    var flash = require('connect-flash');
    require('./config/passport')(passport);
    
    const app = express();
    const PORT = 3000;
    
    // view engine setup
    app.set('view engine', 'ejs');
    app.set('views', path.join(__dirname, '/views'));
    
    // Add middleware 
    app.use(express.static(path.join(__dirname, 'public')));
    app.use(bodyParser.json());
    app.use(bodyParser.urlencoded({ extended: true }));
    app.use(multer({ storage: multer.memoryStorage({}) }).any());
    app.use(cookieParser());
    app.use(morgan('dev'));
    app.use(cookieParser());
    app.use(bodyParser.urlencoded({
     extended: true
    }));
    app.use(session({
      secret: 'justasecret',
      resave:true,
      saveUninitialized: true
     }));
    
     app.use(passport.initialize());
     app.use(passport.session());
     app.use(flash());
    
    
    
    // Tell the app to use the defined routes from above
    app.use(require('./routes/index'));
    app.use(require('./routes/product_routes'));
    app.use(require('./routes/signupLogin.js')(app, passport));
    
    
    app.listen(PORT, () => {
      console.log(`The app is running on port ${PORT} at 'http://localhost:${PORT}' (Use CTRL + C to exit)`);
    });
    
    module.exports = app;
    

    护照.js:

    var LocalStrategy = require("passport-local").Strategy;
    
    var mysql = require('mysql');
    var bcrypt = require('bcrypt-nodejs');
    var dbconfig = require('./database');
    var connection = mysql.createConnection(dbconfig.connection);
    
    connection.query('USE ' + dbconfig.database);
    
    module.exports = function(passport) {
     passport.serializeUser(function(user, done){
      done(null, user.id);
     });
    
     passport.deserializeUser(function(id, done){
      connection.query("SELECT * FROM users WHERE id = ? ", [id],
       function(err, rows){
        done(err, rows[0]);
       });
     });
    
     passport.use(
      'local-signup',
      new LocalStrategy({
       usernameField : 'username',
       passwordField: 'password',
       passReqToCallback: true
      },
      function(req, username, password, done){
       connection.query("SELECT * FROM users WHERE username = ? ", 
       [username], function(err, rows){
        if(err)
         return done(err);
        if(rows.length){
         return done(null, false, req.flash('signupMessage', 'That is already taken'));
        }else{
         var newUserMysql = {
          username: username,
          password: bcrypt.hashSync(password, null, null)
         };
    
         var insertQuery = "INSERT INTO users (username, password) values (?, ?)";
         connection.query(insertQuery, [newUserMysql.username, newUserMysql.password], function(err, rows) {
              if(err) {
                console.log(err);
                return done(null, err);
              } else {
                newUserMysql.id = rows.insertId;
                return done(null, newUserMysql);
            }
         });
        }
       });
      })
     );
    
     passport.use(
      'local-login',
      new LocalStrategy({
       usernameField : 'username',
       passwordField: 'password',
       passReqToCallback: true
      },
      function(req, username, password, done){
       connection.query("SELECT * FROM users WHERE username = ? ", [username],
       function(err, rows){
        if(err)
         return done(err);
        if(!rows.length){
         return done(null, false, req.flash('loginMessage', 'No User Found'));
        }
        if(!bcrypt.compareSync(password, rows[0].password))
         return done(null, false, req.flash('loginMessage', 'Wrong Password'));
    
        return done(null, rows[0]);
       });
      })
     );
    };
    

    package.json包:

    {
      "name": "plant-a-tree",
      "version": "0.0.0",
      "private": true,
      "scripts": {
        "start": "start http://localhost:3000 & nodemon node app.js"
      },
      "dependencies": {
        "bcrypt-nodejs": "0.0.3",
        "body-parser": "^1.19.0",
        "connect-flash": "^0.1.1",
        "cookie-parser": "~1.4.3",
        "debug": "~2.6.9",
        "ejs": "~2.5.7",
        "express": "~4.16.0",
        "express-session": "^1.16.1",
        "http-errors": "~1.6.2",
        "morgan": "~1.9.0",
        "multer": "^1.4.1",
        "mysql": "^2.17.1",
        "nodemon": "^1.18.11",
        "passport": "^0.4.0",
        "passport-local": "^1.0.0"
      }
    }
    

    这是我得到的全部错误:

    TypeError: app.use() requires a middleware function
        at Function.use (/Users/charizze/Desktop/PlantATree/node_modules/express/lib/application.js:210:11)
        at Object.<anonymous> (/Users/charizze/Desktop/PlantATree/app.js:47:5)
        at Module._compile (internal/modules/cjs/loader.js:701:30)
        at Object.Module._extensions..js (internal/modules/cjs/loader.js:712:10)
        at Module.load (internal/modules/cjs/loader.js:600:32)
        at tryModuleLoad (internal/modules/cjs/loader.js:539:12)
        at Function.Module._load (internal/modules/cjs/loader.js:531:3)
        at Function.Module.runMain (internal/modules/cjs/loader.js:754:12)
        at startup (internal/bootstrap/node.js:283:19)
        at bootstrapNodeJSCore (internal/bootstrap/node.js:622:3)
    
    2 回复  |  直到 5 年前
        1
  •  3
  •   Alex Kolarski    5 年前

    应用程序使用()

    app.use(function (req, res, next) {
      console.log('Time:', Date.now())
      next()
    })
    

    我看到你的中间件功能在signupLogin.js中:

     function isLoggedIn(req, res, next){
        if(req.isAuthenticated())
         return next();
        res.redirect('/');
       }
    

    但你没有适当的要求。

    app.use(require('./routes/signupLogin.js')(app, passport));
    

    签名登录.js 但它不是有效的中间件功能。

    在我看来你有两个选择。

    1. 分裂 签名登录.js 分成两个文件一个只包含路由,另一个要求不包含路由 应用程序使用 然后创建另一个只有中间件功能的文件,然后使用 应用程序使用
        require('./routes/signupLogin-routes.js')(app, passport)
        app.use(require('./routes/signupLogin-middeware.js'))
    
    1. 要求 签名登录.js 应用程序使用
    require('./routes/signupLogin.js')(app, passport)
    

    应用程序使用 签名登录.js

     app.use(function isLoggedIn(req, res, next){
        if(req.isAuthenticated())
         return next();
    
        res.redirect('/');
       }
    )
    
        2
  •  1
  •   Joao Paulo    5 年前

    我认为你的问题是app.js上的路由器导入。正如错误所说,你需要一个函数在app.use()方法中传递,通过你的路由器。因为您是node.js的新手,所以我的方法是:

    索引.js

    [...]
    const consultas = require("./routes/consultas");
    app.use("/api/consultas", consultas);
    [...]
    

    const router = require("express").Router();
    
    router.get("/", (req, res) => {
      // router handle
    });
    
    module.exports = router;
    

    我希望这听起来不太乱。