diff --git a/,github/workflows/main.yaml b/,github/workflows/main.yaml
new file mode 100644
index 0000000..ff1ec41
--- /dev/null
+++ b/,github/workflows/main.yaml
@@ -0,0 +1,19 @@
+name: Publish Docker
+
+on:
+ push:
+ branches: [main]
+
+jobs:
+ build:
+ runs-on: ubuntu-latest
+ steps:
+ - uses: actions/checkout@main
+ - name: Publish to registry
+ uses: elgohr/Publish-Docker-Github-Action@v4
+ with:
+ registry: docker.pkg.github.com
+ name: docker.pkg.github.com/pestsov-v/node-js-without-frameworks/v2.0.0
+ username: ${{ github.actor }}
+ password: ${{ secrets.GITHUB_TOKEN }}
+ tags: "develop"
\ No newline at end of file
diff --git a/.idea/vcs.xml b/.idea/vcs.xml
new file mode 100644
index 0000000..94a25f7
--- /dev/null
+++ b/.idea/vcs.xml
@@ -0,0 +1,6 @@
+
+
+
+
+
+
\ No newline at end of file
diff --git a/.idea/workspace.xml b/.idea/workspace.xml
new file mode 100644
index 0000000..a8c4349
--- /dev/null
+++ b/.idea/workspace.xml
@@ -0,0 +1,46 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 1654424616716
+
+
+ 1654424616716
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..b264299
--- /dev/null
+++ b/README.md
@@ -0,0 +1,90 @@
+# Создание приложений на Node.js без фреймворков
+
+Данное приложение затрагивает реализацию как интерфейса командной строки (command line interface - далее CLI), графический
+интерфейс (Graphic user interface - далее GUI), проще говоря - frontend часть сайта так и набор эндпоинтов (application programming interface - далее API),
+проще говоря Backend часть сайта.
+
+Приложение написано на JavaScript ES5 синтаксисе в без архитектурного стиля в первой версии. Переписано на ES7 синтаксис
+со слоеной, модульной, архитектурой во второй версии. И переписано вновь уже на typescript в третьей версии приложения.
+
+## Предназначение и стек технологий
+
+Приложение предназначено для подробного описания и реализации приложений на Node.js без использования фреймворков, а также реализация
+приложений на различных синтаксисах JavaScript и языке TypeScript
+Стек технологий:
+- платформа Node.js
+- fs / path - для работы с файлами
+- crypto - для шифрования паролей
+- url - для работы с URL адресом запроса
+- dns - для проверок существующих IP адресов сайтов
+- os / v8 - для вывода статистики по работе системы
+- readline - для создания CLI
+- child_process - для создания отдельного процесса под тяжелые задачи
+- zlib - для сжатия файлов логирования
+- http / https - для взаимодействия backend и frontend части посредством работы с протоколами
+- util - для создания различных debug режимов, для разделения обработки ошибок в различных частях системы
+
+## Запуск приложения
+
+Предлагается три варианта запустить и протестировать приложение: Запуск через архив на хост машине,
+и запуск непосредственно через Heroku instance (при запуске через Heroku будет запущена обрезанная версия приложения - без CLI и работы с API).
+
+### Запуск на хост машине
+
+Чтобы запустить приложение на локальной хост машине, необходимо скачать проект из Git-репозитория и разархивировать его, после чего:
+- Если версия проекта v1.0.0 или v2.0.0, то зайти в папку server и запустить проект с помощью команды: `node index.js`.
+- Если версия проекта v3.0.0, то зайти в папку server и запустить проект с помощью команды: `npm run dev`.
+
+### Запуск через Heroku
+
+Перейти по ссылке.
+
+## Оглавление
+- [Создание приложений на Node.js без фреймворков](#создание-приложений-на-nodejs-без-фреймворков)
+ - [Предназначение и стек технологий](#предназначение-и-стек-технологий)
+ - [Запуск приложения](#запуск-приложения)
+ - [Запуск на хост машине](#запуск-на-хост-машине)
+ - [Запуск через Heroku](#запуск-через-heroku)
+ - [Оглавление](#оглавление)
+ - [v1.0.0 - JavaScript ES5](#v100---javascript-es5)
+ - [v2.0.0 - JavaScript ES7](#v200---javascript-es7)
+ - [v3.0.0 - TypeScript](#v300---typescript)
+ - [API](#api)
+ - [Command line interface (CLI)](#command-line-interface-cli)
+ - [Graphical user interface (GUI)](#graphical-user-interface-gui)
+
+## [v1.0.0 - JavaScript ES5](wiki/v1.0.0.md)
+
+Здесь описан краткий обзор версии. Чтобы посмотреть полную информацию о версии нажмите: [v1.0.0 - JavaScript ES5](wiki/v1.0.0.md)
+
+Топорный вариант работы, когда весь модуль находится в одном файле. Использование var, а главный архитектурный вариант работы - создание
+объектов - контейнеров, куда как свойства добавляются методы - анонимные функции-callback.
+
+Результат? Разработка проходит быстро и топорно, но само приложение является абсолютно не масштабируемым, поскольку через больше становится
+глобальные объекты - контейнеры, тем сложнее поддерживать его зависимости.
+
+
+
+## [v2.0.0 - JavaScript ES7](wiki/v2.0.0.md)
+
+Здесь описан краткий обзор версии. Чтобы посмотреть полную информацию о версии нажмите: [v2.0.0 - JavaScript ES7](wiki/v2.0.0.md)
+
+Архитектурный вариант, когда сущности разделены, а каждый элемент сущности выведен в отдельный свой файл. Простым языком, если в первой версии
+все сущности были внутри одного объекта - контейнера, то теперь каждая сущность - это отдельная ветка с кодом. Сам код является слоёным:
+все константы и строковые значения вынесены в отдельным файл, работа с базой данных или файловой системой в файл сервиса, который реализовывает только эту логику
+и т.д.
+
+Результат? Разработка проходит средне по времени, но само приложение является масштабируемым, поскольку сущности и функционал разделен как и файлами, так и классами.
+
+## [v3.0.0 - TypeScript](wiki/v3.0.0.md)
+
+Здесь описан краткий обзор версии. Чтобы посмотреть полную информацию о версии нажмите: [v3.0.0 - TypeScript](wiki/v3.0.0.md)
+
+Больше типизации и возможность масштабировать приложение? TypeScript это предоставляет, проверяя все входящие данные и результат выполнения функций. Таким образом позволяя
+организовать более производительный код из-за большей работы Turbofan интерпретатора и нормализации bytecode.
+
+## API
+
+## Command line interface (CLI)
+
+## Graphical user interface (GUI)
\ No newline at end of file
diff --git a/server/config/variables.config.js b/server/config/variables.config.js
index 4a15bdf..616af0f 100644
--- a/server/config/variables.config.js
+++ b/server/config/variables.config.js
@@ -20,8 +20,8 @@ env.staging = {
};
env.testing = {
- httpPort: 4010,
- httpsPort: 4011,
+ httpPort: 4012,
+ httpsPort: 4013,
envName: "staging",
hashingSecret: "ThisIsSecret",
maxChecks: 5,
diff --git a/server/data/checks/5w1lnrzfxpiton97vlop.json b/server/data/checks/5w1lnrzfxpiton97vlop.json
index 4bb2bc7..5980023 100644
--- a/server/data/checks/5w1lnrzfxpiton97vlop.json
+++ b/server/data/checks/5w1lnrzfxpiton97vlop.json
@@ -1 +1 @@
-{"id":"5w1lnrzfxpiton97vlop","userPhone":"1234567890","protocol":"http","url":"22.com","method":"get","code":[200,201],"time":1,"state":"down","lastChecked":1654013853778}
\ No newline at end of file
+{"id":"5w1lnrzfxpiton97vlop","userPhone":"1234567890","protocol":"http","url":"22.com","method":"get","code":[200,201],"time":1,"state":"down","lastChecked":1654778635729}
\ No newline at end of file
diff --git a/server/data/checks/ehc676fk8musszifow4a.json b/server/data/checks/ehc676fk8musszifow4a.json
index dd61d50..58c8a6c 100644
--- a/server/data/checks/ehc676fk8musszifow4a.json
+++ b/server/data/checks/ehc676fk8musszifow4a.json
@@ -1 +1 @@
-{"id":"ehc676fk8musszifow4a","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654013853490}
\ No newline at end of file
+{"id":"ehc676fk8musszifow4a","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654778635203}
\ No newline at end of file
diff --git a/server/data/checks/se910nfq1x8xr9bo64jz.json b/server/data/checks/se910nfq1x8xr9bo64jz.json
index 80f34d0..3e2da4e 100644
--- a/server/data/checks/se910nfq1x8xr9bo64jz.json
+++ b/server/data/checks/se910nfq1x8xr9bo64jz.json
@@ -1 +1 @@
-{"id":"se910nfq1x8xr9bo64jz","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654013853490}
\ No newline at end of file
+{"id":"se910nfq1x8xr9bo64jz","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654778635203}
\ No newline at end of file
diff --git a/server/data/logs/5w1lnrzfxpiton97vlop-1654013853294.gz.b64 b/server/data/logs/5w1lnrzfxpiton97vlop-1654013853294.gz.b64
deleted file mode 100644
index 0b45c55..0000000
--- a/server/data/logs/5w1lnrzfxpiton97vlop-1654013853294.gz.b64
+++ /dev/null
@@ -1 +0,0 @@
-H4sIAAAAAAAACmWQwW6EMAxE7/0Mn6MqCWEDXPmA9l7tAYEpqCFGibdb7Yp/r7Oteulx7PGbke8wLjh+QHeHdYIO6qsJMd3mr31liq3/DLSDgkvG9LpQRLEYW7n65JtWy2JPxDRSkPnC/LCmIqx9HmkTuSEvVMjvyCJHmoTxZrVWVpuzAl43GRgFmQcu+ImuUYxhyNyXaijH5lQ7bSrfeOvaQwFdWOhYWmNKlKCbh5BRQcK8U8zYP2Iq3Rz/wEPAxH8HJf5l7n9+8BvTOG+9O56+AZjMrlMcAQAA
\ No newline at end of file
diff --git a/server/data/logs/5w1lnrzfxpiton97vlop.log b/server/data/logs/5w1lnrzfxpiton97vlop.log
index b773f8a..702d701 100644
--- a/server/data/logs/5w1lnrzfxpiton97vlop.log
+++ b/server/data/logs/5w1lnrzfxpiton97vlop.log
@@ -1 +1 @@
-{"check":{"id":"5w1lnrzfxpiton97vlop","userPhone":"1234567890","protocol":"http","url":"22.com","method":"get","code":[200,201],"time":1,"state":"down","lastChecked":1654013847274},"outcome":{"error":false,"responseCode":308},"state":"down","alert":false,"timeOfCheck":1654013853778}
+{"check":{"id":"5w1lnrzfxpiton97vlop","userPhone":"1234567890","protocol":"http","url":"22.com","method":"get","code":[200,201],"time":1,"state":"down","lastChecked":1654764249334},"outcome":{"error":false,"responseCode":308},"state":"down","alert":false,"timeOfCheck":1654778635729}
diff --git a/server/data/logs/ehc676fk8musszifow4a-1654013786767.gz.b64 b/server/data/logs/ehc676fk8musszifow4a-1654013786767.gz.b64
deleted file mode 100644
index 40e26ec..0000000
--- a/server/data/logs/ehc676fk8musszifow4a-1654013786767.gz.b64
+++ /dev/null
@@ -1 +0,0 @@
-H4sIAAAAAAAACmWQsW7DMAxE934GZyGQZMVxvPoD0r3oIMi0ZcQ2DYlGgAT+91Jt0aUjj8d3B74gRAx3aF8w9dACxlBf6uHeLHvOz2mgh/OgYM+Y3iOtKJbqWhmr9dldZbElYgo0ix6Zt2JNZRiJxhlPgRaRFuRIhT4iyxioF86HMJTV5lMBT4sIVkFmzyWip8cqxtln7ko9lGNTn502Vd2YxtpDAe0sdCzNMSVK0A5+zqggYd5ozdh9x1TaHP/AfsbEfwcl/jZ0P3/4jbk467Q+3r4AAVIUiyABAAA=
\ No newline at end of file
diff --git a/server/data/logs/ehc676fk8musszifow4a-1654013853294.gz.b64 b/server/data/logs/ehc676fk8musszifow4a-1654013853294.gz.b64
deleted file mode 100644
index da870b6..0000000
--- a/server/data/logs/ehc676fk8musszifow4a-1654013853294.gz.b64
+++ /dev/null
@@ -1 +0,0 @@
-H4sIAAAAAAAACtVQu26EQAzs7zNcryJgYXm0fEDSR1egxbDoAKNdo5MO8e/x3ikp0qdIZXk8nhnNAdahvUFzwNRDA+isKc1wq5Y9hMc00D3vQMEe0H84WlEoutZpliRFXsth88RkaRbcMW+R6uMyEo0zvllaBFqQHUX1EVlWS73ofIqGypL0qoCnRYBMQeCOo0VP91WIcxe4jfFQnlNT5EmqyzyTcSqgnUUdY3L0njw0QzcHVOAxbLQGbJ82+kn+JdzN6PnnIdq/D+2rh2+bytSmOC/Hv+vnFfyv+6nysjT6vHwBA+Wil0ACAAA=
\ No newline at end of file
diff --git a/server/data/logs/ehc676fk8musszifow4a.log b/server/data/logs/ehc676fk8musszifow4a.log
index 3526559..d1ab29d 100644
--- a/server/data/logs/ehc676fk8musszifow4a.log
+++ b/server/data/logs/ehc676fk8musszifow4a.log
@@ -1 +1 @@
-{"check":{"id":"ehc676fk8musszifow4a","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654013847763},"outcome":{"error":false,"responseCode":301},"state":"down","alert":false,"timeOfCheck":1654013853489}
+{"check":{"id":"ehc676fk8musszifow4a","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654764249018},"outcome":{"error":false,"responseCode":301},"state":"down","alert":false,"timeOfCheck":1654778635203}
diff --git a/server/data/logs/se910nfq1x8xr9bo64jz-1654013786767.gz.b64 b/server/data/logs/se910nfq1x8xr9bo64jz-1654013786767.gz.b64
deleted file mode 100644
index 2afeb0a..0000000
--- a/server/data/logs/se910nfq1x8xr9bo64jz-1654013786767.gz.b64
+++ /dev/null
@@ -1 +0,0 @@
-H4sIAAAAAAAACmWQwU7DMAyG7zyGzxFK0q5re+0DwB1xKKnbDtK6OJ42beq74wDiwsny79/fb/kOYcbwAe0dTgO0kLBxdh0/3bW+cvNGVfl+AwPnhPw804pqKZrCeWsPZaODjUkoUFR9FtmylXMzEU0RHwMtKi0oM2X6hKJtoEE5L8ow3rpXA3JaVPAGkvSSIwa6rGqMfZIun4e67KpDaV1R1a72x90AnUXpmC9HZmJoxz4mNMCYNloTdt8xhXX7P3AfkeVvIcc/jd3PH35jjqXXsj98AdiMTyAgAQAA
\ No newline at end of file
diff --git a/server/data/logs/se910nfq1x8xr9bo64jz-1654013853294.gz.b64 b/server/data/logs/se910nfq1x8xr9bo64jz-1654013853294.gz.b64
deleted file mode 100644
index 621a3ab..0000000
--- a/server/data/logs/se910nfq1x8xr9bo64jz-1654013853294.gz.b64
+++ /dev/null
@@ -1 +0,0 @@
-H4sIAAAAAAAACtVQQW6EMAy87zN8jqoEQpZw5QHbe9UDBQPbAqaJV10V8fc6u2oPvffQk+XxeGY0G7Qjtm9QbXDuoIKI3uilfzfX8hr8Czn7+gkKLhHD40gLCiX3ucm0LqyXwxqIqaVJ8JF5TdSQloFomPChpVmgGXmkpD4gy9pSJzpPoqEybZ4V8HkWIFMQueFk0dHHIsSpiVyneCjPxhVWm/xoMxm7ArqwqGNKjiFQgKpvpogKAsaVloj1zSa/kX8JNxMG/nlI9qe+vvfwbVM67+x+2P5dP/fgf91PaZ0/FvvhC7hd5dxAAgAA
\ No newline at end of file
diff --git a/server/data/logs/se910nfq1x8xr9bo64jz-1654778635027.gz.b64 b/server/data/logs/se910nfq1x8xr9bo64jz-1654778635027.gz.b64
new file mode 100644
index 0000000..58a283e
--- /dev/null
+++ b/server/data/logs/se910nfq1x8xr9bo64jz-1654778635027.gz.b64
@@ -0,0 +1 @@
+H4sIAAAAAAAACmWQsW7DMAxE934GZyGQZNmpvPoD0j3o4Mq0nVY2XYlBgwb+91ItkKUjj8d3B94hzBg+oL3DZYAWMnqj1/HT3J5vyb9R496/QcE1Y3qZaUWxVL4yVuvaeVlsiZgCRdFn5q1YUxkmoiniIdAi0oI8U6FPyDIGGoRzFoay2rwq4MsiglWQuecSMdDXKsbYZ+5KPZRj09Tu2DjrbH2sdgV0ZaFjaY4pUYJ27GNGBQnzRmvG7jem0mb/B+4jJn4clPjT2P394RHjtfH70w/hX7y2IAEAAA==
\ No newline at end of file
diff --git a/server/data/logs/se910nfq1x8xr9bo64jz.log b/server/data/logs/se910nfq1x8xr9bo64jz.log
index a0870d8..6e94933 100644
--- a/server/data/logs/se910nfq1x8xr9bo64jz.log
+++ b/server/data/logs/se910nfq1x8xr9bo64jz.log
@@ -1 +1 @@
-{"check":{"id":"se910nfq1x8xr9bo64jz","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654013846975},"outcome":{"error":false,"responseCode":301},"state":"down","alert":false,"timeOfCheck":1654013853490}
+{"check":{"id":"se910nfq1x8xr9bo64jz","userPhone":"3931200549","protocol":"http","url":"google.com","method":"get","code":[200,201],"time":2,"state":"down","lastChecked":1654764249019},"outcome":{"error":false,"responseCode":301},"state":"down","alert":false,"timeOfCheck":1654778635202}
diff --git a/server/src/core/color.js b/server/src/core/color.js
new file mode 100644
index 0000000..5e6e903
--- /dev/null
+++ b/server/src/core/color.js
@@ -0,0 +1,9 @@
+const RED = "\x1b[31m%s\x1b[0m";
+const GREEN = "\x1b[32m%s\x1b[0m";
+
+const color = {
+ red: RED,
+ green: GREEN,
+};
+
+module.exports = color;
diff --git a/server/src/core/tester/tester.constants.js b/server/src/core/tester/tester.constants.js
new file mode 100644
index 0000000..4454017
--- /dev/null
+++ b/server/src/core/tester/tester.constants.js
@@ -0,0 +1,7 @@
+exports.START_REPOST_MESSAGE = "НАЧАЛО ОТЧЁТА ТЕСТИРОВАНИЯ";
+exports.END_REPOST_MESSAGE = "КОНЕЦ ОТЧЁТА ТЕСТИРОВАНИЯ";
+exports.START_ERRORS_MESSAGE = "НАЧАЛО ДЕТАЛЕЙ ВОЗНИКШИХ ОШИБОК";
+exports.END_ERRORS_MESSAGE = "КОНЕЦ ДЕТАЛЕЙ ВОЗНИКШИХ ОШИБОК";
+exports.TOTAL_TEST_MESSAGE = "Всего тестов: ";
+exports.PASS_MESSAGE = "Успешно пройденых: ";
+exports.FAIL_MESSAGE = "Не пройденых: ";
diff --git a/server/src/core/tester/tester.controller.js b/server/src/core/tester/tester.controller.js
new file mode 100644
index 0000000..19153c7
--- /dev/null
+++ b/server/src/core/tester/tester.controller.js
@@ -0,0 +1,15 @@
+const http = require("http");
+
+const TesterHelper = require("./tester.helper");
+
+class TesterController {
+ getRequest(path, callback) {
+ const reqDetails = TesterHelper.makeGetRequest(path);
+ const req = http.request(reqDetails, (res) => {
+ callback(res);
+ });
+ req.end();
+ }
+}
+
+module.exports = new TesterController();
diff --git a/server/src/core/tester/tester.files.js b/server/src/core/tester/tester.files.js
new file mode 100644
index 0000000..4b2ab8f
--- /dev/null
+++ b/server/src/core/tester/tester.files.js
@@ -0,0 +1,8 @@
+const { unit, user } = require("../../modules/api/user/tests/tests.index");
+
+tests = {};
+
+tests.unit = unit;
+tests.user = user;
+
+module.exports = tests;
diff --git a/server/src/core/tester/tester.graphic.js b/server/src/core/tester/tester.graphic.js
new file mode 100644
index 0000000..a044c60
--- /dev/null
+++ b/server/src/core/tester/tester.graphic.js
@@ -0,0 +1,15 @@
+class TesterGraphic {
+ emptyLine() {
+ console.log("");
+ }
+
+ headerLine(header) {
+ console.log(`--------------------${header}--------------------`);
+ }
+
+ resultLine(message, result) {
+ console.log(message, result);
+ }
+}
+
+module.exports = new TesterGraphic();
diff --git a/server/src/core/tester/tester.helper.js b/server/src/core/tester/tester.helper.js
new file mode 100644
index 0000000..1a2af39
--- /dev/null
+++ b/server/src/core/tester/tester.helper.js
@@ -0,0 +1,55 @@
+const config = require("../../../config/variables.config");
+const color = require("../color");
+const TesterGraphic = require("./tester.graphic");
+
+const {
+ START_REPOST_MESSAGE,
+ START_ERRORS_MESSAGE,
+ END_ERRORS_MESSAGE,
+ END_REPOST_MESSAGE,
+ TOTAL_TEST_MESSAGE,
+ PASS_MESSAGE,
+ FAIL_MESSAGE,
+} = require("./tester.constants");
+
+class TesterHelper {
+ makeGetRequest(path) {
+ const requestDetails = {
+ protocol: "http:",
+ hostname: "localhost",
+ port: config.httpPort,
+ path: path,
+ headers: {
+ "Content-Type": "application/json",
+ },
+ };
+
+ return requestDetails;
+ }
+
+ produceTestReport(limit, successes, errors) {
+ TesterGraphic.emptyLine();
+ TesterGraphic.headerLine(START_REPOST_MESSAGE);
+ TesterGraphic.emptyLine();
+ TesterGraphic.resultLine(TOTAL_TEST_MESSAGE, limit);
+ TesterGraphic.resultLine(PASS_MESSAGE, successes);
+ TesterGraphic.resultLine(FAIL_MESSAGE, errors.length);
+ TesterGraphic.emptyLine();
+
+ if (errors.length > 0) {
+ TesterGraphic.headerLine(START_ERRORS_MESSAGE);
+ TesterGraphic.emptyLine();
+ errors.forEach(function (testError) {
+ console.log(color.red, testError.name);
+ console.log(testError.error);
+ TesterGraphic.emptyLine();
+ });
+ TesterGraphic.headerLine(END_ERRORS_MESSAGE);
+ }
+
+ TesterGraphic.headerLine(END_REPOST_MESSAGE);
+ process.exit(0);
+ }
+}
+
+module.exports = new TesterHelper();
diff --git a/server/src/core/tester/tester.module.js b/server/src/core/tester/tester.module.js
new file mode 100644
index 0000000..a216b2e
--- /dev/null
+++ b/server/src/core/tester/tester.module.js
@@ -0,0 +1,5 @@
+process.env.NODE_ENV = "testing";
+const tests = require("./tester.files");
+const TesterRunner = require("./tester.runner");
+
+TesterRunner.runTests(tests);
diff --git a/server/src/core/tester/tester.runner.js b/server/src/core/tester/tester.runner.js
new file mode 100644
index 0000000..0428ecc
--- /dev/null
+++ b/server/src/core/tester/tester.runner.js
@@ -0,0 +1,59 @@
+const color = require("../color");
+const TesterHelper = require("./tester.helper");
+
+class TesterRunner {
+ countTests(tests) {
+ let counter = 0;
+ for (const key in tests) {
+ if (tests.hasOwnProperty(key)) {
+ const subTests = tests[key];
+ for (const testName in subTests) {
+ if (subTests.hasOwnProperty(testName)) {
+ counter++;
+ }
+ }
+ }
+ }
+
+ return counter;
+ }
+
+ runTests(tests) {
+ let errors = [];
+ let successes = 0;
+ let counter = 0;
+
+ const limit = this.countTests(tests);
+ for (const key in tests) {
+ if (tests.hasOwnProperty(key)) {
+ const subTests = tests[key];
+ for (const testName in subTests) {
+ if (subTests.hasOwnProperty(testName)) {
+ (function () {
+ const tmpTestName = testName;
+ const testValue = subTests[testName];
+ try {
+ testValue(function () {
+ console.log(color.green, tmpTestName);
+ counter++;
+ successes++;
+ TesterHelper.produceTestReport(limit, successes, errors);
+ });
+ } catch (e) {
+ errors.push({
+ name: testName,
+ error: e,
+ });
+ console.log(color.green, tmpTestName);
+ counter++;
+ TesterHelper.produceTestReport(limit, successes, errors);
+ }
+ })();
+ }
+ }
+ }
+ }
+ }
+}
+
+module.exports = new TesterRunner();
diff --git a/server/src/modules/api/user/tests/tests.index.js b/server/src/modules/api/user/tests/tests.index.js
new file mode 100644
index 0000000..a30a1d1
--- /dev/null
+++ b/server/src/modules/api/user/tests/tests.index.js
@@ -0,0 +1,4 @@
+module.exports = {
+ user: require("./user.e2e"),
+ unit: require("./user.spec"),
+};
diff --git a/server/src/modules/api/user/tests/user.e2e.js b/server/src/modules/api/user/tests/user.e2e.js
new file mode 100644
index 0000000..cc70420
--- /dev/null
+++ b/server/src/modules/api/user/tests/user.e2e.js
@@ -0,0 +1,31 @@
+const app = require("../../../../../index");
+const statusCode = require("../../../../core/base/statusCode");
+
+const assert = require("assert");
+const TesterController = require("../../../../core/tester/tester.controller");
+
+const user = {};
+
+user["app. should start without throwing"] = (done) => {
+ assert.doesNotThrow(() => {
+ app((err) => {
+ done();
+ });
+ }, TypeError);
+};
+
+user["/api/users should respond to GET with 400"] = (done) => {
+ TesterController.getRequest("/api/users", function (res) {
+ assert.equal(res.statusCode, statusCode.BAD_REQUEST);
+ done();
+ });
+};
+
+user["A random path should respond to GET with 404"] = (done) => {
+ TesterController.getRequest("/this/path/shouldnt/exist", function (res) {
+ assert.equal(res.statusCode, statusCode.NOT_FOUND);
+ done();
+ });
+};
+
+module.exports = user;
diff --git a/server/test/unit.js b/server/src/modules/api/user/tests/user.spec.js
similarity index 51%
rename from server/test/unit.js
rename to server/src/modules/api/user/tests/user.spec.js
index 353c801..5d92027 100644
--- a/server/test/unit.js
+++ b/server/src/modules/api/user/tests/user.spec.js
@@ -1,24 +1,11 @@
-const helpers = require("../src/helpers");
const assert = require("assert");
-const logs = require("../modules/logger/logger.module");
+const LoggerModule = require("../../../logger/logger.module");
-var unit = {};
-
-unit["helpers.getNumber should return a number"] = function (done) {
- var val = helpers.getNumber();
- assert.equal(typeof val, "number");
- done();
-};
-
-unit["helpers.getNumber should return 1"] = function (done) {
- var val = helpers.getNumber();
- assert.equal(val, 1);
- done();
-};
+const unit = {};
unit["logs.list should callback a false error and an array of log names"] =
function (done) {
- logs.list(true, function (err, logFileNames) {
+ LoggerModule.list(true, function (err, logFileNames) {
assert.equal(err, false);
assert.ok(logFileNames instanceof Array);
assert.ok(logFileNames.length > 1);
@@ -30,7 +17,7 @@ unit[
"logs.truncate should not throw if the logId does not exist, should callback an error instead"
] = function (done) {
assert.doesNotThrow(function () {
- logs.truncate("I do not exist", function (err) {
+ LoggerModule.truncate("I do not exist", function (err) {
assert.ok(err);
done();
});
diff --git a/server/src/modules/cli/cli.graphic.js b/server/src/modules/cli/cli.graphic.js
index 9b9dce7..e37301c 100644
--- a/server/src/modules/cli/cli.graphic.js
+++ b/server/src/modules/cli/cli.graphic.js
@@ -10,12 +10,12 @@ class CLIGraphic {
console.log(line);
}
- verticalSpace = function (lines) {
+ verticalSpace(lines) {
lines = CLIValidator.linesValidate(lines);
for (let i = 0; i < lines; i++) {
console.log("");
}
- };
+ }
centered(str) {
str = CLIValidator.strValidate(str);
diff --git a/server/test/api.js b/server/test/api.js
deleted file mode 100644
index 859a6be..0000000
--- a/server/test/api.js
+++ /dev/null
@@ -1,48 +0,0 @@
-var app = require("../index");
-const assert = require("assert");
-const http = require("http");
-const config = require("../config/variables.config");
-
-var api = {};
-var helpers = {};
-
-helpers.makeGetRequest = function (path, callback) {
- var requestDetails = {
- protocol: "http:",
- hostname: "localhost",
- port: config.httpPort,
- path: path,
- headers: {
- "Content-Type": "application/json",
- },
- };
-
- var req = http.request(requestDetails, function (res) {
- callback(res);
- });
- req.end();
-};
-
-api["app.init should start without throwing"] = function (done) {
- assert.doesNotThrow(function () {
- app.init(function (err) {
- done();
- });
- }, TypeError);
-};
-
-api["/api/users should respond to GET with 400"] = function (done) {
- helpers.makeGetRequest("/api/users", function (res) {
- assert.equal(res.statusCode, 400);
- done();
- });
-};
-
-api["A random path should respond to GET with 404"] = function (done) {
- helpers.makeGetRequest("/this/path/shouldnt/exist", function (res) {
- assert.equal(res.statusCode, 404);
- done();
- });
-};
-
-module.exports = api;
diff --git a/server/test/index.js b/server/test/index.js
deleted file mode 100644
index ac84679..0000000
--- a/server/test/index.js
+++ /dev/null
@@ -1,91 +0,0 @@
-process.env.NODE_ENV = "testing";
-
-_app = {};
-
-_app.tests = {};
-
-_app.tests.unit = require("./unit");
-_app.tests.api = require("./api");
-
-_app.countTests = function () {
- var counter = 0;
- for (var key in _app.tests) {
- if (_app.tests.hasOwnProperty(key)) {
- var subTests = _app.tests[key];
- for (var testName in subTests) {
- if (subTests.hasOwnProperty(testName)) {
- counter++;
- }
- }
- }
- }
-
- return counter;
-};
-
-_app.runTests = function () {
- var errors = [];
- var successes = 0;
- var limit = _app.countTests();
- var counter = 0;
- for (var key in _app.tests) {
- if (_app.tests.hasOwnProperty(key)) {
- var subTests = _app.tests[key];
- for (var testName in subTests) {
- if (subTests.hasOwnProperty(testName)) {
- (function () {
- var tmpTestName = testName;
- var testValue = subTests[testName];
- try {
- testValue(function () {
- console.log("\x1b[32m%s\x1b[0m", tmpTestName);
- counter++;
- successes++;
- if (counter == limit) {
- _app.produceTestReport(limit, successes, errors);
- }
- });
- } catch (e) {
- errors.push({
- name: testName,
- error: e,
- });
- console.log("\x1b[31m%s\x1b[0m", tmpTestName);
- counter++;
- if (counter == limit) {
- _app.produceTestReport(limit, successes, errors);
- }
- }
- })();
- }
- }
- }
- }
-};
-
-_app.produceTestReport = function (limit, successes, errors) {
- console.log("");
- console.log("--------------------BEGIN TEST REPORT--------------------");
- console.log("");
- console.log("Total Test: ", limit);
- console.log("Pass: ", successes);
- console.log("Fail: ", errors.length);
- console.log("");
-
- if (errors.length > 0) {
- console.log("--------------------BEGIN ERROR DETAILS--------------------");
- console.log("");
- errors.forEach(function (testError) {
- console.log("\x1b[31m%s\x1b[0m", testError.name);
- console.log(testError.error);
- console.log("");
- });
- console.log("--------------------END ERROR DETAILS--------------------");
- }
-
- console.log("");
- console.log("--------------------END TEST REPORT--------------------");
- process.exit(0);
-};
-
-_app.runTests();
diff --git a/wiki/v1.0.0.md b/wiki/v1.0.0.md
new file mode 100644
index 0000000..cf733c4
--- /dev/null
+++ b/wiki/v1.0.0.md
@@ -0,0 +1,28 @@
+## Оглавление
+
+- [Оглавление](#оглавление)
+- [Архитектура](#архитектура)
+- [Сборная солянка](#сборная-солянка)
+
+## Архитектура
+
+Топорный вариант архитектуры - весь функционал одинаковой направленности находится в одном файле. Сам код описан с целью дополнительно показать Callback Hell и в дальнейшем, в версии v2.0.0 реализацию выгребания подобной ямы callback'ов.
+
+[](https://postimg.cc/N51fxv30)
+
+Где:
+- `data.js` - вся логика по работе с файловой системой, поскольку в проекте используется не база данных, а непосредственно файловая система.
+- `handlers.js` - API, которое привязано в один объект - контейнер.
+- `helpers.js` - специфические функции, которые нацелены реализовать узкий функционал.
+- `lib.constants.js` - вынесение за скобки отдельных констант, как предысловие к версии v2.0.0.
+- `user.exception.js` - аналогично как и с `lib.constants.js`
+- `config.js` - описание приватных переменных.
+- `index.js` - входная точка приложения.
+
+## Сборная солянка
+
+Когда говорится о объектах контейнерах имеется в виду следующее:
+
+[](https://postimg.cc/wtWhTm2n)
+
+есть объект `handlers`, в который складываются, к примеру все методы по работе с API. В местах же пользования методов - идёт ссылка на объект с необходимой вложеностью к конкретному методу.
\ No newline at end of file
diff --git a/wiki/v2.0.0.md b/wiki/v2.0.0.md
new file mode 100644
index 0000000..b3851f0
--- /dev/null
+++ b/wiki/v2.0.0.md
@@ -0,0 +1,139 @@
+## Оглавление
+
+- [Оглавление](#оглавление)
+- [Архитектура проекта](#архитектура-проекта)
+- [Серверная архитектура](#серверная-архитектура)
+- [Core (ядро приложения)](#core-ядро-приложения)
+- [Modules (модули)](#modules-модули)
+ - [Application programming interface (API)](#application-programming-interface-api)
+ - [Command line interface (CLI)](#command-line-interface-cli)
+ - [Graphical user interface (GUI)](#graphical-user-interface-gui)
+ - [Logger](#logger)
+ - [Worker](#worker)
+
+## Архитектура проекта
+
+Проект состоит из двух частей:
+- `client` - код для работы с клиентом.
+- `server` - код работы с сервером.
+
+[v2-0-0-root.png](https://postimg.cc/QKr56GqJ)
+
+О клиенте рассуждать нечего - свалочный код, который нужный, только чтобы показать, каким может быть GUI.
+Сервер состоит из следующих директорий:
+- config - конфигурации и приватные переменные.
+- data - база данных, в которой хранятся различные документы.
+- src - програмный код.
+- test - файлы с тестами.
+
+## Серверная архитектура
+
+Серверная архитектура состоит из следующих директорий:
+- `core` - функции и сущности, которые формируют ядро приложения.
+- `modules` - различные модули - сегменты работы приложения.
+- `utils` - специфические функции, которые имеют узкое предназначение.
+
+## Core (ядро приложения)
+
+Ядро приложения наличивают различные перечисления, которые используются по всему приложению, а также файлы с логикой работы с файловой системой.
+
+[](https://postimg.cc/PPNHJpHY)
+
+К примеру в файла `statusCode.js` перечислены все HTTP код статуса, который используются во всём приложения. Возникает вопрос, зачем его создавать? Если у Вас есть много мест, где используются одни и те же сущности, зачем повышать вероятность ошибок и опечаток вручную вставлять стрингу? Создавая переменную с значением этого статус код, по всему коду программы будет использоватся одна и таже переменная, что формирует чистоту кода.
+
+## Modules (модули)
+
+Приложения находит следующие модули:
+- Application programming interface (API) - эндпоинты связи с сервером, которые используются в графическом интерфейсе и предоставляют функционал работы с данными.
+- Command line interface (CLI) - модуль работы с интерфейсом командной строки.
+- Graphical user interface (GUI) - модуль работы с HTML страничками.
+- Logger - модуль работы с файлами логирования, их сжатия, разжатия, чтения и т.д.
+- Worker - системные файлы, которые регулярно создают файлы логирования.
+
+### Application programming interface (API)
+
+API состоит из трёх различных сущностей, каждая из которых едина в своей файловой архитектуре:
+
+[](https://postimg.cc/jC4622cx)
+
+Существуют следующие сущности:
+- 404 - если произошло использование несуществущего эндпоинта - пользователь попадёт на страничку 404
+- check - модуль чеков. Каждый пользователь может сформировать чек. Реализовывает CRUD функционал с зависимостями по токену авторизациию и сущности пользователя.
+- token - модуль авторизации, отвечает за токены, которые имеют свои сроки годноти и создаются для каждого пользователя отдельно. Явялется организатором сессий.
+- user - модуль пользователя.
+
+Каждая стандартная сущность (на примере модуля user) состоит из следующих файлов:
+- `user.constants.js` - все константы, которые используются в модуле вынесены в отдельный файл. Таким образом унифицируя ответа с сервера и очищая код.
+- `user.controller.js` - класс логики получения данных по эндпоинтам, передача их в сервис, а так же реализация ответов по эндпоинту обратно на клиент.
+- `user.exception.js` - все варианты ответов от сервера.
+- `user.helper.js` - класс со специфическими функциями, которые не касаются работы с базой данных, валидации или маршрутизацией данных.
+- `user.module.js` - класс с итоговыми методами, которые могут быть использованы в других модулям.
+- `user.router.js` - описание всех методов приложения.
+- `user.service.js` - класс по работе с базой данных.
+- `user.validator.js` - класс валидации данных, которые приходят на сервер по различным эндпоинтом.
+
+### Command line interface (CLI)
+
+Интерфейс командной строки позволяет получить данные путём введения различных ключей. Структура самого модуля:
+
+[](https://postimg.cc/mzBD5QnK)
+
+Где:
+- `constants` - ярчащий пример понимание масштабируемости - если константы можно сгрупировать, то сами константы разделяются по файлам, а файлы падают в папку общей направленности - константы.
+ - `cli.constants.js` - константы, которые используются по всему модулю CLI.
+ - `messages.constants.js` - константы которые относятся к комманде `help`.
+ - `row.constants.js` - костанты, которые относятся к коммандам со списками.
+ - `stats.constants.js` - константы, котоыре онтосятся к комманде `stats`.
+- `cli.commands.js` - перечень всех комманд, которые могут быть использованы в CLI.
+- `cli.controller.js` - класс логики получения данных по ключевым словами, передача их в сервис, а так же реализация ответов обратно в командною строку.
+- `cli.debug.js` - все варианты ответов ответов в командную строку.
+- `cli.events.js` - чтобы CLI понимал, ключевые слова, ему нужны подписки - привязки на ключевые слова, а также функции обратного вызова, которые применяются при срабатывании того или иного ключевого слова.
+- `cli.graphical.js` - CLI имеет графические свойства, такие как отступы, разделяющие линии и прочее. Эти методы описываются в классе CLIHraphic
+- `cli.helper.js` - класс со специфическими функциями, которые не касаются работы с базой данных, валидации или маршрутизацией данных.
+- `cli.logger.js` - класс, отвечающий за взаимодействие с модулем логера.
+- `cli.module.js` - класс с итоговыми методами, которые могут быть использованы в других модулям.
+- `cli.service.js` - класс по работе с базой данных.
+- `cli.utils.js` - различные утилиты, которые вынесены за скобки и не являются обработчиками данных.
+- `cli.validador.js` - класс валидации данных, которые приходят на сервер с различных команд.
+
+Примеры использования различных команд и запуска самой CLI смотрите на главной странице - [Главная страница](../README.md#command-line-interface-cli)
+
+### Graphical user interface (GUI)
+
+Графический интерфейс представляет из себя несколько страничек, организация маршутизации между ними, а также отдельную работу кнопок ведущих на те или иные эндпоинты.
+
+[](https://postimg.cc/4nBzgdsr)
+
+Где:
+- `templates` - директория со всеми шаблонами - страничками, которые отрисовываются и составляют GUI
+- `gui.base.js` - класс с функциями замыканиями, которые принимают данные различных страничек и путь к ним.
+- `gui.constants.js` - константы, которые применяются по всему модулю.
+- `gui.controller.js` - класс логики получения данных по эндпоинтам, передача их в сервис, а так же реализация ответов по эндпоинту обратно на клиент.
+- `gui.data.js` - данные каждого шаблона - странички.
+- `gui.helper.js` - класс со специфическими функциями, которые не касаются работы с базой данных, валидации или маршрутизацией данных.
+- `gui.module.js` - класс с итоговыми методами, которые могут быть использованы в других модулям.
+- `gui.pages.js` - перечень всех страничек приложения.
+- `gui.public.js` - методы по работе с публичными, статическими файлами, такими как Favicon.
+- `gui.service.js` - класс по работе с базой данных.
+- `gui.validator.js` - класс валидации данных, которые приходят на сервер с клиента.
+
+Вид страничек смотрите на главной странице - [Главная страница](../README.md#graphical-user-interface-gui)
+
+### Logger
+
+Логер необходим для логирования файлов базы данных, таким образом позволяя их в дальнейшем восстановить в случае ошибок в последней.
+
+[](https://postimg.cc/B8CnWjHy)
+
+Где:
+- `logger.constants.js` - константы, которые применяются по всему модулю.
+- `logger.controller.js` - класс логики получения, передачи в сервис необходимых данных и возврат нужного ответа.
+- `logger.module.js` - класс с итоговыми методами, которые могут быть использованы в других модулям.
+- `logger.service.js` - класс по работе с базой данных.
+
+### Worker
+
+Модуль отвечающий за переодическое логирование файлов и их пред / пост обработку при компресии / декомпресии их в работе проекта.
+
+[](https://postimg.cc/z3NXzS0Q)
+