Javascript代码未在PUG/Jade文件上运行 [英] Javascript code not running on PUG/Jade file

查看:62
本文介绍了Javascript代码未在PUG/Jade文件上运行的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在按照本教程使用socket.io实现井字游戏: https://ayushgp.github.io/Tic-Tac-Toe-Socket -IO/.

但是我也想使用登录系统.

当用户登录时,它成功转到了/views/game.pug上的此页面(我将html转换为pug)

doctype html
html
  head
    title Tic Tac Toe
    link(rel='stylesheet', href='/css/main.css')
    link(rel='stylesheet', href='/node_modules/skeleton-css/css/skeleton.css')
  body
    .container
      .menu
        h1 Tic - Tac - Toe
        h3 How To Play
        ol
          li Player 1 Create a new game by entering the username
          li
            | Player 2 Enter another username and the room id that is displayed on first window.
          li Click on join game. 
        h4 Create a new Game
        input#nameNew(type='text', name='name', placeholder='Enter your name', required='')
        button#new New Game
        br
        br
        h4 Join an existing game
        input#nameJoin(type='text', name='name', placeholder='Enter your name', required='')
        input#room(type='text', name='room', placeholder='Enter Game ID', required='')
        button#join Join Game
      .gameBoard
        h2#userHello
        h3#turn
        table.center
          tr
            td
              button#button_00.tile
            td
              button#button_01.tile
            td
              button#button_02.tile
          tr
            td
              button#button_10.tile
            td
              button#button_11.tile
            td
              button#button_12.tile
          tr
            td
              button#button_20.tile
            td
              button#button_21.tile
            td
              button#button_22.tile
    .container
    script(src='/node_modules/jquery/dist/jquery.min.js')
    script(src='/socket.io/socket.io.js')
    script(src='/js/main2.js')

那很好.但是,当我单击ID为#new的按钮时,没有任何反应. 这是我得到的错误: https://i.imgur.com/83p72Ag.png

这是main2.js的相关部分,位于/public/js/main2.js:

  $('#new').on('click', () => {
    const name = $('#nameNew').val();
    if (!name) {
      alert('Please enter your name.');
      return;
    }
    socket.emit('createGame', { name });
    player = new Player(name, P1);
  });

文件的位置:

/public/css/main.css上的

main.css

/node_modules/skeleton-css/css/skeleton.css上的

skeleton.css

/node_modules/jquery/dist/jquery.min.js上的

jquery.min.js /node_modules/socket.io-client/dist/socket.io.js上的

socket.io.js

/public/js/main2.js上的

main2.js

app.js(仅显示相关部分)

const express = require('express');
const path = require('path');
const app = express();
const server = require('http').Server(app);
const io = require('socket.io')(server);
app.use(express.static('.'));
//Load View engine
app.engine('pug', require('pug').__express);
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'pug');

//Set public folder
app.use(express.static(path.join(__dirname, 'public')));

//This get request is sent after the user logs in. It works fine
    app.get('/users/game', function(req, res) {
        res.render('game', {
          title:'Game'
      });
    });

io.on('connection', (socket) => {
//See full code here:https://github.com/ayushgp/tic-tac-toe-socket-io/blob/master/index.js
}

let articles = require('./routes/articles');
let users = require('./routes/users');
app.use('/articles', articles);
app.use('/users', users);

此外,我的main2.js文件与此文件相同: https://github.com/ayushgp/tic-tac-toe-socket-io/blob/master/main.js

完整的app.js代码(相关部分是对用户/游戏的获取请求:

const express = require('express');
const path = require('path');
const app = express();
const server = require('http').Server(app);
const io = require('socket.io')(server);
const mongoose = require('mongoose');
const bodyParser = require('body-parser');
const expressValidator = require('express-validator');
const flash = require('connect-flash');
const session = require('express-session');
const config = require('./config/database');
const passport = require('passport');

let rooms = 0;

app.use(express.static('.'));

mongoose.connect(config.database, {
  useMongoClient: true
});
let db = mongoose.connection;

//Check connection
db.once('open', function(){
  console.log('Connected to MONGOdb')
});

//Check for DB errors
db.on('error', function(err){
  console.log(err);
});

//Bring in models
let Article = require('./models/article');

//Load View Engine
app.engine('pug', require('pug').__express);
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'pug');

// Boddy parser middlware
app.use(bodyParser.urlencoded({ extended: false }))
app.use(bodyParser.json())

//Set public folder
app.use(express.static(path.join(__dirname, 'public')));

//Express Session Middleware
app.set('trust proxy', 1) // trust first proxy
app.use(session({
  secret: 'keyboard cat',
  resave: true,
  saveUninitialized: true,
  cookie: { secure: false }
}));

//Express Messages Middleware
app.use(require('connect-flash')());
app.use(function (req, res, next) {
  res.locals.messages = require('express-messages')(req, res);
  next();
});

//Express Messages Middleware
app.use(expressValidator());

//Passport Config
require('./config/passport')(passport);
//Passport Middleware
app.use(passport.initialize());
app.use(passport.session());

app.get('*', function(req, res, next){
  res.locals.user = req.user || null;
  next();
});


//Home ROute
app.get('/', function(req, res) {
  Article.find({}, function(err, articles){
    if(err){
      console.log(err);
    } else {
      res.render('index', {
        title:'Articles',
        articles: articles
      });
    }
  });
});

app.get('/users/game', function(req, res) {
    res.render('game', {
      title:'Game'
  });
});

io.on('connection', (socket) => {

    // Create a new game room and notify the creator of game.
    socket.on('createGame', (data) => {
        socket.join(`room-${++rooms}`);
        socket.emit('newGame', { name: data.name, room: `room-${rooms}` });
    });

    // Connect the Player 2 to the room he requested. Show error if room full.
    socket.on('joinGame', function (data) {
        var room = io.nsps['/'].adapter.rooms[data.room];
        if (room && room.length === 1) {
            socket.join(data.room);
            socket.broadcast.to(data.room).emit('player1', {});
            socket.emit('player2', { name: data.name, room: data.room })
        } else {
            socket.emit('err', { message: 'Sorry, The room is full!' });
        }
    });

    /**
       * Handle the turn played by either player and notify the other.
       */
    socket.on('playTurn', (data) => {
        socket.broadcast.to(data.room).emit('turnPlayed', {
            tile: data.tile,
            room: data.room
        });
    });

    /**
       * Notify the players about the victor.
       */
    socket.on('gameEnded', (data) => {
        socket.broadcast.to(data.room).emit('gameEnd', data);
    });
});

//Route files
let articles = require('./routes/articles');
let users = require('./routes/users');
app.use('/articles', articles);
app.use('/users', users);


//Start Sever
app.listen(3000, function() {
  console.log('Server running');
});

解决方案

基于您的控制台屏幕抓取,这里至少有两个问题:

  1. 您的script(src='node_modules/jquery/dist/jquery.min.js')服务器端路由(如果您有的话)不起作用,因此jQuery永远不会加载到网页中.因此,没有尝试使用jQuery的方法.

  2. 您的socket.io服务器未在服务器上启动或正确初始化.

为了能够提出修复建议,我们需要查看相关的服务器端代码,并且我们需要知道game.pug中引用的所有资源在服务器端文件系统中的位置(完整路径) .您可能缺少jQuery文件的路由定义,或者路由定义中存在错误.

它确实看起来像main2.js正确加载,尽管由于缺少jQuery它立即遇到错误.


仅供参考,使用如下脚本路径:

script(src='/node_modules/jquery/dist/jquery.min.js')

通常不认为

是一种好的做法,因为它会使您暴露于特定的服务器端文件结构并与之绑定.通常,您会改为执行以下操作:

app.use("/jquery", express.static(path.join(__dirname, "/node_modules/jQuery/dist")));

然后,在客户端中使用它:

script(src='/jquery/jquery.min.js')

现在,您公开显示的唯一目录是/node_modules/jQuery/dist,并且您尚未在客户端网页和服务器端文件结构之间创建硬链接.

您将为需要绘制的每个dist目录重复该过程.按照现在的方式,您已经授予了对整个node_modules服务器端目录的公共访问权限,而这并不是您想做的事情.


此外,当您的socket.io服务器在服务器上正常工作时,它具有socket.io.js的内置路由.您可以只在客户端中使用它:

script(src='/socket.io/socket.io.js')

然后,socket.io服务器将从该路由自动为socket.io.js提供服务器.您不必为此手动创建路由.


要使socket.io正常工作,请对此进行更改;

//Start Sever
app.listen(3000, function() {
  console.log('Server running');
});

对此:

//Start Sever
server.listen(3000, function() {
  console.log('Server running');
});

在这两行代码中,您创建了一个Web服务器并将socket.io绑定到该服务器:

const server = require('http').Server(app);
const io = require('socket.io')(server);

但是,然后使用app.listen(),您创建了另一台Web服务器并启动了它,却从未启动过socket.io连接到的服务器.相反,您想使用server.listen(...)来启动将socket.io附加到的那个.

I'm following this tutorial to implement a tic tac toe game using socket.io: https://ayushgp.github.io/Tic-Tac-Toe-Socket-IO/ .

But I also want to use a login system.

When the user logs in, it successfully goes to this page (I converted html to pug), located on /views/game.pug

doctype html
html
  head
    title Tic Tac Toe
    link(rel='stylesheet', href='/css/main.css')
    link(rel='stylesheet', href='/node_modules/skeleton-css/css/skeleton.css')
  body
    .container
      .menu
        h1 Tic - Tac - Toe
        h3 How To Play
        ol
          li Player 1 Create a new game by entering the username
          li
            | Player 2 Enter another username and the room id that is displayed on first window.
          li Click on join game. 
        h4 Create a new Game
        input#nameNew(type='text', name='name', placeholder='Enter your name', required='')
        button#new New Game
        br
        br
        h4 Join an existing game
        input#nameJoin(type='text', name='name', placeholder='Enter your name', required='')
        input#room(type='text', name='room', placeholder='Enter Game ID', required='')
        button#join Join Game
      .gameBoard
        h2#userHello
        h3#turn
        table.center
          tr
            td
              button#button_00.tile
            td
              button#button_01.tile
            td
              button#button_02.tile
          tr
            td
              button#button_10.tile
            td
              button#button_11.tile
            td
              button#button_12.tile
          tr
            td
              button#button_20.tile
            td
              button#button_21.tile
            td
              button#button_22.tile
    .container
    script(src='/node_modules/jquery/dist/jquery.min.js')
    script(src='/socket.io/socket.io.js')
    script(src='/js/main2.js')

That works fine. But when I click the button with id #new, nothing happens. This is the error I get: https://i.imgur.com/83p72Ag.png .

This is the relevant part of main2.js, located on /public/js/main2.js:

  $('#new').on('click', () => {
    const name = $('#nameNew').val();
    if (!name) {
      alert('Please enter your name.');
      return;
    }
    socket.emit('createGame', { name });
    player = new Player(name, P1);
  });

EDIT:

Files' locations:

main.css on /public/css/main.css

skeleton.css on /node_modules/skeleton-css/css/skeleton.css

jquery.min.js on /node_modules/jquery/dist/jquery.min.js

socket.io.js on /node_modules/socket.io-client/dist/socket.io.js

main2.js on /public/js/main2.js

app.js (only relevant parts are shown):

const express = require('express');
const path = require('path');
const app = express();
const server = require('http').Server(app);
const io = require('socket.io')(server);
app.use(express.static('.'));
//Load View engine
app.engine('pug', require('pug').__express);
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'pug');

//Set public folder
app.use(express.static(path.join(__dirname, 'public')));

//This get request is sent after the user logs in. It works fine
    app.get('/users/game', function(req, res) {
        res.render('game', {
          title:'Game'
      });
    });

io.on('connection', (socket) => {
//See full code here:https://github.com/ayushgp/tic-tac-toe-socket-io/blob/master/index.js
}

let articles = require('./routes/articles');
let users = require('./routes/users');
app.use('/articles', articles);
app.use('/users', users);

Also, my main2.js file is identical to this one: https://github.com/ayushgp/tic-tac-toe-socket-io/blob/master/main.js

EDIT2: Full app.js code (the relevant part is the get request to users/game:

const express = require('express');
const path = require('path');
const app = express();
const server = require('http').Server(app);
const io = require('socket.io')(server);
const mongoose = require('mongoose');
const bodyParser = require('body-parser');
const expressValidator = require('express-validator');
const flash = require('connect-flash');
const session = require('express-session');
const config = require('./config/database');
const passport = require('passport');

let rooms = 0;

app.use(express.static('.'));

mongoose.connect(config.database, {
  useMongoClient: true
});
let db = mongoose.connection;

//Check connection
db.once('open', function(){
  console.log('Connected to MONGOdb')
});

//Check for DB errors
db.on('error', function(err){
  console.log(err);
});

//Bring in models
let Article = require('./models/article');

//Load View Engine
app.engine('pug', require('pug').__express);
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'pug');

// Boddy parser middlware
app.use(bodyParser.urlencoded({ extended: false }))
app.use(bodyParser.json())

//Set public folder
app.use(express.static(path.join(__dirname, 'public')));

//Express Session Middleware
app.set('trust proxy', 1) // trust first proxy
app.use(session({
  secret: 'keyboard cat',
  resave: true,
  saveUninitialized: true,
  cookie: { secure: false }
}));

//Express Messages Middleware
app.use(require('connect-flash')());
app.use(function (req, res, next) {
  res.locals.messages = require('express-messages')(req, res);
  next();
});

//Express Messages Middleware
app.use(expressValidator());

//Passport Config
require('./config/passport')(passport);
//Passport Middleware
app.use(passport.initialize());
app.use(passport.session());

app.get('*', function(req, res, next){
  res.locals.user = req.user || null;
  next();
});


//Home ROute
app.get('/', function(req, res) {
  Article.find({}, function(err, articles){
    if(err){
      console.log(err);
    } else {
      res.render('index', {
        title:'Articles',
        articles: articles
      });
    }
  });
});

app.get('/users/game', function(req, res) {
    res.render('game', {
      title:'Game'
  });
});

io.on('connection', (socket) => {

    // Create a new game room and notify the creator of game.
    socket.on('createGame', (data) => {
        socket.join(`room-${++rooms}`);
        socket.emit('newGame', { name: data.name, room: `room-${rooms}` });
    });

    // Connect the Player 2 to the room he requested. Show error if room full.
    socket.on('joinGame', function (data) {
        var room = io.nsps['/'].adapter.rooms[data.room];
        if (room && room.length === 1) {
            socket.join(data.room);
            socket.broadcast.to(data.room).emit('player1', {});
            socket.emit('player2', { name: data.name, room: data.room })
        } else {
            socket.emit('err', { message: 'Sorry, The room is full!' });
        }
    });

    /**
       * Handle the turn played by either player and notify the other.
       */
    socket.on('playTurn', (data) => {
        socket.broadcast.to(data.room).emit('turnPlayed', {
            tile: data.tile,
            room: data.room
        });
    });

    /**
       * Notify the players about the victor.
       */
    socket.on('gameEnded', (data) => {
        socket.broadcast.to(data.room).emit('gameEnd', data);
    });
});

//Route files
let articles = require('./routes/articles');
let users = require('./routes/users');
app.use('/articles', articles);
app.use('/users', users);


//Start Sever
app.listen(3000, function() {
  console.log('Server running');
});

解决方案

Based on your console screen grab, there are at least two problems here:

  1. Your server-side route (if you even have one) for script(src='node_modules/jquery/dist/jquery.min.js') is not working so jQuery never loads in the web page. Thus, no attempt to use jQuery works.

  2. Your socket.io server is not started or initialized properly on the server.

To be able to suggest fixes, we'd need to see the relevant server-side code and we'd need to know where all resources referenced in game.pug are located in your server-side file system (full path). You are either missing route a definition for the jQuery file or there's an error in the route definition.

It does look like main2.js is loading properly, though it immediately encounters an error because of the missing jQuery.


FYI, using script paths like this:

script(src='/node_modules/jquery/dist/jquery.min.js')

is generally not considered a good practice because it exposes and ties you to a specific server-side file structure. In general, you would do something like this instead:

app.use("/jquery", express.static(path.join(__dirname, "/node_modules/jQuery/dist")));

And, then use this in the client:

script(src='/jquery/jquery.min.js')

Now, the ONLY directory you've exposed to the public is /node_modules/jQuery/dist and you've not created a hard link between client web pages and server-side file structure.

You would repeat that process for each dist directory that you need to draw from. The way you have it now, you have granted public access to your entire node_modules server-side directory which is NOT something you want to do.


Also, when your socket.io server is working appropriately on the server, then it has a built-in route for socket.io.js. You can just use this in the client:

script(src='/socket.io/socket.io.js')

And, the socket.io server will automatically server the socket.io.js from that route. You don't have to manually create a route for that.


To get socket.io working properly, change this;

//Start Sever
app.listen(3000, function() {
  console.log('Server running');
});

to this:

//Start Sever
server.listen(3000, function() {
  console.log('Server running');
});

In these two lines of code, you created a web server and bound socket.io to it:

const server = require('http').Server(app);
const io = require('socket.io')(server);

But, then with app.listen(), you created a different web server and started it and never started the one that socket.io is connected to. Instead, you want to use server.listen(...) to start the one that you attached socket.io to.

这篇关于Javascript代码未在PUG/Jade文件上运行的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆