Node.js это кроссплатформенная среда выполнения JavaScript с открытым исходным кодом, которая позволяет разработчикам выполнять JavaScript-код вне веб-браузера. Первоначально она была выпущена в 2009 году Райаном Далем и с тех пор завоевала значительную популярность благодаря своей эффективности и масштабируемости.
Node.js построен на движке JavaScript версии V8, том же движке, что и в Google Chrome, что обеспечивает быстрое выполнение кода. Ключевые особенности Node.js включают в себя
- Архитектура, управляемая событиями: Node.js работает на основе неблокирующей модели ввода-вывода, управляемой событиями, что делает его легким и эффективным.
- Однопоточный цикл обработки событий: Несмотря на то, что он однопоточный, Node.js благодаря механизму цикла обработки событий он может обрабатывать несколько операций одновременно.
- Богатая экосистема: Экосистема npm (Node Package Manager) предлагает обширную библиотеку модулей и пакетов, что упрощает создание приложений.
Распространенные варианты использования Node.js включают веб-серверы, API-сервисы, приложения для общения в режиме реального времени и архитектуру микросервисов.
Цель руководства
В этом руководстве мы расскажем вам о процессе создания простого Node.js приложения. К концу этого руководства у вас будет функциональный веб-сервер, способный обрабатывать основные HTTP-запросы. Это руководство предназначено для начинающих, имеющих базовое представление о JavaScript.
Предпосылки
- Базовые знания JavaScript.
- Node.js установлен на вашем компьютере.
Настройка среды
Чтобы начать разработку с помощью Node.js, вам необходимо установить Node.js и npm, создать каталог проекта и инициализировать новый Node.js проект с npm в нем. Эти шаги позволят настроить среду разработки, что позволит вам эффективно управлять зависимостями и сценариями. Давайте рассмотрим каждый шаг, чтобы убедиться, что ваша среда готова к созданию вашего первого Node.js применение.
Установка Node.js
Прежде чем вы сможете приступить к созданию своего Node.js приложение, которое вам необходимо установить Node.js на вашем компьютере. Выполните следующие действия для установки Node.js:
- Скачать Node.js: Посетите официальный веб-сайт Node.js по адресу https://nodejs.org/ и загрузите версию LTS (долгосрочная поддержка) для вашей операционной системы.
- Установка Node.js: Запустите программу установки и следуйте инструкциям на экране. Программа установки также установит npm (диспетчер пакетов узлов) по умолчанию.
- Проверьте установку: Откройте свой терминал или командную строку и выполните следующие команды для проверки установки:
node -v
npm -v
Эти команды должны отображать установленные версии Node.js и npm соответственно.
Настройка каталога проекта
С Node.js установив его, теперь вы можете настроить каталог своего проекта. Этот каталог будет содержать все файлы, относящиеся к вашему Node.js применение.
Создайте папку проекта
- Создайте новую папку для вашего проекта. Вы можете назвать его my-node-app или любым другим именем, которое вам больше нравится.
mkdir my-node-app
cd my-node-app
Инициализируйте новый проект Node.js
- Используйте npm для инициализации нового проекта Node.js. Эта команда создаст файл package.json, который будет содержать метаданные о вашем проекте и его зависимостях.
npm init
Вам будет предложено ввести подробную информацию о вашем проекте. Вы можете нажать Enter, чтобы принять значения по умолчанию или ввести свои собственные. Конечный файл package.json будет выглядеть примерно так:
{
"name": "my-node-app",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"keywords": [],
"author": "",
"license": "ISC"
}
Общие сведения о файле package.json
Файл package.json является важнейшим компонентом любого Node.js проект. Он содержит различные метаданные, имеющие отношение к проекту, такие как:
- название: Название вашего проекта.
- версия: Текущая версия вашего проекта.
- описание: Краткое описание вашего проекта.
- main: точка входа в ваше приложение (обычно это основной файл JavaScript).
- scripts: скрипты для выполнения различных задач (например, тестирования, сборки).
- ключевые слова: ключевые слова, относящиеся к вашему проекту.
- автор: Имя автора.
- лицензия: Лицензия, по которой распространяется проект.
К настоящему времени у вас должен быть установлен Node.js и настроен каталог проекта с файлом package.json. Эта основа имеет решающее значение для создания любого Node.js приложения.
Понимание основных концепций
Node.js работает на ключевых принципах, которые отличают его от традиционных серверных сред. К ним относятся модули, которые помогают организовать код в повторно используемые компоненты; цикл обработки событий, который позволяет Node.js эффективно обрабатывать асинхронные операции, несмотря на однопоточность; и методы асинхронного программирования, такие как обратные вызовы, обещания и асинхронное ожидание, которые предотвращают блокировку и обеспечивают бесперебойное выполнение операций ввода-вывода. Овладение этими понятиями необходимо для эффективной разработки Node.js.
Модули
Модули являются фундаментальным аспектом Node.js, позволяющим вам организовать свой код в виде повторно используемых компонентов. Модуль – это, по сути, файл JavaScript, который можно импортировать и использовать в других файлах.
- Использование встроенных модулей: Node.js поставляется с несколькими встроенными модулями, такими как fs (файловая система) и http. Чтобы использовать встроенный модуль, он должен быть указан в вашем файле.
const fs = require('fs');
const http = require('http');
- Создание и экспорт пользовательских модулей: Вы можете создавать свои собственные модули, записывая функции или объекты в отдельный файл и экспортируя их.
// greeting.js
function greet(name) {
return `Hello, ${name}!`;
}
module.exports = greet;
Затем вы можете импортировать и использовать этот модуль в другом файле.
// app.js
const greet = require('./greeting');
console.log(greet('World'));
Цикл обработки событий
Цикл обработки событий является центральной частью Node.js, что позволяет ему выполнять неблокирующие операции ввода-вывода. Это означает, что Node.js может обрабатывать несколько операций одновременно, несмотря на то, что он однопоточный.
- Объяснение архитектуры, управляемой событиями: В Node.js операции выполняются асинхронно. Когда операция инициирована, Node.js регистрируется функция обратного вызова и выполняется выполнение других задач. После завершения операции выполняется обратный вызов.
- Как работает цикл обработки событий: Цикл обработки событий непрерывно проверяет стек вызовов и очередь обратного вызова. Если стек вызовов пуст, он обрабатывает следующий обратный вызов в очереди.
console.log('Start');
setTimeout(() => {
console.log('Callback');
}, 1000);
console.log('End');
Вывод:
Start
End
Callback
Асинхронное программирование
Асинхронное программирование имеет решающее значение в Node.js для обработки операций ввода-вывода, не блокируя выполнение других задач.
- Функции обратного вызова: Обратные вызовы – это функции, передаваемые в качестве аргументов другим функциям и выполняемые после завершения определенных задач.
fs.readFile('example.txt', 'utf8', (err, data) => {
if (err) throw err;
console.log(data);
});
- Обещания: Обещания предоставляют способ более эффективной обработки асинхронных операций, позволяя вам объединять операции в цепочки и более изящно обрабатывать ошибки.
const readFile = (filePath) => {
return new Promise((resolve, reject) => {
fs.readFile(filePath, 'utf8', (err, data) => {
if (err) reject(err);
else resolve(data);
});
});
};
readFile('example.txt')
.then(data => console.log(data))
.catch(err => console.error(err));
- Async/Await: Async/await – это синтаксический сахар по сравнению с promises, благодаря которому асинхронный код выглядит и ведет себя больше как синхронный код.
const readFileAsync = async (filePath) => {
try {
const data = await readFile(filePath);
console.log(data);
} catch (err) {
console.error(err);
}
};
readFileAsync('example.txt');
Создание простого веб-сервера
Создание простого веб-сервера в Node.js предполагает использование встроенного http-модуля. Используя метод createServer, вы можете настроить сервер, который прослушивает входящие HTTP-запросы и отвечает соответствующим образом. Это включает в себя обработку различных маршрутов и отправку соответствующего контента, будь то обычный текст, HTML или JSON. Понимание того, как создавать базовый сервер и управлять им, является основополагающим навыком в Node.js развитие.
Использование модуля HTTP
Node.js включает модуль http для создания веб-серверов. Этот модуль предоставляет функциональные возможности, необходимые для обработки HTTP-запросов и ответов.
- Импорт модуля HTTP: Чтобы создать сервер, сначала импортируйте модуль http.
const http = require('http');
- Создание базового сервера: Используйте метод createServer для настройки простого сервера.
const server = http.createServer((req, res) => {
res.statusCode = 200;
res.setHeader('Content-Type', 'text/plain');
res.end('Hello, World!\n');
});
server.listen(3000, '127.0.0.1', () => {
console.log('Server running at http://127.0.0.1:3000/');
});
- Обработка запросов и отправка ответов: В функции обратного вызова create Server вы можете обрабатывать входящие запросы и отправлять ответы.
const server = http.createServer((req, res) => {
if (req.url === '/') {
res.statusCode = 200;
res.setHeader('Content-Type', 'text/html');
res.end('<h1>Home Page</h1>');
} else if (req.url === '/about') {
res.statusCode = 200;
res.setHeader('Content-Type', 'text/html');
res.end('<h1>About Page</h1>');
} else {
res.statusCode = 404;
res.setHeader('Content-Type', 'text/html');
res.end('<h1>Page Not Found</h1>');
}
});
Маршрутизация
Маршрутизация позволяет вам определять различные конечные точки на вашем сервере и отправлять в ответ различный контент на основе URL-адреса запроса.
Настройка основных маршрутов: В приведенном выше коде мы настроили маршруты для домашней страницы и страницы о программе.
Предоставление различного контента по разным путям: Вы можете дополнительно расширить логику маршрутизации, чтобы предоставлять более динамичный контент на основе URL-адреса запроса.
Усовершенствование вашего сервера
Усовершенствование вашего сервера Node.js включает в себя добавление таких функций, как обслуживание статических HTML-файлов и обработка данных форм. Используя модуль fs, вы можете читать и обслуживать HTML-файлы, что обеспечивает более широкий пользовательский опыт. Кроме того, реализация логики для обработки запросов POST и анализа входящих данных форм позволяет вашему серверу динамически взаимодействовать с пользователями, делая ваше приложение более интерактивным и функциональным. Эти улучшения имеют решающее значение для разработки надежных веб-приложений.
Обслуживание HTML-файлов
Вместо отправки обычного текста вы можете использовать HTML-файлы для создания более сложных веб-страниц.
- Использование модуля fs для чтения файлов: Используйте модуль fs для чтения HTML-файлов и отправки их в виде ответов.
const fs = require('fs');
const server = http.createServer((req, res) => {
if (req.url === '/') {
fs.readFile('index.html', (err, data) => {
if (err) {
res.statusCode = 500;
res.setHeader('Content-Type', 'text/plain');
res.end('Internal Server Error\n');
} else {
res.statusCode = 200;
res.setHeader('Content-Type', 'text/html');
res.end(data);
}
});
}
});
- Обслуживание статических HTML-файлов: Сохраните ваш HTML-контент в файле (например, index.html) и предоставьте его, используя описанный выше метод.
Обработка данных формы
Вы можете обрабатывать отправленные формы, анализируя данные входящего запроса.
- Анализ данных входящего запроса: Используйте Node.js streams для сбора данных, отправленных в POST-запросе.
const server = http.createServer((req, res) => {
if (req.method === 'POST' && req.url === '/submit') {
let body = '';
req.on('data', chunk => {
body += chunk.toString();
});
req.on('end', () => {
console.log(body);
res.end('Data received');
});
}
});
- Обработка запросов POST: Убедитесь, что ваша HTML-форма использует метод POST и отправляет данные в правильную конечную точку.
<form action="/submit" method="POST">
<input type="text" name="name" />
<button type="submit">Submit</button>
</form>
В этом подробном руководстве мы рассмотрели основные концепции Node.js, такие как модули, цикл обработки событий и асинхронное программирование. Мы также продемонстрировали, как создать простой веб-сервер с использованием модуля HTTP и улучшить его, предоставляя HTML-файлы и обрабатывая данные форм. Эти основополагающие навыки имеют решающее значение для создания более сложных и масштабируемых Node.js приложения.
Добавление асинхронных функций
В Node.js Включение асинхронных функций важно для поддержки адаптивного приложения. Это включает в себя использование асинхронных файловых операций с модулем fs для чтения и записи файлов без блокировки других процессов, а также выполнение HTTP-запросов с использованием https-модуля для получения данных из внешних источников. Эти методы гарантируют, что ваше приложение сможет выполнять несколько операций одновременно, повышая производительность и удобство работы с пользователем.
Асинхронное чтение и запись файлов
Асинхронные файловые операции имеют решающее значение в Node.js для обеспечения того, чтобы ваш сервер оставался отзывчивым. Использование асинхронных методов из модуля fs позволяет читать и записывать файлы, не блокируя выполнение других операций.
- Использование асинхронных методов fs: Node.js предоставляет асинхронные методы, такие как fs.ReadFile и fs.WriteFile, для обработки файловых операций.
const fs = require('fs');
// Asynchronous file read
fs.readFile('example.txt', 'utf8', (err, data) => {
if (err) {
console.error('Error reading file:', err);
} else {
console.log('File content:', data);
}
});
// Asynchronous file write
const content = 'This is an example content.';
fs.writeFile('example.txt', content, (err) => {
if (err) {
console.error('Error writing file:', err);
} else {
console.log('File written successfully');
}
});
- Реализация файловых операций на вашем сервере: Вы можете встроить эти файловые операции в свой сервер для динамического чтения и записи данных на основе запросов клиента.
const http = require('http');
const fs = require('fs');
const server = http.createServer((req, res) => {
if (req.url === '/read') {
fs.readFile('example.txt', 'utf8', (err, data) => {
if (err) {
res.statusCode = 500;
res.end('Error reading file');
} else {
res.statusCode = 200;
res.setHeader('Content-Type', 'text/plain');
res.end(data);
}
});
} else if (req.url === '/write') {
const content = 'New content added!';
fs.writeFile('example.txt', content, (err) => {
if (err) {
res.statusCode = 500;
res.end('Error writing file');
} else {
res.statusCode = 200;
res.end('File written successfully');
}
});
} else {
res.statusCode = 404;
res.end('Not Found');
}
});
server.listen(3000, () => {
console.log('Server running at http://localhost:3000/');
});
Отправка HTTP-запросов
Node.js также может выступать в качестве клиента для отправки HTTP-запросов другим серверам, что полезно для получения внешних данных.
- Использование модуля https: Модуль https предоставляет методы для отправки HTTP-запросов.
const https = require('https');
const url = 'https://jsonplaceholder.typicode.com/todos/1';
https.get(url, (res) => {
let data = '';
res.on('data', (chunk) => {
data += chunk;
});
res.on('end', () => {
console.log('Data received:', data);
});
}).on('error', (err) => {
console.error('Error:', err);
});
- Обработка асинхронных ответов: Событие data собирает фрагменты ответа, а событие end указывает, когда ответ был получен полностью.
Улучшение структуры кода
Улучшение структуры кода в приложении Node.js предполагает использование промежуточного программного обеспечения для модульной обработки запросов и организации кода в отдельные модули. Функции промежуточного программного обеспечения позволяют вам управлять такими задачами, как ведение журнала, аутентификация и анализ данных, простым и многократно используемым способом, в то время как модульность помогает разбить приложение на управляемые, отдельные компоненты. Это приводит к повышению удобства обслуживания, масштабируемости и удобочитаемости кода.
Использование промежуточного программного обеспечения
Функции промежуточного программного обеспечения необходимы для модульной обработки запросов до того, как они дойдут до конечного обработчика маршрутов.
Что такое промежуточное программное обеспечение? Функции промежуточного программного обеспечения имеют доступ к объекту запроса, объекту ответа и следующей функции промежуточного программного обеспечения в цикле запрос-ответ приложения.
Создание и использование функций промежуточного программного обеспечения: Промежуточное программное обеспечение может использоваться для выполнения таких операций, как ведение журнала, аутентификация и анализ данных.
const express = require('express');
const app = express();
// Simple middleware function
const requestLogger = (req, res, next) => {
console.log(`${req.method} ${req.url}`);
next();
};
// Using middleware in the application
app.use(requestLogger);
app.get('/', (req, res) => {
res.send('Hello, World!');
});
app.listen(3000, () => {
console.log('Server running at http://localhost:3000/');
});
Модульность вашего кода
Разбиение вашего приложения на модули повышает удобство сопровождения и масштабируемость.
- Разделение кода на отдельные модули: Переместите различные части вашего кода в отдельные файлы.
// routes.js
module.exports = (app) => {
app.get('/', (req, res) => {
res.send('Hello, World!');
});
};
- Импорт и использование этих модулей: Импортируйте модуль и используйте его в вашем основном файле приложения.
const express = require('express');
const app = express();
const routes = require('./routes');
routes(app);
app.listen(3000, () => {
console.log('Server running at http://localhost:3000/');
});
Последние штрихи и тестирование
Доработка вашего приложения Node.js включает в себя внедрение надежной обработки ошибок, тщательное тестирование и эффективное ведение журнала. Правильная обработка ошибок гарантирует, что приложение сможет корректно справляться с непредвиденными проблемами, а тестирование с помощью таких инструментов, как Mocha и Chai, гарантирует, что приложение работает должным образом. Ведение журнала позволяет получить представление о работе сервера, помогает в мониторинге и отладке, что в совокупности повышает надежность и удобство обслуживания приложения.
Обработка ошибок
Правильная обработка ошибок гарантирует, что ваше приложение сможет корректно справляться с непредвиденными проблемами.
- Реализация базовой обработки ошибок: используйте блоки try-catch и промежуточное программное обеспечение для обработки ошибок.
app.use((err, req, res, next) => {
console.error(err.stack);
res.status(500).send('Something went wrong!');
});
- Использование блоков Try-Catch и событий ошибок: оберните асинхронный код в блоки try-catch.
app.get('/data', async (req, res) => {
try {
const data = await fetchData();
res.send(data);
} catch (err) {
res.status(500).send('Error fetching data');
}
});
Тестирование вашего приложения
Тестирование имеет решающее значение для обеспечения того, чтобы ваше приложение работало должным образом.
- Ручное тестирование с использованием различных инструментов: Используйте такие инструменты, как Postman и ваш браузер, для ручного тестирования конечных точек.
- Написание простых тестовых сценариев: Автоматизированное тестирование можно проводить с помощью таких платформ, как Mocha и Chai.
const request = require('supertest');
const app = require('../app');
describe('GET /', () => {
it('should return Hello, World!', (done) => {
request(app)
.get('/')
.expect(200)
.expect('Hello, World!', done);
});
});
Регистрация
Ведение журнала помогает отслеживать и отлаживать ваше приложение.
- Добавление ведения журнала для мониторинга активности сервера: используйте журналы консоли или сторонние библиотеки, такие как winston.
const winston = require('winston');
const logger = winston.createLogger({
level: 'info',
format: winston.format.json(),
transports: [
new winston.transports.File({ filename: 'error.log', level: 'error' }),
new winston.transports.File({ filename: 'combined.log' }),
],
});
app.use((req, res, next) => {
logger.info(`${req.method} ${req.url}`);
next();
});
Мы изучили возможность добавления асинхронных функций в ваше приложение Node.js, улучшили структуру кода с помощью промежуточного программного обеспечения и модульности, а также внесли последние изменения, такие как обработка ошибок, тестирование и ведение журнала. Эти методы необходимы для создания надежных, масштабируемых и поддерживаемых приложений Node.js. Пока вы продолжаете развивать свои навыки, эти основополагающие методы послужат основой для процесса разработки Node.js.
Заключение
Мы начали с понимания ключевых концепций, таких как асинхронное программирование и модули, перешли к созданию базового веб-сервера, а затем расширили его, предоставив HTML-файлы и обработав данные форм. Кроме того, мы добавили асинхронные функции для поддержания быстродействия, улучшили структуру кода с помощью промежуточного программного обеспечения и модульности, а также внедрили важные завершающие штрихи, такие как обработка ошибок, тестирование и ведение журнала. Эти основополагающие методы имеют жизненно важное значение для разработки надежных, масштабируемых и поддерживаемых приложений Node.js они дают вам навыки, необходимые для создания эффективных серверных решений.