Compare commits
2 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 0114a88043 | |||
| 4993816a95 |
7
.gitignore
vendored
7
.gitignore
vendored
@@ -12,6 +12,13 @@ dist
|
|||||||
dist-ssr
|
dist-ssr
|
||||||
*.local
|
*.local
|
||||||
|
|
||||||
|
# Env files (never commit secrets)
|
||||||
|
.env
|
||||||
|
.env.*
|
||||||
|
!.env.example
|
||||||
|
!.env.production
|
||||||
|
backend/.env
|
||||||
|
|
||||||
# Editor directories and files
|
# Editor directories and files
|
||||||
.vscode/*
|
.vscode/*
|
||||||
!.vscode/extensions.json
|
!.vscode/extensions.json
|
||||||
|
|||||||
30
README.md
30
README.md
@@ -86,7 +86,17 @@ VITE_DOMA_AI_PASSWORD=your-password
|
|||||||
|
|
||||||
**Для тестирования** можно использовать тестовый стенд: https://condo.d.doma.ai/
|
**Для тестирования** можно использовать тестовый стенд: https://condo.d.doma.ai/
|
||||||
|
|
||||||
### 3. Запуск в режиме разработки
|
### 3. (Ubuntu) Один раз настройте PostgreSQL
|
||||||
|
|
||||||
|
Логин и пароль БД заданы в `backend/.env` (логин: **mkd_user**, пароль: **MkdUbuntu24Secure**). Выполните в терминале (введёте пароль sudo):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo bash scripts/setup-postgres-ubuntu.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
Затем в одном терминале: `cd backend && npm start`, в другом: `npm run dev`.
|
||||||
|
|
||||||
|
### 4. Запуск в режиме разработки
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm run dev
|
npm run dev
|
||||||
@@ -94,13 +104,27 @@ npm run dev
|
|||||||
|
|
||||||
Приложение будет доступно по адресу: `http://localhost:3000`
|
Приложение будет доступно по адресу: `http://localhost:3000`
|
||||||
|
|
||||||
### 4. Сборка для продакшена
|
### 4.1. Запуск в tmux (не зависит от SSH)
|
||||||
|
|
||||||
|
Бэкенд и фронт в tmux-сессиях **back** и **front** — после отключения SSH процессы продолжают работать.
|
||||||
|
|
||||||
|
```bash
|
||||||
|
bash scripts/start-tmux.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
- Подключиться к логам: `tmux attach -t back` или `tmux attach -t front`
|
||||||
|
- Выйти из tmux без остановки: **Ctrl+B**, затем **D**
|
||||||
|
- Список сессий: `tmux ls`
|
||||||
|
|
||||||
|
Доступ снаружи (если открыты порты в файрволе): **http://<IP-сервера>:3000** (фронт), **http://<IP-сервера>:4000/api** (API). На Ubuntu при необходимости: `sudo ufw allow 3000 && sudo ufw allow 4000 && sudo ufw reload`
|
||||||
|
|
||||||
|
### 5. Сборка для продакшена
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm run build
|
npm run build
|
||||||
```
|
```
|
||||||
|
|
||||||
### 5. Просмотр production сборки
|
### 6. Просмотр production сборки
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm run preview
|
npm run preview
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
PORT=4000
|
PORT=4000
|
||||||
DATABASE_URL=postgres://mkd_user:Nemo348ax@@localhost:5432/mkd_control_center
|
# Логин: mkd_user, пароль: MkdUbuntu24Secure
|
||||||
DOMA_API_URL=https://condo.d.doma.ai/admin/api
|
DATABASE_URL=postgres://mkd_user:MkdUbuntu24Secure@localhost:5432/mkd_control_center
|
||||||
|
DOMA_API_URL=https://condo.d.doma.ai/admin/api
|
||||||
DOMA_API_TOKEN=d-7Tf8g0r277ismVAmBnVOZvxaTBYCkz.CLBfWjkEc503Df4Nifw558wKi3w1XnvpF/L4zIDqylc
|
DOMA_API_TOKEN=d-7Tf8g0r277ismVAmBnVOZvxaTBYCkz.CLBfWjkEc503Df4Nifw558wKi3w1XnvpF/L4zIDqylc
|
||||||
@@ -12,6 +12,13 @@ const DEFAULT_ADMIN_LOGIN = 'its';
|
|||||||
const DEFAULT_ADMIN_PASSWORD = 'iiEasy348ax@';
|
const DEFAULT_ADMIN_PASSWORD = 'iiEasy348ax@';
|
||||||
const DEFAULT_ADMIN_ROLE = 'DIRECTOR';
|
const DEFAULT_ADMIN_ROLE = 'DIRECTOR';
|
||||||
|
|
||||||
|
// Демо-пользователь с теми же правами, что и its (DIRECTOR)
|
||||||
|
const DEMO_EMPLOYEE_ID = 'e-demo';
|
||||||
|
const DEMO_EMPLOYEE_NAME = 'Demo';
|
||||||
|
const DEMO_LOGIN = 'demo';
|
||||||
|
const DEMO_PASSWORD = 'demo123';
|
||||||
|
const DEMO_ROLE = 'DIRECTOR';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Инициализация базы данных PostgreSQL
|
* Инициализация базы данных PostgreSQL
|
||||||
* Создает БД при первом запуске и проверяет целостность при последующих запусках
|
* Создает БД при первом запуске и проверяет целостность при последующих запусках
|
||||||
@@ -220,6 +227,9 @@ async function initializeDatabase() {
|
|||||||
// Администратор портала по умолчанию (логин its) — создаётся, если ещё нет
|
// Администратор портала по умолчанию (логин its) — создаётся, если ещё нет
|
||||||
await applyDefaultAdminSeed(client);
|
await applyDefaultAdminSeed(client);
|
||||||
|
|
||||||
|
// Демо-пользователь (demo / demo123) с правами DIRECTOR — создаётся при каждом старте, если ещё нет
|
||||||
|
await applyDemoUserSeed(client);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
success: true,
|
success: true,
|
||||||
initialized: !integrityCheck.isInitialized,
|
initialized: !integrityCheck.isInitialized,
|
||||||
@@ -2572,6 +2582,55 @@ async function applyDefaultAdminSeed(client) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Демо-пользователь портала (логин demo, пароль demo123) с правами DIRECTOR, как у its.
|
||||||
|
*/
|
||||||
|
async function applyDemoUserSeed(client) {
|
||||||
|
try {
|
||||||
|
const existingUser = await client.query(
|
||||||
|
'SELECT id FROM portal_users WHERE login = $1',
|
||||||
|
[DEMO_LOGIN]
|
||||||
|
);
|
||||||
|
if (existingUser.rows.length > 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const employeeExists = await client.query(
|
||||||
|
'SELECT id FROM employees WHERE id = $1',
|
||||||
|
[DEMO_EMPLOYEE_ID]
|
||||||
|
);
|
||||||
|
if (employeeExists.rows.length === 0) {
|
||||||
|
await client.query(
|
||||||
|
`INSERT INTO employees (id, name, position, phone, status, salary, assigned_district_id)
|
||||||
|
VALUES ($1, $2, $3, $4, $5, $6, $7)
|
||||||
|
ON CONFLICT (id) DO NOTHING`,
|
||||||
|
[
|
||||||
|
DEMO_EMPLOYEE_ID,
|
||||||
|
DEMO_EMPLOYEE_NAME,
|
||||||
|
'Демо-пользователь',
|
||||||
|
'+70000000001',
|
||||||
|
'active',
|
||||||
|
0,
|
||||||
|
null,
|
||||||
|
]
|
||||||
|
);
|
||||||
|
console.log('[dbInit] Создан сотрудник для демо:', DEMO_EMPLOYEE_NAME);
|
||||||
|
}
|
||||||
|
const passwordHash = await bcrypt.hash(DEMO_PASSWORD, 10);
|
||||||
|
await client.query(
|
||||||
|
`INSERT INTO portal_users (employee_id, login, role, password_hash, is_active)
|
||||||
|
VALUES ($1, $2, $3, $4, true)
|
||||||
|
ON CONFLICT (login) DO NOTHING`,
|
||||||
|
[DEMO_EMPLOYEE_ID, DEMO_LOGIN, DEMO_ROLE, passwordHash]
|
||||||
|
);
|
||||||
|
const check = await client.query('SELECT id FROM portal_users WHERE login = $1', [DEMO_LOGIN]);
|
||||||
|
if (check.rows.length > 0) {
|
||||||
|
console.log('[dbInit] Создан демо-пользователь портала: логин', DEMO_LOGIN, ', роль', DEMO_ROLE);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.warn('[dbInit] Ошибка при создании демо-пользователя:', error.message);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Таблица настроек интеграций (DaData и др.)
|
* Таблица настроек интеграций (DaData и др.)
|
||||||
*/
|
*/
|
||||||
|
|||||||
6
backend/package-lock.json
generated
6
backend/package-lock.json
generated
@@ -862,7 +862,8 @@
|
|||||||
"version": "0.0.1551306",
|
"version": "0.0.1551306",
|
||||||
"resolved": "https://registry.npmjs.org/devtools-protocol/-/devtools-protocol-0.0.1551306.tgz",
|
"resolved": "https://registry.npmjs.org/devtools-protocol/-/devtools-protocol-0.0.1551306.tgz",
|
||||||
"integrity": "sha512-CFx8QdSim8iIv+2ZcEOclBKTQY6BI1IEDa7Tm9YkwAXzEWFndTEzpTo5jAUhSnq24IC7xaDw0wvGcm96+Y3PEg==",
|
"integrity": "sha512-CFx8QdSim8iIv+2ZcEOclBKTQY6BI1IEDa7Tm9YkwAXzEWFndTEzpTo5jAUhSnq24IC7xaDw0wvGcm96+Y3PEg==",
|
||||||
"license": "BSD-3-Clause"
|
"license": "BSD-3-Clause",
|
||||||
|
"peer": true
|
||||||
},
|
},
|
||||||
"node_modules/dom-serializer": {
|
"node_modules/dom-serializer": {
|
||||||
"version": "2.0.0",
|
"version": "2.0.0",
|
||||||
@@ -1929,7 +1930,6 @@
|
|||||||
"resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz",
|
"resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz",
|
||||||
"integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==",
|
"integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"peer": true,
|
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"js-tokens": "^3.0.0 || ^4.0.0"
|
"js-tokens": "^3.0.0 || ^4.0.0"
|
||||||
},
|
},
|
||||||
@@ -2330,6 +2330,7 @@
|
|||||||
"resolved": "https://registry.npmjs.org/pg/-/pg-8.17.2.tgz",
|
"resolved": "https://registry.npmjs.org/pg/-/pg-8.17.2.tgz",
|
||||||
"integrity": "sha512-vjbKdiBJRqzcYw1fNU5KuHyYvdJ1qpcQg1CeBrHFqV1pWgHeVR6j/+kX0E1AAXfyuLUGY1ICrN2ELKA/z2HWzw==",
|
"integrity": "sha512-vjbKdiBJRqzcYw1fNU5KuHyYvdJ1qpcQg1CeBrHFqV1pWgHeVR6j/+kX0E1AAXfyuLUGY1ICrN2ELKA/z2HWzw==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"pg-connection-string": "^2.10.1",
|
"pg-connection-string": "^2.10.1",
|
||||||
"pg-pool": "^3.11.0",
|
"pg-pool": "^3.11.0",
|
||||||
@@ -2806,7 +2807,6 @@
|
|||||||
"resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz",
|
"resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz",
|
||||||
"integrity": "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==",
|
"integrity": "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"peer": true,
|
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"loose-envify": "^1.1.0"
|
"loose-envify": "^1.1.0"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -374,8 +374,8 @@ async function startServer() {
|
|||||||
process.exit(1);
|
process.exit(1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
app.listen(PORT, () => {
|
app.listen(PORT, '0.0.0.0', () => {
|
||||||
console.log(`Backend API running on http://localhost:${PORT}${API_PREFIX}`);
|
console.log(`Backend API running on http://0.0.0.0:${PORT}${API_PREFIX}`);
|
||||||
if (DATABASE_URL) {
|
if (DATABASE_URL) {
|
||||||
ensureEmployeeResponsibilityTable()
|
ensureEmployeeResponsibilityTable()
|
||||||
.then(() => console.log('[backend] Таблица employee_responsibility проверена/создана'))
|
.then(() => console.log('[backend] Таблица employee_responsibility проверена/создана'))
|
||||||
|
|||||||
161
docs/UBUNTU_SETUP.md
Normal file
161
docs/UBUNTU_SETUP.md
Normal file
@@ -0,0 +1,161 @@
|
|||||||
|
# Запуск проекта на Ubuntu 24.04
|
||||||
|
|
||||||
|
После переноса с Windows проект запускается на Ubuntu так же через Node.js и PostgreSQL. Ниже — пошаговая настройка.
|
||||||
|
|
||||||
|
## 1. Установка Node.js (18+)
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Через NodeSource (рекомендуется LTS)
|
||||||
|
curl -fsSL https://deb.nodesource.com/setup_20.x | sudo -E bash -
|
||||||
|
sudo apt-get install -y nodejs
|
||||||
|
|
||||||
|
# Проверка
|
||||||
|
node -v # v20.x.x
|
||||||
|
npm -v
|
||||||
|
```
|
||||||
|
|
||||||
|
Либо через стандартный репозиторий Ubuntu:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo apt update
|
||||||
|
sudo apt install -y nodejs npm
|
||||||
|
```
|
||||||
|
|
||||||
|
## 2. Установка PostgreSQL
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo apt update
|
||||||
|
sudo apt install -y postgresql postgresql-contrib
|
||||||
|
sudo systemctl start postgresql
|
||||||
|
sudo systemctl enable postgresql
|
||||||
|
```
|
||||||
|
|
||||||
|
Создание пользователя и базы (опционально, если ещё не созданы):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo -u postgres psql -c "CREATE USER mkd_user WITH PASSWORD 'your_password';"
|
||||||
|
sudo -u postgres psql -c "CREATE DATABASE mkd_control_center OWNER mkd_user;"
|
||||||
|
```
|
||||||
|
|
||||||
|
Строка подключения для `.env` бэкенда:
|
||||||
|
|
||||||
|
```
|
||||||
|
postgres://mkd_user:your_password@localhost:5432/mkd_control_center
|
||||||
|
```
|
||||||
|
|
||||||
|
## 3. Зависимости для Puppeteer (бэкенд)
|
||||||
|
|
||||||
|
Бэкенд использует Puppeteer. На Ubuntu нужны системные библиотеки:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo apt install -y \
|
||||||
|
ca-certificates fonts-liberation libasound2 libatk-bridge2.0-0 \
|
||||||
|
libatk1.0-0 libc6 libcairo2 libcups2 libdbus-1-3 libexpat1 \
|
||||||
|
libfontconfig1 libgbm1 libgcc1 libglib2.0-0 libgtk-3-0 libnspr4 \
|
||||||
|
libnss3 libpango-1.0-0 libpangocairo-1.0-0 libstdc++6 libx11-6 \
|
||||||
|
libx11-xcb1 libxcb1 libxcomposite1 libxcursor1 libxdamage1 \
|
||||||
|
libxext6 libxfixes3 libxi6 libxrandr2 libxrender1 libxss1 \
|
||||||
|
libxtst6 lsb-release wget xdg-utils
|
||||||
|
```
|
||||||
|
|
||||||
|
## 4. Настройка проекта
|
||||||
|
|
||||||
|
### 4.1 Клонирование / копирование
|
||||||
|
|
||||||
|
Если репозиторий уже скопирован в каталог проекта (например, `/home/its/mkd`), переходите в него:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd /home/its/mkd
|
||||||
|
```
|
||||||
|
|
||||||
|
### 4.2 Установка зависимостей
|
||||||
|
|
||||||
|
В корне (фронтенд) и в `backend`:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
npm install
|
||||||
|
cd backend && npm install && cd ..
|
||||||
|
```
|
||||||
|
|
||||||
|
### 4.3 Переменные окружения
|
||||||
|
|
||||||
|
**Корень проекта** — для фронтенда. Создайте `.env` или `.env.local` на основе `.env.example`:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cp .env.example .env.local
|
||||||
|
# Отредактируйте .env.local при необходимости (VITE_API_BASE_URL, Doma AI и т.д.)
|
||||||
|
```
|
||||||
|
|
||||||
|
**Бэкенд** — в `backend/.env` должны быть минимум:
|
||||||
|
|
||||||
|
```env
|
||||||
|
# Обязательно для работы БД
|
||||||
|
DATABASE_URL=postgres://mkd_user:your_password@localhost:5432/mkd_control_center
|
||||||
|
|
||||||
|
# Обязательно в production
|
||||||
|
JWT_SECRET=ваш-секретный-ключ-для-jwt
|
||||||
|
JWT_EXPIRES_IN=7d
|
||||||
|
|
||||||
|
# Опционально: Doma AI, Turnstile и т.д.
|
||||||
|
# DOMA_API_URL=...
|
||||||
|
# DOMA_API_TOKEN=...
|
||||||
|
```
|
||||||
|
|
||||||
|
Пути в конфигах (например, `path.join(__dirname, 'uploads')`) на Linux не меняют — Node использует `/` и `path.join` корректно.
|
||||||
|
|
||||||
|
## 5. Запуск
|
||||||
|
|
||||||
|
Нужны два процесса: бэкенд (API) и фронтенд (Vite).
|
||||||
|
|
||||||
|
### Вариант A: два терминала
|
||||||
|
|
||||||
|
**Терминал 1 — бэкенд:**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd /home/its/mkd/backend
|
||||||
|
npm start
|
||||||
|
```
|
||||||
|
|
||||||
|
Должно появиться сообщение о запуске на порту 4000 (или вашем `PORT`).
|
||||||
|
|
||||||
|
**Терминал 2 — фронтенд:**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd /home/its/mkd
|
||||||
|
npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
Откройте в браузере: **http://localhost:3000**. Запросы к `/api` уйдут на бэкенд через прокси Vite (localhost:4000).
|
||||||
|
|
||||||
|
### Вариант B: один терминал (фоновый бэкенд)
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd /home/its/mkd/backend && npm start &
|
||||||
|
cd /home/its/mkd && npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
### Сборка для production
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd /home/its/mkd
|
||||||
|
npm run build
|
||||||
|
```
|
||||||
|
|
||||||
|
Статика окажется в `dist/`. Раздавать её можно nginx’ом, указав API и `uploads` на бэкенд (порт 4000).
|
||||||
|
|
||||||
|
## 6. Проверка
|
||||||
|
|
||||||
|
| Компонент | URL / проверка |
|
||||||
|
|------------|----------------|
|
||||||
|
| Фронтенд | http://localhost:3000 |
|
||||||
|
| API бэкенд | http://localhost:4000/api (например, health, если есть) |
|
||||||
|
| PostgreSQL | `sudo -u postgres psql -c "\l"` — список баз |
|
||||||
|
|
||||||
|
## 7. Частые проблемы на Ubuntu
|
||||||
|
|
||||||
|
- **«DATABASE_URL не задана»** — добавьте `DATABASE_URL` в `backend/.env` и перезапустите бэкенд.
|
||||||
|
- **Puppeteer/Chromium не запускается** — установите зависимости из пункта 3; при необходимости в `backend` можно задать `PUPPETEER_EXECUTABLE_PATH` на системный chromium.
|
||||||
|
- **Порт 3000 или 4000 занят** — смените в `.env`: фронт — `server.port` в `vite.config.ts` или переменные Vite; бэкенд — `PORT` в `backend/.env`.
|
||||||
|
- **Права на каталог uploads** — если бэкенд пишет файлы от другого пользователя: `chmod 755 backend/uploads` (или 775 при необходимости).
|
||||||
|
|
||||||
|
После выполнения шагов 1–5 проект на Ubuntu 24.04 должен запускаться так же, как на Windows.
|
||||||
8
package-lock.json
generated
8
package-lock.json
generated
@@ -54,6 +54,7 @@
|
|||||||
"integrity": "sha512-H3mcG6ZDLTlYfaSNi0iOKkigqMFvkTKlGUYlD8GW7nNOYRrevuA46iTypPyv+06V3fEmvvazfntkBU34L0azAw==",
|
"integrity": "sha512-H3mcG6ZDLTlYfaSNi0iOKkigqMFvkTKlGUYlD8GW7nNOYRrevuA46iTypPyv+06V3fEmvvazfntkBU34L0azAw==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@babel/code-frame": "^7.28.6",
|
"@babel/code-frame": "^7.28.6",
|
||||||
"@babel/generator": "^7.28.6",
|
"@babel/generator": "^7.28.6",
|
||||||
@@ -1221,6 +1222,7 @@
|
|||||||
"integrity": "sha512-MciR4AKGHWl7xwxkBa6xUGxQJ4VBOmPTF7sL+iGzuahOFaO0jHCsuEfS80pan1ef4gWId1oWOweIhrDEYLuaOw==",
|
"integrity": "sha512-MciR4AKGHWl7xwxkBa6xUGxQJ4VBOmPTF7sL+iGzuahOFaO0jHCsuEfS80pan1ef4gWId1oWOweIhrDEYLuaOw==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"undici-types": "~6.21.0"
|
"undici-types": "~6.21.0"
|
||||||
}
|
}
|
||||||
@@ -1305,6 +1307,7 @@
|
|||||||
}
|
}
|
||||||
],
|
],
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"baseline-browser-mapping": "^2.9.0",
|
"baseline-browser-mapping": "^2.9.0",
|
||||||
"caniuse-lite": "^1.0.30001759",
|
"caniuse-lite": "^1.0.30001759",
|
||||||
@@ -1719,6 +1722,7 @@
|
|||||||
"integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==",
|
"integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=12"
|
"node": ">=12"
|
||||||
},
|
},
|
||||||
@@ -1775,6 +1779,7 @@
|
|||||||
"resolved": "https://registry.npmjs.org/quill-delta/-/quill-delta-5.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/quill-delta/-/quill-delta-5.1.0.tgz",
|
||||||
"integrity": "sha512-X74oCeRI4/p0ucjb5Ma8adTXd9Scumz367kkMK5V/IatcX6A0vlgLgKbzXWy5nZmCGeNJm2oQX0d2Eqj+ZIlCA==",
|
"integrity": "sha512-X74oCeRI4/p0ucjb5Ma8adTXd9Scumz367kkMK5V/IatcX6A0vlgLgKbzXWy5nZmCGeNJm2oQX0d2Eqj+ZIlCA==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"fast-diff": "^1.3.0",
|
"fast-diff": "^1.3.0",
|
||||||
"lodash.clonedeep": "^4.5.0",
|
"lodash.clonedeep": "^4.5.0",
|
||||||
@@ -1799,6 +1804,7 @@
|
|||||||
"resolved": "https://registry.npmjs.org/react/-/react-19.2.3.tgz",
|
"resolved": "https://registry.npmjs.org/react/-/react-19.2.3.tgz",
|
||||||
"integrity": "sha512-Ku/hhYbVjOQnXDZFv2+RibmLFGwFdeeKHFcOTlrt7xplBnya5OGn/hIRDsqDiSUcfORsDC7MPxwork8jBwsIWA==",
|
"integrity": "sha512-Ku/hhYbVjOQnXDZFv2+RibmLFGwFdeeKHFcOTlrt7xplBnya5OGn/hIRDsqDiSUcfORsDC7MPxwork8jBwsIWA==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=0.10.0"
|
"node": ">=0.10.0"
|
||||||
}
|
}
|
||||||
@@ -1808,6 +1814,7 @@
|
|||||||
"resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.3.tgz",
|
"resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.3.tgz",
|
||||||
"integrity": "sha512-yELu4WmLPw5Mr/lmeEpox5rw3RETacE++JgHqQzd2dg+YbJuat3jH4ingc+WPZhxaoFzdv9y33G+F7Nl5O0GBg==",
|
"integrity": "sha512-yELu4WmLPw5Mr/lmeEpox5rw3RETacE++JgHqQzd2dg+YbJuat3jH4ingc+WPZhxaoFzdv9y33G+F7Nl5O0GBg==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"scheduler": "^0.27.0"
|
"scheduler": "^0.27.0"
|
||||||
},
|
},
|
||||||
@@ -2041,6 +2048,7 @@
|
|||||||
"integrity": "sha512-+Oxm7q9hDoLMyJOYfUYBuHQo+dkAloi33apOPP56pzj+vsdJDzr+j1NISE5pyaAuKL4A3UD34qd0lx5+kfKp2g==",
|
"integrity": "sha512-+Oxm7q9hDoLMyJOYfUYBuHQo+dkAloi33apOPP56pzj+vsdJDzr+j1NISE5pyaAuKL4A3UD34qd0lx5+kfKp2g==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
"peer": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"esbuild": "^0.25.0",
|
"esbuild": "^0.25.0",
|
||||||
"fdir": "^6.4.4",
|
"fdir": "^6.4.4",
|
||||||
|
|||||||
8
scripts/setup-postgres-ubuntu.sh
Executable file
8
scripts/setup-postgres-ubuntu.sh
Executable file
@@ -0,0 +1,8 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# Один раз выполните: sudo bash scripts/setup-postgres-ubuntu.sh
|
||||||
|
# Логин: mkd_user, пароль: MkdUbuntu24Secure
|
||||||
|
set -e
|
||||||
|
sudo -u postgres psql -c "DO \$\$ BEGIN CREATE USER mkd_user WITH PASSWORD 'MkdUbuntu24Secure'; EXCEPTION WHEN duplicate_object THEN ALTER USER mkd_user WITH PASSWORD 'MkdUbuntu24Secure'; END \$\$;"
|
||||||
|
sudo -u postgres psql -c "SELECT 1 FROM pg_database WHERE datname='mkd_control_center'" | grep -q 1 || sudo -u postgres psql -c "CREATE DATABASE mkd_control_center OWNER mkd_user;"
|
||||||
|
sudo -u postgres psql -d mkd_control_center -c "GRANT ALL ON SCHEMA public TO mkd_user; GRANT CREATE ON SCHEMA public TO mkd_user;"
|
||||||
|
echo "Готово. Логин: mkd_user, пароль: MkdUbuntu24Secure"
|
||||||
29
scripts/start-tmux.sh
Executable file
29
scripts/start-tmux.sh
Executable file
@@ -0,0 +1,29 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# Запуск бэкенда и фронтенда в tmux (сессии back и front).
|
||||||
|
# После отключения SSH процессы продолжают работать.
|
||||||
|
# Подключиться: tmux attach -t back или tmux attach -t front
|
||||||
|
# Список сессий: tmux ls
|
||||||
|
|
||||||
|
set -e
|
||||||
|
ROOT="$(cd "$(dirname "$0")/.." && pwd)"
|
||||||
|
cd "$ROOT"
|
||||||
|
|
||||||
|
# Если порты заняты не tmux — освободите: kill процесс на 4000 и 3000, затем запустите скрипт снова.
|
||||||
|
echo "Останавливаем старые сессии tmux back/front..."
|
||||||
|
tmux kill-session -t back 2>/dev/null || true
|
||||||
|
tmux kill-session -t front 2>/dev/null || true
|
||||||
|
|
||||||
|
# Backend в сессии "back"
|
||||||
|
tmux new-session -d -s back -c "$ROOT/backend" "npm start"
|
||||||
|
|
||||||
|
# Frontend в сессии "front"
|
||||||
|
tmux new-session -d -s front -c "$ROOT" "npm run dev"
|
||||||
|
|
||||||
|
echo "Tmux сессии запущены:"
|
||||||
|
echo " back — бэкенд (порт 4000)"
|
||||||
|
echo " front — фронтенд (порт 3000)"
|
||||||
|
echo ""
|
||||||
|
echo "Подключиться: tmux attach -t back или tmux attach -t front"
|
||||||
|
echo "Выйти из tmux без остановки: Ctrl+B, затем D"
|
||||||
|
echo ""
|
||||||
|
echo "Доступ снаружи: http://<IP-сервера>:3000 (фронт), :4000/api (API)"
|
||||||
@@ -8,7 +8,7 @@ export default defineConfig(({ mode }) => {
|
|||||||
server: {
|
server: {
|
||||||
port: 3000,
|
port: 3000,
|
||||||
host: '0.0.0.0',
|
host: '0.0.0.0',
|
||||||
allowedHosts: ['note.iieasy.ru'],
|
allowedHosts: true,
|
||||||
proxy: {
|
proxy: {
|
||||||
'/api': {
|
'/api': {
|
||||||
target: process.env.API_PROXY_TARGET || 'http://localhost:4000',
|
target: process.env.API_PROXY_TARGET || 'http://localhost:4000',
|
||||||
|
|||||||
Reference in New Issue
Block a user