Пример подключения зеркала в веб-сервисе

Пример подключения зеркала в веб-сервисе

Настоящий проект доступен в репозитории GitVerse, в ветке npm-mirror (opens in a new tab), он демонстрирует подключение и установку через зеркало https://npm-mirror.gitverse.ru зависимостей для простейшего веб-приложения, реализующего функционал списка дел (To-Do List).

Подготовительные действия

Для запуска кода JavaScript требуется менеджер пакетов npm и платформа для запуска Node.js.

  1. Установка npm:
sudo apt install npm
  1. Установка Node.js:
sudo apt install nodejs

Структура проекта

gitverse-registry-mirrors/
├── .gitignore
├── .npmrc
├── index.js
├── package.json
├── package-lock.json
├── node_modules/
├── public/
│   ├── index.html
│   └── script.js

.gitignore

Обычно рекомендуется папку node_modules добавлять в .gitignore.

Код .gitignore:

node_modules/

.npmrc

.npmrc — это конфигурационный файл, используемый менеджером пакетов npm для настройки различных параметров.

Добавьте в файл .npmrc gitverse зеркало:

registry=https://npm-mirror.gitverse.ru

Теперь вы можете использовать стандартную команду npm install для загрузки пакетов через зеркало https://npm-mirror.gitverse.ru:

npm install local-storage

index.js

Главный файл в проекте на Node.js. Он служит точкой входа для запуска приложения. Интерпретатор Node.js начинает исполнение кода с этого файла.

Код файла index.js:

// Импорт модулей
const express = require('express');
const path = require('path');
// Создание приложения
const app = express();
const port = 3000;
 
// Настройка статических файлов
app.use(express.static('public'));
 
// Запуск сервера
app.listen(port, () => {
  console.log(`Server listening on port ${port}`);   
 
});

Пояснение к коду файла index.js

Импорт модулей:

  • express — импортируется фреймворк Express.js, который используется для создания веб-приложений;
  • path — импортируется модуль path для работы с путями к файлам.

Создание приложения:

  • const app = express(); — cоздается экземпляр приложения Express.js.

Настройка статических файлов:

  • app.use(express.static('public')); — настраивается middleware для обслуживания статических файлов из папки public. Это позволяет пользователям загружать HTML, CSS, JavaScript и другие файлы напрямую из браузера.

Запуск сервера:

  • app.listen(port, () => { ... }); — запускается сервер на указанном порту (в данном случае, 3000). Когда сервер успешно запущен, в консоль выводится сообщение.

package.json

Данный файл:

  • содержит в формате JSON метаданные проекта, диапазон версий зависимостей ;
  • генерируется командой npm init -y, флаг -y используется для автоматического принятия всех значений по умолчанию при создании файла package.json.

Отройте файл и пропишите в нем:

  • в разделе dependencies — пакет local-storage и фреймворк Express.js:
  "dependencies": {
    "express": "^4.21.1",
    "local-storage": "^1.4.2"
  }
  • в разделе scripts — скприт запуска файла index.js:
"scripts": {
"start": "node index.js"
},

Результирующий код файла package.json:

{
  "name": "gitverse-mirror-example",
  "version": "1.0.0",
  "description": "In the example project, the package name we use from npm is local-storage.",
  "main": "index.js",
  "scripts": {
    "start": "node index.js"
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "dependencies": {
    "express": "^4.21.1",
    "local-storage": "^1.4.2"
  }
}

Описание полей файла package.json

  • name — уникальный идентификатор проекта. Это важно для публикации вашего проекта на npm или других реестрах пакетов;

  • version — версия проекта. Оно используется для контроля версий, управления зависимостями и отслеживания релизов;

  • description — краткое описание проекта;

  • main — главный входной файл вашего проекта. Когда ваш пакет устанавливается как зависимость, этот файл будет точкой входа по умолчанию;

  • scripts — скрипты, которые можно запускать с помощью npm run <имя_скрипта>;

  • keywords — ключевые слова, чтобы помочь пользователям найти ваш пакет на npm;

  • author — указывает автора(ов) проекта. Оно предоставляет информацию об авторе и контакты;

  • license — указывает лицензию, под которой ваш проект выпущен. Оно определяет юридические условия использования и распространения вашего кода;

  • dependencies — версия библиотеки. Символ ^ означает, что при установке будут использоваться все версии, совместимые с указанными, включая патчи и минорные обновления, но не мажорные.

package-lock.json

Файл создается автоматический при установке зависимостей, в нем фиксируются точные данные, версии скачанных зависимостей.

node_modules

Каталог создается автоматический при установки зависимостей, в нем хранятся скачанные зависимости.

index.html

Код создает базовую структуру HTML-страницы приложения.

Код файла index.html:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>To-Do List</title>
</head>
<body>
    <h1>To-Do List</h1>
    <input type="text" id="new-todo" placeholder="Add a new todo">
    <button id="add-todo-btn">Add</button>
    <ul id="todo-list"></ul>
    <script src="script.js"></script>
</body>
</html>

Пояснение к коду файла index.html

  1. Структура документа:
  • <!DOCTYPE html> — объявляет тип документа как HTML5;
  • <html lang="en"> — корневой элемент HTML-документа, устанавливает язык содержимого на английский.
  1. Головной раздел (<head>):

<meta charset="UTF-8"> — устанавливает кодировку символов UTF-8 для корректного отображения текста; <meta name="viewport" content="width=device-width, initial-scale=1.0"> — оптимизирует отображение страницы на разных устройствах, устанавливая ширину области просмотра равной ширине устройства и начальный масштаб равным 1; <title>To-Do List</title> — Задает заголовок страницы, который отображается в браузере.

  1. Тело документа (<body>):
  • <h1>To-Do List</h1> — заголовок первого уровня для обозначения списка дел;
  • <input type="text" id="new-todo" placeholder="Add a new todo"> — поле ввода текста для добавления нового дела. Идентификатор new-todo используется для доступа к этому элементу в JavaScript;
  • <button id="add-todo-btn">Add</button> — кнопка для добавления нового дела в список. Идентификатор add-todo-btn используется для доступа к этой кнопке в JavaScript;
  • <ul id="todo-list"></ul> — неупорядоченный список для отображения добавленных дел. Идентификатор todo-list используется для доступа к этому списку в JavaScript;
  • <script src="script.js"></script> — подключает внешний файл script.js, где будет реализована функциональность приложения.

scripts.js

Код реализует в приложении функциональность добавления новых дел, сохранения их в локальном хранилище и отображения на странице, взаимодействуя с элементами HTML-страницы, описанными в файле index.html.

Код файла scripts.js:

// 1. Получение элементов DOM
const todoList = document.getElementById("todo-list");
const newTodoInput = document.getElementById("new-todo");
const addTodoBtn = document.getElementById("add-todo-btn");
 
// 2. Проверка, поддерживается ли локальное хранилище в браузере
const storage = window.localStorage;
 
// 3. функция получения списка существующих дел из локального хранилища
function getTodos() {
  let todos;
  if (storage.getItem("todos")) {
    todos = JSON.parse(storage.getItem("todos"));
  } else {
    todos = [];
  }
  return todos;
}
 
// 4. Сохранение списка дел в локальном хранилище
function setTodos(todos) {
  storage.setItem("todos", JSON.stringify(todos));
}
 
// 5. Отображения списка дел на странице
function displayTodos(todos) {
  todoList.innerHTML = ""; // Clear the list before displaying
  todos.forEach((todo) => {
    const listItem = document.createElement("li");
    listItem.textContent = todo;
    todoList.appendChild(listItem);
  });
}
 
// 6. Добавление нового дела
function addTodo() {
  const newTodoValue = newTodoInput.value.trim();
  if (!newTodoValue) return; // Don't add empty tasks
 
  const todos = getTodos();
  todos.push(newTodoValue);
  setTodos(todos);
  displayTodos(todos);
  newTodoInput.value = ""; // Clear the input field
}
 
// 7. Инициализацию приложения при загрузке страницы
const todos = getTodos();
displayTodos(todos);
 
// 8. Добавление addEventListener на кнопку addTodoBtn
addTodoBtn.addEventListener("click", addTodo);

Пояснение к коду файла scripts.js

  1. Получение элементов DOM:
  • todoList получает ссылку на элемент <ul> с идентификатором todo-list;
  • newTodoInput получает ссылку на элемент <input> с идентификатором new-todo;
  • addTodoBtn получает ссылку на элемент <button> с идентификатором add-todo-btn.
  1. Проверка, поддерживается ли локальное хранилище в браузере:
  • window.localStorage обращается к объекту localStorage глобального объекта window. Этот объект позволяет веб-приложениям хранить данные пользователя на его компьютере. Если локальное хранилище доступно, то переменная storage будет содержать ссылку на этот объект. В дальнейшем, код может использовать его для сохранения и извлечения данных, таких как список дел, настройки пользователя и другие.
  1. функция получения списка существующих дел из локального хранилища:
  • storage.getItem("todos") проверяет, есть ли в локальном хранилище элемент с ключом "todos";

  • если элемент существует, то функция продолжает к следующему шагу;

  • если элемент не найден, то создается пустой массив todos;

  • если элемент todos найден, то JSON.parse(storage.getItem("todos")) извлекает данные из хранилища и преобразует их из формата JSON обратно в массив JavaScript;

  • функция возвращает массив todos, который содержит список существующих дел, либо пустой массив, если таких дел нет.

  1. Сохранение списка дел в локальном хранилище:
  • JSON.stringify(todos) преобразует массив todos, содержащий список дел, в строку формата JSON. Это необходимо, потому что локальное хранилище может хранить только строки;

  • storage.setItem("todos", JSON.stringify(todos)) сохраняет строку JSON в локальном хранилище под ключом todos.

  1. Отображения списка дел на странице:
  • todoList.innerHTML = ""; очищает содержимое элемента <ul> с идентификатором todo-list, удаляя все существующие элементы списка;

  • todos.forEach((todo) => { ... }) перебирает каждый элемент todo в массиве todos;

  • const listItem = document.createElement("li"); создает новый элемент <li>.

  1. Добавление нового дела:
  • const newTodoValue = newTodoInput.value.trim(); получает значение из поля ввода с идентификатором new-todo и удаляет лишние пробелы с начала и конца строки. Проверка на пустое значение:

  • if (!newTodoValue) return; проверяет, не является ли введенное значение пустым. Если значение пустое, функция завершается, и новое дело не добавляется.

  • const todos = getTodos(); вызывает функцию getTodos() для получения текущего списка дел из локального хранилища.

  • todos.push(newTodoValue); добавляет новое дело, полученное из поля ввода, в конец массива todos.

  • setTodos(todos); вызывает функцию setTodos() для сохранения обновленного списка дел в локальном хранилище.

  • displayTodos(todos); вызывает функцию displayTodos() для обновления отображения списка дел на странице.

  • newTodoInput.value = ""; очищает поле ввода, чтобы пользователь мог сразу ввести новое дело.

  1. Инициализацию приложения при загрузке страницы:
  • const todos = getTodos(); вызывает функцию getTodos() для получения списка существующих дел из локального хранилища;

  • displayTodos(todos); вызывает функцию displayTodos() для отображения полученного списка дел на странице.

  1. Добавление addEventListener на кнопку addTodoBtn:
  • строка addTodoBtn.addEventListener("click", addTodo); настраивает взаимодействие пользователя с приложением;

  • когда пользователь нажимает на кнопку addTodoBtn, браузер генерирует событие клика и вызывается функция добавления нового дела addTodo().

Установка зависимостей

Если вы прописали в фале .npmrc зеркало registry=https://npm-mirror.gitverse.ru, то для установки зависимостей достаточно команды npm install.

Для установки через зеркало всех пакетов, указанных в файле package.json, также можно использовать флаг --registry=https://npm-mirror.gitverse.ru:

npm install --registry=https://npm-mirror.gitverse.ru

В результате появятся:

  • файл package-lock.json, где фиксирует точные данные скаченных зависимостей;
  • каталог node_modules со скаченными зависимостями.

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

Запуск и проверка проекта

Для проверки проекта:

  1. Запустите сервер командой npm run start в терминале.
  2. Откройте в браузере страницу http://localhost:3000, которая ранее была указана в файле index.js.

Прекращение работы сервера

Для прекращения работы сервера нажмите в терминале сочетание клавиш Ctrl+C.