12

Использование Node.js в качестве простого веб-сервера

18

Я хочу запустить очень простой HTTP-сервер. Каждый GET-запрос к example.com должен получать index.html в качестве обычной HTML-страницы (т.е. с таким же опытом, как при чтении обычных веб-страниц).

Используя приведенный ниже код, я могу читать содержимое index.html. Как мне обслужить index.html как обычную веб-страницу?

var http = require('http');
var fs = require('fs');
var index = fs.readFileSync('index.html');

http.createServer(function (req, res) {
  res.writeHead(200, {'Content-Type': 'text/plain'});
  res.end(index);
}).listen(9615);

Одно из предложений ниже слишком сложное и требует от меня написания строки get для каждого ресурса (CSS, JavaScript, изображения), который я хочу использовать.

Как мне обслужить одну HTML-страницу с некоторыми изображениями, CSS и JavaScript?

5 ответ(ов)

1

Вы можете обойтись без Express и Connect. Node.js предоставляет HTTP-функциональность «из коробки». Все, что вам нужно сделать — это вернуть файл в зависимости от запроса. Вот простой пример:

var http = require('http')
var url = require('url')
var fs = require('fs')

http.createServer(function (request, response) {
    var requestUrl = url.parse(request.url)    
    response.writeHead(200)
    fs.createReadStream(requestUrl.pathname).pipe(response)  // НИКОГДА не используйте синхронные методы fs в production (например, readFileSync) 
}).listen(9615)    

Вот более полный пример, который гарантирует, что запросы не могут получить доступ к файлам вне базового каталога, и включает в себя обработку ошибок:

var http = require('http')
var url = require('url')
var fs = require('fs')
var path = require('path')
var baseDirectory = __dirname   // или любой другой базовый каталог, который вы хотите

var port = 9615

http.createServer(function (request, response) {
    try {
        var requestUrl = url.parse(request.url)

        // Используем path.normalize, чтобы предотвратить доступ к директориям ниже базового каталога
        var fsPath = baseDirectory + path.normalize(requestUrl.pathname)

        var fileStream = fs.createReadStream(fsPath)
        fileStream.pipe(response)
        fileStream.on('open', function() {
            response.writeHead(200)
        })
        fileStream.on('error', function(e) {
            response.writeHead(404)     // предполагаем, что файл не существует
            response.end()
        })
    } catch(e) {
        response.writeHead(500)
        response.end()     // завершаем ответ, чтобы браузеры не зависали
        console.log(e.stack)
    }
}).listen(port)

console.log("Слушаем на порту " + port)

Этот код обеспечивает базовую реализацию HTTP-сервера с обработкой запросов и ошибками. Следите за тем, чтобы не открывать доступ к файлам вне заданного диска и обрабатывайте ошибки корректно.

0

Вы, вероятно, упустили важный момент: вы отправляете заголовок:

Content-Type: text/plain

Если вы хотите, чтобы веб-браузер корректно отображал HTML, вам нужно изменить этот заголовок на:

Content-Type: text/html
0

Чтобы создать простой HTTP-сервер с помощью Express, выполните следующие шаги:

Шаг 1 (в командной строке, убедитесь, что вы перешли в свою папку):

npm install express

Шаг 2: Создайте файл server.js и добавьте в него следующий код:

var fs = require("fs");
var host = "127.0.0.1";
var port = 1337;
var express = require("express");

var app = express();
app.use(express.static(__dirname + "/public")); // используем статические файлы из папки ROOT/public

app.get("/", function(request, response){ // корневая директория
    response.send("Hello!!");
});

app.listen(port, host);

Обратите внимание, что вы должны добавить WATCHFILE (или использовать nodemon) для автоматического перезапуска сервера при изменениях в коде. В приведённом коде только базовый сервер.

Шаг 3: Запустите сервер командой:

node server.js

или, если вы используете nodemon:

nodemon server.js

Если вам нужен более простой способ для запуска простого HTTP-сервера, вы можете использовать пакет http-server. Для этого выполните команду:

npm install -g http-server

Затем перейдите в вашу директорию и выполните:

http-server

Дополнительную информацию можно найти по ссылке: http-server на npm.

0

Быстрый способ:

var express = require('express');
var app = express();
app.use('/', express.static(__dirname + '/../public')); // ← измените путь
app.listen(3000, function() { console.log('Слушаем на порту 3000'); });

Ваш способ:

var http = require('http');
var fs = require('fs');

http.createServer(function (req, res) {
    console.dir(req.url);

    // вы получите '/' или 'index.html' или 'css/styles.css' ...
    // • вам нужно выделить расширение
    // • иметь небольшой массив/объект для определения типа контента
    // • читать файл только тогда, когда это необходимо
    // • и передавать его после установки правильного типа контента

    res.writeHead(200, {'Content-Type': 'text/html'});

    res.end('ok');
}).listen(3001);

В общем, использование Express позволяет вам обойтись без лишней обработки, а также быстро и просто раздавать статические файлы из указанной папки. Если же вы хотите создать сервер, используя чистый Node.js, то это требует большего количества кода для управления файлами и их типами.

0

Вместо использования оператора switch, я считаю более удобным использовать словарь для получения типа контента по расширению файла:

var contentTypesByExtension = {
    'html': "text/html",
    'js':   "text/javascript"
};

...

var contentType = contentTypesByExtension[fileExtension] || 'text/plain';

Таким образом, если расширение файла не найдено в словаре, будет возвращён тип контента по умолчанию - text/plain. Это упрощает код и делает его более читаемым.

Чтобы ответить на вопрос, пожалуйста, войдите или зарегистрируйтесь