Приложение чата Node.js с Socket.io и Express работает на локальном, но не на хостинге - PullRequest
0 голосов
/ 04 сентября 2018

Я сделал пример "Getting старт" для socket.io, он отлично работает на локальном хосте на моем компьютере. Но когда я загружаю его на свой хостинг, он не работает, клиент выдает ошибку 404, пытаясь получить socket.io.js:

<script src="/socket.io/socket.io.js"></script>

Я решил это с помощью другой ссылки (мне не нужно было делать это на локальном хосте):

<script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/2.0.4/socket.io.js"></script>

Но тогда я получаю 404 ошибки постоянно, когда клиент работает на хостинге. Кажется, что сервер Node.js не работает на сервере и не обслуживает файлы socket.io, когда находится на хостинге. Я не получаю эти 404 ошибки, когда я нахожусь на localhost. Вот пример таких звонков:

GET http://localhost/socket.io/?EIO=3&transport=polling&t=MMc5E4X (200 отлично работает на местном)

GET http://tinatest.gearhostpreview.com/socket.io/?EIO=3&transport=polling&t=MMc5E4X (404)

Я получил этот пример на бесплатном хостинге Node.js, чтобы вы могли на него посмотреть, я активировал Node.js 8 на этом сервере, и он работает на порту 80:

http://tinatest.gearhostpreview.com/

Файлы на сервере:

Index.html

<!doctype html>
 <html>
 <head>
  <title>Socket.IO chat</title>
  <style>

  </style>
 </head>
 <body>
  <ul id="messages"></ul>
  <form action="">
    <input id="m" autocomplete="off" /><button>Send</button>
  </form>
 </body>
 <script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/2.0.4/socket.io.js"></script>
 <script src="https://code.jquery.com/jquery-1.11.1.js"></script>
 <script>
    $(function () {
    var socket = io();
    $('form').submit(function(){
    socket.emit('chat message', $('#m').val());
    $('#m').val('');
    return false;
   });
   socket.on('chat message', function(msg){
     $('#messages').append($('<li>').text(msg));
   });
 });
   </script>
 </html>

index.js

var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);

app.get('/', function(req, res){
 res.sendFile(__dirname + '/index.html');
});

io.on('connection', function(socket){
    socket.on('chat message', function(msg){
      io.emit('chat message', msg);
    });
  });

http.listen(80, function(){
  console.log('listening on *:80');
});

package.json

{
 "name": "socket-chat-example",
 "version": "0.0.1",
 "description": "my first socket.io app",
 "dependencies": {
    "express": "^4.15.2",
    "socket.io": "^2.1.1",
    "socket.io-client": "^2.1.1"
 }
}

Я надеюсь, что кто-то может помочь мне сделать это или сказать, почему это невозможно. Если вам нужна дополнительная информация, пожалуйста, спросите, у меня есть другой рабочий сервер, на котором он не работает, я думал, что это был узел на этом сервере, но не сейчас.

Спасибо заранее.

Ответы [ 2 ]

0 голосов
/ 06 сентября 2018

Поскольку я все время думал, что проблема заключалась в том, что у меня не было ни одного узла сервера. Я следовал этим шагам, в моем случае, что я был на бесплатном не выделенном хостинге (без удаленного рабочего стола), я использовал VS Code:

  1. Измените мой хостинг на Windows VPS (с удаленным рабочим столом).
  2. Установите туда node.js.
  3. Создайте отдельное серверное приложение socket.io.
  4. Запустите сервер с node index на локальном хосте: 8080 с кодом cmd.
  5. Установлен iis с панели управления Windows.
  6. Создать отдельный код клиента, который указывает на сервер: VPS_IP_ADRESS:8080
  7. Сборка клиента и копирование содержимого папки dist в корневую папку IIS (наиболее вероятно C:\inetpub\wwroot)
  8. Запустите IIS.

Теперь все отлично работает в моем VPS IP на любом устройстве. Я могу общаться между моими устройствами. Я использовал IIS для клиента, потому что я использую для публикации там. Я думаю, что никак не могу сделать это на моем старом хостинге, так как я прошу поддержку Node, и они сказали мне, что их нет. Ubuntu VPS должен быть более дешевым вариантом, но это для меня сейчас много. Если у вас есть опыт работы с Node + Ubuntu server, попробуйте.

  • Я отредактирую их с окончательным рабочим кодом (скрывая мой IP) через несколько часов
0 голосов
/ 04 сентября 2018

Подумайте о том, что делает сервер Node.js + express. Помимо всего прочего, он может обслуживать файлы на основе различных типов http-запросов. Однако вы должны точно указать, какие типы запросов следует прослушивать (GET, POST и т. Д.) И по каким маршрутам (/, /folder). Вы даже можете прослушивать строки запроса, параметры, тела почтовых сообщений и т. Д. И т. Д. Однако вы можете их определить.

Просмотрите ваш код, какой маршрут вы определили?

Только один: /, и вы разрешаете GET запросы к этому маршруту, и в ответ вы обслуживаете index.html, который имеет всю вашу логику интерфейса, по крайней мере, в этом случае.

Если вы попробуете GET другие маршруты, например /socket.io/, по умолчанию вы получите ошибку 404.

Файл сценария, который вы упомянули, имеет значение src /socket.io, так как у вас нет маршрута для обслуживания кода socket.io, в работе он не работает.

На локальном хосте, если файлы доступны в одном проекте, ваш браузер может разрешить относительный путь на вашем локальном компьютере. Как только проект развернут, относительные пути больше не обращаются к вашей машине, а попадают на ваш маршрутизатор с полным списком URL. Он ожидает, что эти файлы будут обслуживаться.

Вы можете решить проблему на производстве, указав полную ссылку на необходимый socket.io код.

БОЛЬШЕ: Пример:

index.js - см. Комментарии ниже

var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);

/**
 * Your ROUTES
 * in production, when someone goes to http://tinatest.gearhostpreview.com/
 * they are calling your root route "/"
 * Your callback function is sending back index.html from your root directory
 * You add __dirname because you don't know where gearhost is actually putting
 * your stuff. 
 *
 * In production, you can only access server-side files if you serve them
 */
app.get('/', function(req, res){
    res.sendFile(__dirname + '/index.html');
});

/** 
 * ONE WAY TO SERVE JS TO YOUR CLIENT 
 * (there are many better ways of doing this)
 *
 * If you do this, you will not get a 404 error
 */
app.get('/socket.io/socket.io.js', function(req, res){
    // this assumes you have a folder within your root named socket.io 
    // and that it contains socket.io.js, 
    res.sendFile(__dirname + '/socket.io/socket.io.js');
})


io.on('connection', function(socket){
    socket.on('chat message', function(msg){
      io.emit('chat message', msg);
    });
});

http.listen(80, function(){
    console.log('listening on *:80');
});

index.html - только глядя на сценарии

<!-- 
    The src is the URI of an external script, that is, 
    a script external to this particular document.

    Below, the URIs are absolute paths for getting for files hosted by other services.
-->
<script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/2.0.4/socket.io.js"></script>
<script src="https://code.jquery.com/jquery-1.11.1.js"></script>

<!-- 
    You can also use relative paths.

    If your src value is /socket.io, 
    then your page looks for a file
    relative to the current location of itself.

    On localhost, your page has access to files within its own folder
-->

<script src="/socket.io/socket.io.js"></script>

<!--
    HOWEVER, in production, you cannot use relative paths
    UNLESS you are serving your files either as static assets

    via middleware (http://expressjs.com/en/guide/using-middleware.html)
    OR via a public route (http://expressjs.com/en/4x/api.html#app.use)

    You are getting a 404 in production because you aren't serving
    assets.

    BUT!!! you can always use an external 3rd party service
-->
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...