mirror of
https://github.com/sergeyyarkov/digital-store.git
synced 2026-10-11 18:29:11 +03:00
added docker
This commit is contained in:
parent
020d8599b9
commit
965e6b0a56
5
.dockerignore
Normal file
5
.dockerignore
Normal file
@ -0,0 +1,5 @@
|
||||
/node_modules
|
||||
|
||||
npm-debug.log
|
||||
yarn-debug.log*
|
||||
yarn-error.log*
|
||||
11
Dockerfile
Normal file
11
Dockerfile
Normal file
@ -0,0 +1,11 @@
|
||||
FROM node:10
|
||||
|
||||
WORKDIR /usr/src/app
|
||||
|
||||
COPY package*.json ./
|
||||
|
||||
RUN npm install
|
||||
|
||||
COPY . .
|
||||
|
||||
CMD ["npm", "start"]
|
||||
418
README.md
418
README.md
@ -27,281 +27,45 @@
|
||||
</a>
|
||||
</p>
|
||||
|
||||
## Содержание
|
||||
- [О проекте](#О-проекте)
|
||||
- [Структура репозитория](#Структура-репозитория)
|
||||
- [Установка и настройка скрипта](#Установка-и-настройка-скрипта)
|
||||
- [Запуск скрипта на локальном компьютере](#Запуск-скрипта-на-локальном-компьютере)
|
||||
- [Запуск скрипта на удаленном сервере](#Запуск-скрипта-на-удаленном-сервере)
|
||||
- [Выгрузка скрипта на бесплтаный хостинг от Heroku](#Выгрузка-скрипта-на-бесплтаный-хостинг-от-Heroku)
|
||||
- [Переменные среды](#Переменные-среды)
|
||||
- [API](#API)
|
||||
- [Требования](#Требования)
|
||||
- [Лицензия](#Лицензия)
|
||||
## 🐬 Установка через Docker:
|
||||
|
||||
## О проекте:
|
||||
Этот проект представляет из себя интернет-магазин на платформе NodeJS, Вы можете продавать свои цифровые товары именно загрузив этот репозиторий, в [панели управления](#Панель-управления) Вы сможете создавать, удалять и редактировать товары или категории . В проекте используется концепция REST API, поэтому для отдачи информации клиенту существует отдельный API. Информация о покупателях, товарах, категориях и т.д хранится в БД MongoDB (используется нативный драйвер).
|
||||
### Функционал покупателя:
|
||||
- Возможность выбирать интересующие категории, переход по одиночным страницам конкретного товара.
|
||||
- Возможность комментировать как отдельный товар, так и весь магазин на отдельной странице с помощью системы комментариев Disqus.
|
||||
- Возможность фильтровать интересующую категорию или все товары через фильтр.
|
||||
- Покупатель может совершать одну или несколько покупок через корзину или кнопку "Купить".
|
||||
- Оплата осуществляется через сервис QIWI API.
|
||||
- Результатом оплаты будут данные одного или нескольких товаров, все данные отсылаются на электронную почту покупателя, которую он указал при создании заказа.
|
||||
- Покупатель может узнать все свои совершенные покупки в магазине на отдельной странице.
|
||||
### Функционал администратора:
|
||||
Для входа в админ-панель необходимо дописать в адресной строке `/admin`, после Вы попадете на страницу авторизации где нужно ввести данные в формате `email:password`. По умолчанию `admin@support.ru:admin`
|
||||
- Пароль админа хэшируется через `bcrypt` для безопасности и записывается в БД.
|
||||
- На главной странице есть небольшая статистика, где можно посмотреть: сумму проданных товаров, кол-во проданных товаров, кол-во товаров в наличии.
|
||||
- На главной странце так же можно узнать подробные данные о покупателях: номер заказа, почта покупателя, способ оплаты, дата покупки, сумма и данные которые были высланы по почте.
|
||||
- Возможность находить конкретного покупателя через поле (нужно знать номер заказа).
|
||||
- Возможность добавлять, удалять или редактировать товары на странице "Товары", так же можно посмотреть и информацию о товаре.
|
||||
- Поиск товаров через поле поиска (нужно знать частичное или полное название товара).
|
||||
- Добавление, удаление и редактирование категорий через страницу "Категории", каждой категории присваивается собственная иконка, которую можно загрузить через страницу "Иконки".
|
||||
- Возможность править контент, изменять общее оформление магазина (только цвет).
|
||||
- Возможность изменять данные администратора: почта, пароль, имя.
|
||||
|
||||
## Структура репозитория:
|
||||
В основе всего репозитория существуют две ветки. Ветка master предназначена для разработки приложения, для выгрузки готового приложения на сервер используйте ветку production.
|
||||
|
||||
## Установка и настройка скрипта:
|
||||
|
||||
### Запуск скрипта на локальном компьютере:
|
||||
- [Установите последний релиз Digital Store](https://github.com/sergeyyarkov/digital-store/releases) из GitHub репозитория.
|
||||
- Или клонировать репозиторий `git clone https://github.com/sergeyyarkov/digital-store.git -b production`.
|
||||
- Установите [Node.js](https://nodejs.org/ru/) не ниже версии 7.6.0, в процессе установки Node.js установите Node Package Manager.
|
||||
- Установите БД MongoDB на ваш компьютер или создайте кластер на сайте [www.mongodb.com](https://www.mongodb.com/) и импортируйте туда дамп структуры БД, которые находится в корне приложения `/database_dump`.
|
||||
- Для работоспособности интернет-магазина необходимо установить зависимости. Выполните комманду `npm i`.
|
||||
- Далле необходимо настроить переменные среды. Создайте файл `.env` в корне вашего интернет-магазина и запишите туда [значения для переменных](#Переменные-среды). Обратите внимание, что для выгрузки скрипта на production сервер, нужно устанавливать переменные среды для вашего сервера, файл `.env` создавать не нужно.
|
||||
- После этого, введите `npm run start` и перейдите по адресу `localhost:3000`, вы увидите уже рабочий интернет-магазин который запущен у вас на локальном компьютере.
|
||||
|
||||
### Запуск скрипта на удаленном сервере:
|
||||
В данном примере на удаленном сервере будет использоваться связка `Ubuntu 18.04, Nginx, MongoDB, PM2, NodeJS` + `SSL Lets Encrypt`
|
||||
|
||||
- Переходим на сайт [RUVDS.COM](https://ruvds.com/pr4435) и приобретаем услугу VPS-хостинга.
|
||||
- Подключаемся к серверу по SSH и следуем далее описанным шагам.
|
||||
- Устанавливаем NodeJS:
|
||||
|
||||
```bash
|
||||
apt-get update && apt-get install curl -y
|
||||
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.35.2/install.sh | bash
|
||||
export NVM_DIR="$([ -z "${XDG_CONFIG_HOME-}" ] && printf %s "${HOME}/.nvm" || printf %s "${XDG_CONFIG_HOME}/nvm")"
|
||||
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"
|
||||
source ~/.bashrc
|
||||
nvm install 12
|
||||
```
|
||||
Если при выполнении команд `node -v` и `npm -v` выдается версия, то идем дальше.
|
||||
- Создаем папку `/apps`, после переходим в нее и клонируем проект с github и переходим в наш магазин:
|
||||
|
||||
```bash
|
||||
mkdir apps
|
||||
|
||||
cd apps/
|
||||
|
||||
git clone https://github.com/sergeyyarkov/digital-store.git -b production
|
||||
|
||||
cd digital-store/
|
||||
```
|
||||
- Устанавливаем зависимости для интернет-магазина `npm install`.
|
||||
- Устанавливаем MongoDB:
|
||||
|
||||
```bash
|
||||
apt install -y mongodb
|
||||
|
||||
systemctl status mongodb <--- проверяем состояние службы, должно быть active (running)
|
||||
```
|
||||
Теперь нужно дать доступ для подключения к БД именно с вашего компьютера, это нам понадобится для импортирования дампа БД:
|
||||
ip адресс берете с сайта 2ip
|
||||
|
||||
```bash
|
||||
ufw enable
|
||||
|
||||
ufw allow from ваш_ip_адресс_компьютера/32 to any port 27017
|
||||
```
|
||||
- Далее открываем конфигурационный файл MongoDB: `nano /etc/mongodb.conf`:
|
||||
Добавляем IP-адрес вашего сервера в значение bindIP:
|
||||
|
||||
```bash
|
||||
logappend=true
|
||||
|
||||
bind_ip = 127.0.0.1,your_server_ip
|
||||
#port = 27017
|
||||
```
|
||||
|
||||
- Сохраните файл, закройте редактор и перезапустите MongoDB: `systemctl restart mongodb`:
|
||||
- Теперь доступ к БД есть только у вашего компьютера, далее скачиваем [Studio 3T](https://studio3t.com/) и создаем новое соединение, ip адресс указываем вашего сервера.
|
||||
- После подключения, создаем новую БД и называем её как хотим.
|
||||
- Кликаем по вашей созданной БД и вверху нажимаем `Import`, после выбираем все JSON файлы, которые хранятся в папке `/database_dump`.
|
||||
- Если все 6 коллекций успешно импортировались, то идем дальше.
|
||||
- Устанавливаем менеджер процессов PM2 `npm install -g pm2`.
|
||||
- Редактируем файл с переменными в файле ecosystem.config.js и устанавливаем свои значения `nano ecosystem.config.js`.
|
||||
- Далее запускаем наше приложение:
|
||||
|
||||
```bash
|
||||
pm2 start ecosystem.config.js --env production <--- стартуем наше приложение
|
||||
|
||||
pm2 status <--- как узнать статус запущенных процессов
|
||||
|
||||
pm2 save <--- сохраняем процесс
|
||||
|
||||
pm2 startup ubuntu <--- автоматически запускаем наше приложение в случае рестарта сервера
|
||||
```
|
||||
|
||||
- Настраиваем файрволл:
|
||||
|
||||
```bash
|
||||
ufw allow ssh
|
||||
|
||||
ufw allow http
|
||||
|
||||
ufw allow https
|
||||
```
|
||||
|
||||
- Далее устанавливаем веб-сервер nginx `apt install nginx`, после редактируем конфигурационный файл `nano /etc/nginx/sites-available/default`:
|
||||
|
||||
```bash
|
||||
server_name yourdomain.com www.yourdomain.com;
|
||||
|
||||
location / {
|
||||
proxy_pass http://localhost:3000; #порт запущенного приложения
|
||||
proxy_http_version 1.1;
|
||||
proxy_set_header Upgrade $http_upgrade;
|
||||
proxy_set_header Connection 'upgrade';
|
||||
proxy_set_header Host $host;
|
||||
proxy_cache_bypass $http_upgrade;
|
||||
}
|
||||
```
|
||||
|
||||
- Обязательно настройте gzip сжатие, ваш сайт будет работать быстрее:
|
||||
|
||||
```bash
|
||||
server {
|
||||
gzip on;
|
||||
gzip_disable "msie6";
|
||||
gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript application/javascript;
|
||||
}
|
||||
```
|
||||
|
||||
- Так же желательно избавиться от дубля страницы www:
|
||||
|
||||
```bash
|
||||
if ($host = 'www.example.com') {
|
||||
return 301 https://example.com$request_uri;
|
||||
}
|
||||
```
|
||||
|
||||
- После настройки проверьте ваш конфигурационный файл на ошибки `nginx -t`, если ошибок нет, то перезапускаем сервис nginx `service nginx restart`.
|
||||
- На сайте RUDVS добавьте свой домен и привяжите его к своему серверу, настройте DNS записи у регистратора. Через какое то время ваш магазин будет доступен по домену.
|
||||
- Далее настройте SSL сертификат:
|
||||
|
||||
```bash
|
||||
add-apt-repository ppa:certbot/certbot
|
||||
|
||||
apt-get update
|
||||
|
||||
apt-get install python-certbot-nginx
|
||||
|
||||
certbot --nginx -d yourdomain.com <--- в процессе установки выбираем цифру 2
|
||||
```
|
||||
|
||||
- Ваш конфигурационный файл должен выглядеть примерно так:
|
||||
|
||||
```bash
|
||||
server {
|
||||
|
||||
gzip on;
|
||||
gzip_disable "msie6";
|
||||
gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript application/javascript;
|
||||
|
||||
root /var/www/html;
|
||||
|
||||
index index.html index.htm index.nginx-debian.html;
|
||||
|
||||
server_name yourdomain.ru www.yourdomain.ru;
|
||||
|
||||
location / {
|
||||
proxy_pass http://localhost:3000;
|
||||
proxy_http_version 1.1;
|
||||
proxy_set_header Upgrade $http_upgrade;
|
||||
proxy_set_header Connection 'upgrade';
|
||||
proxy_set_header Host $host;
|
||||
proxy_cache_bypass $http_upgrade;
|
||||
}
|
||||
|
||||
if ($host = 'www.yourdomain.ru') {
|
||||
return 301 https://yourdomain.ru$request_uri;
|
||||
}
|
||||
|
||||
listen [::]:443 ssl ipv6only=on; # managed by Certbot
|
||||
listen 443 ssl; # managed by Certbot
|
||||
ssl_certificate /etc/letsencrypt/live/yourdomain.ru/fullchain.pem; # managed by Certbot
|
||||
ssl_certificate_key /etc/letsencrypt/live/yourdomain.ru/privkey.pem; # managed by Certbot
|
||||
include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
|
||||
ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot
|
||||
}
|
||||
|
||||
server {
|
||||
if ($host = www.yourdomain.ru) {
|
||||
return 301 https://$host$request_uri;
|
||||
} # managed by Certbot
|
||||
|
||||
|
||||
if ($host = yourdomain.ru) {
|
||||
return 301 https://$host$request_uri;
|
||||
} # managed by Certbot
|
||||
|
||||
listen 80 default_server;
|
||||
listen [::]:80 default_server;
|
||||
|
||||
server_name yourdomain.ru www.yourdomain.ru;
|
||||
return 404; # managed by Certbot
|
||||
}
|
||||
|
||||
```
|
||||
|
||||
### Установка скрипта на бесплатный хостинг от Heroku:
|
||||
- Регистрируемся на сайте [Heroku](https://signup.heroku.com/login).
|
||||
- Устанавливаем heroku-cli `https://devcenter.heroku.com/articles/heroku-cli`.
|
||||
- Проверьте установку, написав в консоле `heroku --help` если всё выводит, идем дальше.
|
||||
- Залогиньтесь: `heroku login`.
|
||||
- Создайте новый проект Herkou: `heroku create`.
|
||||
- Создайте кластер на сайте [www.mongodb.com](https://www.mongodb.com/) и импортируйте туда дамп структуры БД, который находится в корне приложения `/database_dump`. При подключении к БД выберите метод `Connect Your Application`
|
||||
- Переходим на сайт heroku, идем в свое созданное приложение и открываем вкладку `Settings -> Config Vars` кнопка `Reveal Config Vars` и настраиваем [переменные среды](#Переменные-среды).
|
||||
- Создаем папку с любым названием, открываем её и клонируем проект с github: `git clone https://github.com/sergeyyarkov/digital-store.git -b production .`
|
||||
- Сменим ветку на master: `git checkout -b master`
|
||||
- Удаляем файл ecosystem.config.js (в случае с heroku он не нужен т.к переменные мы храним у heroku)
|
||||
- Добавляем удаленный репозиторий `heroku git:remote -a название вашего приложения`.
|
||||
- Деплой:
|
||||
```bash
|
||||
git add .
|
||||
git commit -m "make it better"
|
||||
git push heroku master
|
||||
```
|
||||
-
|
||||
|
||||
### Настройка платежной системы:
|
||||
|
||||
В скрипте на данный момент доступна система оплаты через сервис QIWI, чтобы настроить оплату в вашем магазине следуйте следующим шагам:
|
||||
|
||||
- Перейдите на сайт [QIWI API](https://qiwi.com/p2p-admin/transfers/api) и создайте пару ключей авторизации. Сохраните секретный ключ.
|
||||
- Если вы хотите настроить оформление формы приемов перевода, то перейдите [сюда](https://qiwi.com/p2p-admin/transfers/link) и скопируйте значение переменной `themeCode` и вставьте это значение по адресу `config/routes/payments/qiwi.payment.js`.
|
||||
- Секретный ключ нужно указать в поле переменной среды `QIWI_SECRET_KEY`.
|
||||
- Редирект после оплаты товара через QIWI на локальный адрес `localhost:3000` работать не будет, необходим домен.
|
||||
|
||||
### Настройка почтового сервиса:
|
||||
|
||||
Для отдачи данных товара на почту покупателя после покупки товара, нужно настроить nodemailer:
|
||||
|
||||
- Настройте почтовый сервис по адресу `config/nodemailer.config.js`:
|
||||
|
||||
```javascript
|
||||
host: "smtp.mail.ru",
|
||||
port: 465,
|
||||
secure: true, // true для 465, false для остальных.
|
||||
```
|
||||
|
||||
- Затем укажите переменные среды `EMAIL_LOGIN` и `EMAIL_PASSWORD`.
|
||||
|
||||
### Настройка системы комментариев:
|
||||
|
||||
В интернет магазине используется система комментариев [Disqus](https://disqus.com/):
|
||||
|
||||
- Добавьте свой домен на их сайт и замените embed код по адресу `dist/public/js/disqus.js`.
|
||||
|
||||
## Переменные среды:
|
||||
|
||||
Перменные среды нужны для работоспособности всего приложения, очень важно вписать верные данные для избежания возможных ошибок.
|
||||
|
||||
### Описание переменных:
|
||||
|
||||
| Переменная | Описание |
|
||||
| --------------- | -------------------------------------------------------- |
|
||||
| DATABASE_URI | Подключение к БД MongoDB |
|
||||
@ -311,6 +75,7 @@ secure: true, // true для 465, false для остальных.
|
||||
| QIWI_SECRET_KEY | Секретный ключ QIWI для работоспособности системы оплаты |
|
||||
|
||||
`.env` файл:
|
||||
|
||||
```bash
|
||||
DATABASE_URI=
|
||||
DATABASE_NAME=
|
||||
@ -318,161 +83,186 @@ QIWI_SECRET_KEY=
|
||||
EMAIL_LOGIN=
|
||||
EMAIL_PASSWORD=
|
||||
```
|
||||
|
||||
|
||||
## API:
|
||||
|
||||
### API представляет из себя различные URL, которые отвечают данными только в формате JSON. Здесь описаны основные `GET` запросы на сервер для получения данных:
|
||||
|
||||
#### Для просмотра всех товаров которые существуют в магазине отправляется запрос:
|
||||
```bash
|
||||
https://store-name.com/api/items
|
||||
|
||||
```bash
|
||||
https://store-name.com/api/items
|
||||
```
|
||||
|
||||
Ответ:
|
||||
|
||||
```javascript
|
||||
[
|
||||
;[
|
||||
{
|
||||
_id: "5e15dbc415303a1980cd77a0",
|
||||
title: "Тестовый товар №1",
|
||||
_id: '5e15dbc415303a1980cd77a0',
|
||||
title: 'Тестовый товар №1',
|
||||
count: 0,
|
||||
price: 1,
|
||||
category: "steam",
|
||||
description: "-",
|
||||
date: "2020-01-08T13:40:20.353Z"
|
||||
category: 'steam',
|
||||
description: '-',
|
||||
date: '2020-01-08T13:40:20.353Z',
|
||||
},
|
||||
{
|
||||
_id: "5e15dcb4138c3339bcbc3719",
|
||||
title: "Тестовый товар №2",
|
||||
_id: '5e15dcb4138c3339bcbc3719',
|
||||
title: 'Тестовый товар №2',
|
||||
count: 0,
|
||||
price: 1,
|
||||
category: "uplay",
|
||||
description: "-",
|
||||
date: "2020-01-08T13:44:20.940Z"
|
||||
category: 'uplay',
|
||||
description: '-',
|
||||
date: '2020-01-08T13:44:20.940Z',
|
||||
},
|
||||
]
|
||||
```
|
||||
|
||||
### Для просмотра товаров в интересующей категории отправляется запрос:
|
||||
|
||||
```bash
|
||||
https://store-name.com/api/items/{category}
|
||||
```
|
||||
|
||||
Ответ:
|
||||
|
||||
```javascript
|
||||
[
|
||||
;[
|
||||
{
|
||||
_id: "5e15dbc415303a1980cd77a0",
|
||||
title: "Тестовый товар №1",
|
||||
_id: '5e15dbc415303a1980cd77a0',
|
||||
title: 'Тестовый товар №1',
|
||||
count: 0,
|
||||
price: 1,
|
||||
category: "steam",
|
||||
description: "-",
|
||||
date: "2020-01-08T13:40:20.353Z"
|
||||
category: 'steam',
|
||||
description: '-',
|
||||
date: '2020-01-08T13:40:20.353Z',
|
||||
},
|
||||
{
|
||||
_id: "5e1ccf30d5b894228c86385a",
|
||||
title: "Тестовый товар №2",
|
||||
_id: '5e1ccf30d5b894228c86385a',
|
||||
title: 'Тестовый товар №2',
|
||||
count: 10,
|
||||
price: 1,
|
||||
category: "steam",
|
||||
description: "-",
|
||||
date: "2020-01-13T20:12:32.814Z"
|
||||
}
|
||||
category: 'steam',
|
||||
description: '-',
|
||||
date: '2020-01-13T20:12:32.814Z',
|
||||
},
|
||||
]
|
||||
```
|
||||
|
||||
### Для просмотра информации о всех категориях отправляется запрос:
|
||||
|
||||
```bash
|
||||
https://store-name.com/api/categories
|
||||
```
|
||||
|
||||
Ответ:
|
||||
|
||||
```javascript
|
||||
[
|
||||
;[
|
||||
{
|
||||
_id: "5df64563309e691f2c33d400",
|
||||
title: "uplay",
|
||||
img: "img-1576349954743.svg",
|
||||
type: "type",
|
||||
format: "format"
|
||||
_id: '5df64563309e691f2c33d400',
|
||||
title: 'uplay',
|
||||
img: 'img-1576349954743.svg',
|
||||
type: 'type',
|
||||
format: 'format',
|
||||
},
|
||||
{
|
||||
_id: "5e04ea023625771abc75fd14",
|
||||
title: "fortnite",
|
||||
img: "img-1576349989720.svg",
|
||||
type: "type",
|
||||
format: "format"
|
||||
_id: '5e04ea023625771abc75fd14',
|
||||
title: 'fortnite',
|
||||
img: 'img-1576349989720.svg',
|
||||
type: 'type',
|
||||
format: 'format',
|
||||
},
|
||||
]
|
||||
```
|
||||
|
||||
### Для просмотра информации о интересующей категории отправляется запрос:
|
||||
|
||||
```bash
|
||||
https://store-name.com/api/category/{category}
|
||||
```
|
||||
|
||||
Ответ:
|
||||
|
||||
```javascript
|
||||
[
|
||||
;[
|
||||
{
|
||||
_id: "5df64563309e691f2c33d400",
|
||||
title: "uplay",
|
||||
img: "img-1576349954743.svg",
|
||||
type: "type",
|
||||
format: "format"
|
||||
}
|
||||
_id: '5df64563309e691f2c33d400',
|
||||
title: 'uplay',
|
||||
img: 'img-1576349954743.svg',
|
||||
type: 'type',
|
||||
format: 'format',
|
||||
},
|
||||
]
|
||||
```
|
||||
|
||||
### Для просмотра данных всех товаров отправляется запрос: **Нужна авторизация для администратора.**
|
||||
|
||||
```bash
|
||||
https://store-name.com/api/items/data
|
||||
```
|
||||
|
||||
Ответ:
|
||||
|
||||
```javascript
|
||||
[
|
||||
;[
|
||||
{
|
||||
_id: "5e15dbc415303a1980cd77a0",
|
||||
title: "Тестовый товар №1",
|
||||
data: ["login:pass", "login:pass", "login:pass"]
|
||||
_id: '5e15dbc415303a1980cd77a0',
|
||||
title: 'Тестовый товар №1',
|
||||
data: ['login:pass', 'login:pass', 'login:pass'],
|
||||
},
|
||||
{
|
||||
_id: "5e175c63b479600ac493ce88",
|
||||
title: "Тестовый товар №2",
|
||||
data: ["login:pass", "login:pass", "login:pass"]
|
||||
}
|
||||
_id: '5e175c63b479600ac493ce88',
|
||||
title: 'Тестовый товар №2',
|
||||
data: ['login:pass', 'login:pass', 'login:pass'],
|
||||
},
|
||||
]
|
||||
```
|
||||
|
||||
### Для просмотра покупателей отправляется запрос: **Нужна авторизация для администратора.**
|
||||
|
||||
```bash
|
||||
https://store-name.com/api/buyers
|
||||
```
|
||||
|
||||
Ответ:
|
||||
|
||||
```javascript
|
||||
[
|
||||
;[
|
||||
{
|
||||
_id: "5e1c97701b619a31f010062c",
|
||||
bill_id: "9244e5ae-560a-432a-9882-bc1b941c8cca",
|
||||
email: "test-email@mail.com",
|
||||
method: "qiwi",
|
||||
date: "2020-01-13T18:13:38.623+03:00",
|
||||
_id: '5e1c97701b619a31f010062c',
|
||||
bill_id: '9244e5ae-560a-432a-9882-bc1b941c8cca',
|
||||
email: 'test-email@mail.com',
|
||||
method: 'qiwi',
|
||||
date: '2020-01-13T18:13:38.623+03:00',
|
||||
amount: 2,
|
||||
data: ["login:pass", "login:pass"]
|
||||
}
|
||||
data: ['login:pass', 'login:pass'],
|
||||
},
|
||||
]
|
||||
```
|
||||
|
||||
### Для просмотра списка иконок отправляется запрос: **Нужна авторизация для администратора.**
|
||||
|
||||
```bash
|
||||
https://store-name.com/api/icons
|
||||
```
|
||||
|
||||
Ответ:
|
||||
|
||||
```javascript
|
||||
[
|
||||
"img-1576349954743.svg",
|
||||
"img-1576349989720.svg",
|
||||
"img-1576420937629.svg",
|
||||
"img-1576421960189.svg"
|
||||
;[
|
||||
'img-1576349954743.svg',
|
||||
'img-1576349989720.svg',
|
||||
'img-1576420937629.svg',
|
||||
'img-1576421960189.svg',
|
||||
]
|
||||
```
|
||||
|
||||
## Требования:
|
||||
|
||||
- Node.js v7.6.0 или выше
|
||||
|
||||
## Лицензия:
|
||||
|
||||
[MIT](https://github.com/sergeyyarkov/digital-store/blob/master/LICENSE)<br><br>
|
||||
|
||||
BIN
data/backup/digital_store/administrators.bson
Normal file
BIN
data/backup/digital_store/administrators.bson
Normal file
Binary file not shown.
1
data/backup/digital_store/administrators.metadata.json
Normal file
1
data/backup/digital_store/administrators.metadata.json
Normal file
@ -0,0 +1 @@
|
||||
{"options":{},"indexes":[{"v":{"$numberInt":"2"},"key":{"_id":{"$numberInt":"1"}},"name":"_id_","ns":"digital_store.administrators"}],"uuid":"7c7a24d1f1984eb3823ca3af77c8f887"}
|
||||
0
data/backup/digital_store/buyers.bson
Normal file
0
data/backup/digital_store/buyers.bson
Normal file
1
data/backup/digital_store/buyers.metadata.json
Normal file
1
data/backup/digital_store/buyers.metadata.json
Normal file
@ -0,0 +1 @@
|
||||
{"options":{},"indexes":[{"v":{"$numberInt":"2"},"key":{"_id":{"$numberInt":"1"}},"name":"_id_","ns":"digital_store.buyers"}],"uuid":"4e3bebb2aa9648a5ba18b6dc30b2b2e8"}
|
||||
BIN
data/backup/digital_store/categories.bson
Normal file
BIN
data/backup/digital_store/categories.bson
Normal file
Binary file not shown.
1
data/backup/digital_store/categories.metadata.json
Normal file
1
data/backup/digital_store/categories.metadata.json
Normal file
@ -0,0 +1 @@
|
||||
{"options":{},"indexes":[{"v":{"$numberInt":"2"},"key":{"_id":{"$numberInt":"1"}},"name":"_id_","ns":"digital_store.categories"}],"uuid":"73f3159b00974d27a9c03a507b4734dd"}
|
||||
BIN
data/backup/digital_store/content.bson
Normal file
BIN
data/backup/digital_store/content.bson
Normal file
Binary file not shown.
1
data/backup/digital_store/content.metadata.json
Normal file
1
data/backup/digital_store/content.metadata.json
Normal file
@ -0,0 +1 @@
|
||||
{"options":{},"indexes":[{"v":{"$numberInt":"2"},"key":{"_id":{"$numberInt":"1"}},"name":"_id_","ns":"digital_store.content"}],"uuid":"3f734f39ee614324be532246ad14faf3"}
|
||||
BIN
data/backup/digital_store/info.bson
Normal file
BIN
data/backup/digital_store/info.bson
Normal file
Binary file not shown.
1
data/backup/digital_store/info.metadata.json
Normal file
1
data/backup/digital_store/info.metadata.json
Normal file
@ -0,0 +1 @@
|
||||
{"options":{},"indexes":[{"v":{"$numberInt":"2"},"key":{"_id":{"$numberInt":"1"}},"name":"_id_","ns":"digital_store.info"}],"uuid":"33f3568c85fe4350bfae3aec7059bd91"}
|
||||
BIN
data/backup/digital_store/items.bson
Normal file
BIN
data/backup/digital_store/items.bson
Normal file
Binary file not shown.
1
data/backup/digital_store/items.metadata.json
Normal file
1
data/backup/digital_store/items.metadata.json
Normal file
@ -0,0 +1 @@
|
||||
{"options":{},"indexes":[{"v":{"$numberInt":"2"},"key":{"_id":{"$numberInt":"1"}},"name":"_id_","ns":"digital_store.items"},{"v":{"$numberInt":"2"},"key":{"_fts":"text","_ftsx":{"$numberInt":"1"}},"name":"title_text","language_override":"language","ns":"digital_store.items","weights":{"title":{"$numberInt":"1"}},"default_language":"english","textIndexVersion":{"$numberInt":"3"}}],"uuid":"14bff4a55fcf4fd2963b07f75add3ae8"}
|
||||
20
data/nginx/app.conf
Normal file
20
data/nginx/app.conf
Normal file
@ -0,0 +1,20 @@
|
||||
server {
|
||||
listen 80;
|
||||
|
||||
gzip on;
|
||||
gzip_disable "msie6";
|
||||
gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript application/javascript;
|
||||
|
||||
server_name localhost;
|
||||
server_tokens off;
|
||||
|
||||
location / {
|
||||
proxy_pass http://nodejs:3000;
|
||||
|
||||
proxy_http_version 1.1;
|
||||
proxy_set_header Upgrade $http_upgrade;
|
||||
proxy_set_header Connection 'upgrade';
|
||||
proxy_set_header Host $host;
|
||||
proxy_cache_bypass $http_upgrade;
|
||||
}
|
||||
}
|
||||
@ -1,7 +0,0 @@
|
||||
{
|
||||
"_id" : ObjectId("5de9733dc58a41381415a7b0"),
|
||||
"id" : "1575580477024",
|
||||
"name" : "Administrator",
|
||||
"email" : "admin@support.ru",
|
||||
"password" : "$2a$10$l5A1VHuN3a9IXhPq.tK.WOWvrIDZJxu1LKIPOYe6ywlS4dbjIMBu6"
|
||||
}
|
||||
@ -1,11 +0,0 @@
|
||||
{
|
||||
"_id" : ObjectId("5e2c6e4770964b0017bb9009"),
|
||||
"bill_id" : "51076c5e-25d7-422e-8f73-9bc3f583679c",
|
||||
"email" : "testmail@mail.com",
|
||||
"method" : "qiwi",
|
||||
"date" : "2020-01-25T19:35:14.025+03:00",
|
||||
"amount" : NumberInt(1),
|
||||
"data" : [
|
||||
"login:pass"
|
||||
]
|
||||
}
|
||||
@ -1,28 +0,0 @@
|
||||
{
|
||||
"_id" : ObjectId("5df63ed5044ecc18c43e9e91"),
|
||||
"title" : "steam",
|
||||
"img" : "img-1576420937629.svg",
|
||||
"type" : "Steam Type",
|
||||
"format" : "Steam Format"
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5df64563309e691f2c33d400"),
|
||||
"title" : "uplay",
|
||||
"img" : "img-1576349954743.svg",
|
||||
"type" : "Uplay Type",
|
||||
"format" : "Uplay Format"
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e04ea023625771abc75fd14"),
|
||||
"title" : "fortnite",
|
||||
"img" : "img-1576349989720.svg",
|
||||
"type" : "Fortnite Type",
|
||||
"format" : "Fortnite Format"
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e11c381471ae208f0b6aae4"),
|
||||
"title" : "origin",
|
||||
"img" : "img-1576421960189.svg",
|
||||
"type" : "Origin Type",
|
||||
"format" : "Origin Format"
|
||||
}
|
||||
@ -1,11 +0,0 @@
|
||||
{
|
||||
"_id" : ObjectId("5e0b7466fbd02d01c46038a7"),
|
||||
"title" : "Store Name",
|
||||
"email" : "email@support.ru",
|
||||
"info" : "Sed ut perspiciatis unde omnis iste natus error sit voluptatem accusantium doloremque laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione voluptatem sequi nesciunt. Neque porro quisquam est, qui dolorem ipsum quia dolor sit amet, consectetur, adipisci velit, sed quia non numquam eius modi tempora incidunt ut labore et dolore magnam aliquam quaerat voluptatem. Ut enim ad minima veniam, quis nostrum exercitationem ullam corporis suscipit laboriosam, nisi ut aliquid ex ea commodi consequatur? Quis autem vel eum iure reprehenderit qui in ea voluptate velit esse quam nihil molestiae consequatur, vel illum qui dolorem eum fugiat quo voluptas nulla pariatur?",
|
||||
"infoBottom" : "Sed ut perspiciatis unde omnis iste natus error sit voluptatem accusantium doloremque laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione voluptatem sequi nesciunt. Neque porro quisquam est, qui dolorem ipsum quia dolor sit amet, consectetur, adipisci velit, sed quia non numquam eius modi tempora incidunt ut labore et dolore magnam aliquam quaerat voluptatem. Ut enim ad minima veniam, quis nostrum exercitationem ullam corporis suscipit laboriosam, nisi ut aliquid ex ea commodi consequatur? Quis autem vel eum iure reprehenderit qui in ea voluptate velit esse quam nihil molestiae consequatur, vel illum qui dolorem eum fugiat quo voluptas nulla pariatur?",
|
||||
"howToBuy" : "Sed ut perspiciatis unde omnis iste natus error sit voluptatem accusantium doloremque laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione voluptatem sequi nesciunt. Neque porro quisquam est, qui dolorem ipsum quia dolor sit amet, consectetur, adipisci velit, sed quia non numquam eius modi tempora incidunt ut labore et dolore magnam aliquam quaerat voluptatem. Ut enim ad minima veniam, quis nostrum exercitationem ullam corporis suscipit laboriosam, nisi ut aliquid ex ea commodi consequatur? Quis autem vel eum iure reprehenderit qui in ea voluptate velit esse quam nihil molestiae consequatur, vel illum qui dolorem eum fugiat quo voluptas nulla pariatur?",
|
||||
"contacts" : "1. Почта: email@support.ru\r\n2. Telegram: @support.ru",
|
||||
"recommendations" : "Sed ut perspiciatis unde omnis iste natus error sit voluptatem accusantium doloremque laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione voluptatem sequi nesciunt. Neque porro quisquam est, qui dolorem ipsum quia dolor sit amet, consectetur, adipisci velit, sed quia non numquam eius modi tempora incidunt ut labore et dolore magnam aliquam quaerat voluptatem. Ut enim ad minima veniam, quis nostrum exercitationem ullam corporis suscipit laboriosam, nisi ut aliquid ex ea commodi consequatur? Quis autem vel eum iure reprehenderit qui in ea voluptate velit esse quam nihil molestiae consequatur, vel illum qui dolorem eum fugiat quo voluptas nulla pariatur?",
|
||||
"color" : "#26a69a"
|
||||
}
|
||||
@ -1,64 +0,0 @@
|
||||
{
|
||||
"_id" : ObjectId("5e15dbc415303a1980cd77a0"),
|
||||
"title" : "Тестовый товар №1",
|
||||
"data" : [
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass"
|
||||
]
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e15dcb4138c3339bcbc3719"),
|
||||
"title" : "Тестовый товар №3",
|
||||
"data" : [
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass"
|
||||
]
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e175c63b479600ac493ce88"),
|
||||
"title" : "Тестовый товар №4",
|
||||
"data" : [
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass"
|
||||
]
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e1ccf30d5b894228c86385a"),
|
||||
"title" : "Тестовый товар №5",
|
||||
"data" : [
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass",
|
||||
"login:pass"
|
||||
]
|
||||
}
|
||||
@ -1,36 +0,0 @@
|
||||
{
|
||||
"_id" : ObjectId("5e15dbc415303a1980cd77a0"),
|
||||
"title" : "Тестовый товар №1",
|
||||
"count" : NumberInt(10),
|
||||
"price" : NumberInt(1),
|
||||
"category" : "steam",
|
||||
"description" : "Тестовый товар №1 описание",
|
||||
"date" : ISODate("2020-01-08T13:40:20.353+0000")
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e15dcb4138c3339bcbc3719"),
|
||||
"title" : "Тестовый товар №3",
|
||||
"count" : NumberInt(10),
|
||||
"price" : NumberInt(1),
|
||||
"category" : "uplay",
|
||||
"description" : "Тестовый товар №3 fdsfd",
|
||||
"date" : ISODate("2020-01-08T13:44:20.940+0000")
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e175c63b479600ac493ce88"),
|
||||
"title" : "Тестовый товар №4",
|
||||
"count" : NumberInt(10),
|
||||
"price" : NumberInt(1),
|
||||
"category" : "fortnite",
|
||||
"description" : "Тестовый товар №4 opis",
|
||||
"date" : ISODate("2020-01-09T17:01:23.446+0000")
|
||||
},
|
||||
{
|
||||
"_id" : ObjectId("5e1ccf30d5b894228c86385a"),
|
||||
"title" : "Тестовый товар №5",
|
||||
"count" : NumberInt(10),
|
||||
"price" : NumberInt(1),
|
||||
"category" : "origin",
|
||||
"description" : "sdsdsds",
|
||||
"date" : ISODate("2020-01-13T20:12:32.814+0000")
|
||||
}
|
||||
47
docker-compose.yml
Normal file
47
docker-compose.yml
Normal file
@ -0,0 +1,47 @@
|
||||
version: '3'
|
||||
services:
|
||||
mongodb:
|
||||
container_name: mongodb
|
||||
image: mongo
|
||||
environment:
|
||||
- MONGO_INITDB_ROOT_USERNAME=root
|
||||
- MONGO_INITDB_ROOT_PASSWORD=secret
|
||||
- MONGO_INITDB_DATABASE=digital_store
|
||||
ports:
|
||||
- '27017'
|
||||
restart: always
|
||||
volumes:
|
||||
- ./data/backup:/backup
|
||||
- ./mongo-init.js:/docker-entrypoint-initdb.d/mongo-init.js:ro
|
||||
nodejs:
|
||||
container_name: nodejs
|
||||
restart: always
|
||||
build: .
|
||||
ports:
|
||||
- '3000'
|
||||
environment:
|
||||
- DATABASE_NAME=digital_store
|
||||
- DATABASE_URI=mongodb://root:secret@mongodb:27017
|
||||
- EMAIL_LOGIN=
|
||||
- EMAIL_PASSWORD=
|
||||
- HOSTNAME_URI=
|
||||
- QIWI_SECRET_KEY=
|
||||
nginx:
|
||||
image: nginx
|
||||
container_name: nginx
|
||||
restart: unless-stopped
|
||||
ports:
|
||||
- '80:80'
|
||||
- '443:443'
|
||||
volumes:
|
||||
- ./data/nginx:/etc/nginx/conf.d
|
||||
- ./data/certbot/conf:/etc/letsencrypt
|
||||
- ./data/certbot/www:/var/www/certbot
|
||||
command: '/bin/sh -c ''while :; do sleep 6h & wait $${!}; nginx -s reload; done & nginx -g "daemon off;"'''
|
||||
certbot:
|
||||
image: certbot/certbot
|
||||
restart: unless-stopped
|
||||
volumes:
|
||||
- ./data/certbot/conf:/etc/letsencrypt
|
||||
- ./data/certbot/www:/var/www/certbot
|
||||
entrypoint: "/bin/sh -c 'trap exit TERM; while :; do certbot renew; sleep 12h & wait $${!}; done;'"
|
||||
@ -1,21 +0,0 @@
|
||||
module.exports = {
|
||||
apps : [{
|
||||
name: 'server',
|
||||
script: 'server/server.js',
|
||||
autorestart: true,
|
||||
watch: true,
|
||||
instances: 'max',
|
||||
exec_mode: 'cluster',
|
||||
env: {
|
||||
NODE_ENV: 'development'
|
||||
},
|
||||
env_production: {
|
||||
NODE_ENV: 'production',
|
||||
DATABASE_URI: 'mongodb://127.0.0.1:27017',
|
||||
DATABASE_NAME: '',
|
||||
EMAIL_LOGIN: '',
|
||||
EMAIL_PASSWORD: '',
|
||||
QIWI_SECRET_KEY: ''
|
||||
}
|
||||
}],
|
||||
};
|
||||
80
init-letsencrypt.sh
Normal file
80
init-letsencrypt.sh
Normal file
@ -0,0 +1,80 @@
|
||||
#!/bin/bash
|
||||
|
||||
if ! [ -x "$(command -v docker-compose)" ]; then
|
||||
echo 'Error: docker-compose is not installed.' >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
domains=(domain.ru www.domain.ru)
|
||||
rsa_key_size=4096
|
||||
data_path="./data/certbot"
|
||||
email="yourmail@mail.ru" # Adding a valid address is strongly recommended
|
||||
staging=0 # Set to 1 if you're testing your setup to avoid hitting request limits
|
||||
|
||||
if [ -d "$data_path" ]; then
|
||||
read -p "Existing data found for $domains. Continue and replace existing certificate? (y/N) " decision
|
||||
if [ "$decision" != "Y" ] && [ "$decision" != "y" ]; then
|
||||
exit
|
||||
fi
|
||||
fi
|
||||
|
||||
|
||||
if [ ! -e "$data_path/conf/options-ssl-nginx.conf" ] || [ ! -e "$data_path/conf/ssl-dhparams.pem" ]; then
|
||||
echo "### Downloading recommended TLS parameters ..."
|
||||
mkdir -p "$data_path/conf"
|
||||
curl -s https://raw.githubusercontent.com/certbot/certbot/master/certbot-nginx/certbot_nginx/_internal/tls_configs/options-ssl-nginx.conf > "$data_path/conf/options-ssl-nginx.conf"
|
||||
curl -s https://raw.githubusercontent.com/certbot/certbot/master/certbot/certbot/ssl-dhparams.pem > "$data_path/conf/ssl-dhparams.pem"
|
||||
echo
|
||||
fi
|
||||
|
||||
echo "### Creating dummy certificate for $domains ..."
|
||||
path="/etc/letsencrypt/live/$domains"
|
||||
mkdir -p "$data_path/conf/live/$domains"
|
||||
docker-compose run --rm --entrypoint "\
|
||||
openssl req -x509 -nodes -newkey rsa:1024 -days 1\
|
||||
-keyout '$path/privkey.pem' \
|
||||
-out '$path/fullchain.pem' \
|
||||
-subj '/CN=localhost'" certbot
|
||||
echo
|
||||
|
||||
|
||||
echo "### Starting nginx ..."
|
||||
docker-compose up --force-recreate -d
|
||||
echo
|
||||
|
||||
echo "### Deleting dummy certificate for $domains ..."
|
||||
docker-compose run --rm --entrypoint "\
|
||||
rm -Rf /etc/letsencrypt/live/$domains && \
|
||||
rm -Rf /etc/letsencrypt/archive/$domains && \
|
||||
rm -Rf /etc/letsencrypt/renewal/$domains.conf" certbot
|
||||
echo
|
||||
|
||||
|
||||
echo "### Requesting Let's Encrypt certificate for $domains ..."
|
||||
#Join $domains to -d args
|
||||
domain_args=""
|
||||
for domain in "${domains[@]}"; do
|
||||
domain_args="$domain_args -d $domain"
|
||||
done
|
||||
|
||||
# Select appropriate email arg
|
||||
case "$email" in
|
||||
"") email_arg="--register-unsafely-without-email" ;;
|
||||
*) email_arg="--email $email" ;;
|
||||
esac
|
||||
|
||||
# Enable staging mode if needed
|
||||
if [ $staging != "0" ]; then staging_arg="--staging"; fi
|
||||
|
||||
docker-compose run --rm --entrypoint "\
|
||||
certbot certonly --webroot -w /var/www/certbot \
|
||||
$staging_arg \
|
||||
$email_arg \
|
||||
$domain_args \
|
||||
--rsa-key-size $rsa_key_size \
|
||||
--agree-tos \
|
||||
--force-renewal" certbot
|
||||
echo
|
||||
|
||||
echo "### Reloading nginx ..."
|
||||
docker-compose exec nginx nginx -s reload
|
||||
10
mongo-init.js
Normal file
10
mongo-init.js
Normal file
@ -0,0 +1,10 @@
|
||||
db.createUser({
|
||||
user: 'root',
|
||||
pwd: 'secret',
|
||||
roles: [
|
||||
{
|
||||
role: 'readWrite',
|
||||
db: 'digital_store',
|
||||
},
|
||||
],
|
||||
})
|
||||
2
package-lock.json
generated
2
package-lock.json
generated
@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "digital-store",
|
||||
"version": "1.0.0",
|
||||
"version": "1.1.1",
|
||||
"lockfileVersion": 1,
|
||||
"requires": true,
|
||||
"dependencies": {
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
module.exports = {
|
||||
url: process.env.DATABASE_URI,
|
||||
name: process.env.DATABASE_NAME
|
||||
}
|
||||
url: process.env.DATABASE_URI,
|
||||
name: process.env.DATABASE_NAME,
|
||||
}
|
||||
|
||||
126
server/server.js
126
server/server.js
@ -1,63 +1,77 @@
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
require('dotenv').config();
|
||||
require('dotenv').config()
|
||||
}
|
||||
|
||||
const MongoClient = require('mongodb').MongoClient;
|
||||
const db_config = require('./database');
|
||||
const express = require('express');
|
||||
const server = express();
|
||||
const cors = require('cors');
|
||||
const path = require('path');
|
||||
const passport = require('passport');
|
||||
const flash = require('express-flash');
|
||||
const session = require('express-session');
|
||||
const methodOverride = require('method-override');
|
||||
const multer = require('multer');
|
||||
const QiwiBillPaymentsAPI = require('@qiwi/bill-payments-node-js-sdk');
|
||||
const MongoClient = require('mongodb').MongoClient
|
||||
const db_config = require('./database')
|
||||
const express = require('express')
|
||||
const server = express()
|
||||
const cors = require('cors')
|
||||
const path = require('path')
|
||||
const passport = require('passport')
|
||||
const flash = require('express-flash')
|
||||
const session = require('express-session')
|
||||
const methodOverride = require('method-override')
|
||||
const multer = require('multer')
|
||||
const QiwiBillPaymentsAPI = require('@qiwi/bill-payments-node-js-sdk')
|
||||
|
||||
const qiwiApi = new QiwiBillPaymentsAPI(process.env.QIWI_SECRET_KEY);
|
||||
const qiwiApi = new QiwiBillPaymentsAPI(process.env.QIWI_SECRET_KEY)
|
||||
|
||||
MongoClient.connect(db_config.url, {useNewUrlParser: true, useUnifiedTopology: true})
|
||||
.then((client) => {
|
||||
const db = client.db(db_config.name);
|
||||
const storage = multer.diskStorage({
|
||||
destination: 'dist/public/img/service-icons',
|
||||
filename: function(req, file, cb) {
|
||||
cb(null, `${file.fieldname}-${Date.now()}${path.extname(file.originalname)}`);
|
||||
}
|
||||
});
|
||||
|
||||
// Config
|
||||
server.use(cors());
|
||||
server.use(express.static(`${__dirname}/../dist/public`));
|
||||
server.use(multer({storage: storage}).single('img'));
|
||||
server.use(express.urlencoded({ extended: false }));
|
||||
server.use(express.json());
|
||||
server.use(flash());
|
||||
server.use(session({secret: require('crypto-random-string')({length: 64, type: 'base64'}), resave: true,saveUninitialized: false}));
|
||||
server.use(passport.initialize());
|
||||
server.use(passport.session());
|
||||
server.use(methodOverride('_method'));
|
||||
server.set('view engine', 'pug');
|
||||
server.set('views', `${__dirname}/../dist/views`);
|
||||
|
||||
// Routes
|
||||
require('./routes/main')(server, db); // маршруты сайта
|
||||
require('./routes/admin')(server, db); // маршрут с формой авторизации админа
|
||||
require('./routes/control-panel')(server, db); // маршруты с панелью управления
|
||||
require('./routes/api')(server, db); // отдача данных клиенту
|
||||
|
||||
// Payments
|
||||
require('./routes/success')(server, db, qiwiApi);
|
||||
require('./routes/payments/qiwi.payment')(server, db, qiwiApi);
|
||||
|
||||
// 404 Redirect
|
||||
server.use((req, res) => res.status(404).render('main/404'));
|
||||
MongoClient.connect(db_config.url, {
|
||||
useNewUrlParser: true,
|
||||
useUnifiedTopology: true,
|
||||
})
|
||||
.then((client) => {
|
||||
const db = client.db(db_config.name)
|
||||
const storage = multer.diskStorage({
|
||||
destination: 'dist/public/img/service-icons',
|
||||
filename: function (req, file, cb) {
|
||||
cb(
|
||||
null,
|
||||
`${file.fieldname}-${Date.now()}${path.extname(file.originalname)}`
|
||||
)
|
||||
},
|
||||
})
|
||||
.catch((error) => {
|
||||
server.get('*', (req, res) => {
|
||||
res.send('Произошла ошибка при запуске. Используйте команду "pm2 log" для того чтобы узнать ошибку.');
|
||||
console.log(error);
|
||||
});
|
||||
|
||||
// Config
|
||||
server.use(cors())
|
||||
server.use(express.static(`${__dirname}/../dist/public`))
|
||||
server.use(multer({ storage: storage }).single('img'))
|
||||
server.use(express.urlencoded({ extended: false }))
|
||||
server.use(express.json())
|
||||
server.use(flash())
|
||||
server.use(
|
||||
session({
|
||||
secret: require('crypto-random-string')({ length: 64, type: 'base64' }),
|
||||
resave: true,
|
||||
saveUninitialized: false,
|
||||
})
|
||||
)
|
||||
server.use(passport.initialize())
|
||||
server.use(passport.session())
|
||||
server.use(methodOverride('_method'))
|
||||
server.set('view engine', 'pug')
|
||||
server.set('views', `${__dirname}/../dist/views`)
|
||||
|
||||
// Routes
|
||||
require('./routes/main')(server, db) // маршруты сайта
|
||||
require('./routes/admin')(server, db) // маршрут с формой авторизации админа
|
||||
require('./routes/control-panel')(server, db) // маршруты с панелью управления
|
||||
require('./routes/api')(server, db) // отдача данных клиенту
|
||||
|
||||
// Payments
|
||||
require('./routes/success')(server, db, qiwiApi)
|
||||
require('./routes/payments/qiwi.payment')(server, db, qiwiApi)
|
||||
|
||||
// 404 Redirect
|
||||
server.use((req, res) => res.status(404).render('main/404'))
|
||||
})
|
||||
.catch((error) => {
|
||||
server.get('*', (req, res) => {
|
||||
res.send('Произошла ошибка.')
|
||||
console.log(error)
|
||||
})
|
||||
.finally(server.listen(process.env.PORT || 3000, console.log('App is running...')));
|
||||
})
|
||||
.finally(
|
||||
server.listen(process.env.PORT || 3000, console.log('App is running...'))
|
||||
)
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user