Как я развернул сайт на Java Spring Boot + Angular SSR с Docker и Nginx: личный опыт
Реальный опыт развёртывания сайта на Spring Boot и Angular SSR с использованием Docker, Nginx и HTTPS. Ошибки, тонкости настройки и защита от ботов — всё по шагам.
445 открытий3К показов

Проект представляет собой веб-приложение на Spring Boot и Angular. Первоначально я выбрал простую монолитную архитектуру, но по мере роста требований и целей пришлось перейти на микросервисный подход. Здесь я расскажу, как это происходило: с конфигурациями, ошибками и решениями.
Монолитная архитектура
Исходная схема:
- Backend: Spring Boot
- Frontend: Angular
Так как у меня уже был арендованный VDS, я зарегистрировал домен у одного известного провайдера, а хостил сайт уже на VDS сервере. Для простоты интегрировал Angular-сборку в Spring Boot как статику через frontend-maven-plugin. Всё собиралось в один JAR. Почему так? Ранее уже был такой опыт, и я решил пойти этим путем.
После регистрации домена необходимо подождать, чтобы ввести доменное имя. Значит есть время для запуска и настройки приложения. Однако при тестировании проявились ключевые недостатки:
- Отсутствие SSR в Angular негативно влияло на SEO;
- Ошибка в Angular ломала Maven-сборку;
- Сложно поддерживать и масштабировать.
Переход на микросервисы
Было принято решение разделить фронтенд и бэкенд на отдельные сервисы и использовать микросервисный подход с SSR для Angular:
Новая структура:
- Backend: Spring Boot
- Frontend: Angular Universal (SSR)
- Инфраструктура: Docker Compose, Nginx, HTTPS
Docker, Nginx и запуск
Создана базовая структура docker-compose.yml:
И соответствующий Nginx:
После запуска проект открывался по IP, но появилось множество проблем:
- Дублирование API-префиксов: /api/api/endpoint → Решение: корректировка proxy_pass и URL в Angular
- Редиректы на POST: Spring добавлял лишние слеши → Решение: правильные аннотации и настройка Nginx
- 405 Method Not Allowed → Решение: использовать @PostMapping
- Docker-сети → Решение: задать общую сеть в docker-compose.yml
Безопасность: HTTPS, SSL, CORS
Чтобы сайт открывался по имени с панели провайдера для моего домена, значения DNS-сервера оставил без изменений (провайдер предоставляет их бесплатно), а для ресурсной записи @ и www указал ip адрес своего хостинга. Так как провайдер домена бесплатно предоставил SSL-сертификаты (Let's Encrypt), то как я их интегрировал:
Скачал с панели провайдера и перенес на хостинг такие файлы:
domain.crt — сертификат
domain.key — приватный ключ
ca_bundle.crt — цепочка доверия
Добавил в Nginx такую запись для HTTPS:
Но при обращении к сайту по https конечно же возникли ошибки.
А именно: в логах Nginx были ошибки на
SSL_CTX_use_PrivateKey_file
.
Оказалось формат был PKCS#7, а
требовался PEM. Конвертировал через
OpenSSL:
Так как сертификаты имеют срок действия, не стоит забывать об их продлении и обновлении.
К тому же всегда следует проверять логи Nginx (error.log), там могут находится ответы на вопросы, почему сайт не работает.
На стороне Spring Boot были CORS-проблемы, решено так:
Атаки ботов и защита
После запуска сайта в логах Nginx стали появляться тысячи запросов от ботов, ищущих уязвимости WordPress, PHPMyAdmin и других популярных утилит, хотя мой сайт работает на Java/Angular. Пример лога:
45.155.205.213 - - [01/Jan/2023:04:12:11 +0000] "GET /wp-login.php HTTP/1.1" 404 153
Добавлен фильтр в nginx.conf:
Финальная конфигурация
После всех настроек мой сайт работает и полностью функционирует. Конфигурация сильно изменена по сравнению с первоначальной. Вот как они выглядят сейчас.
docker-compose.yml
nginx.conf
Dockerfile backend
Dockerfile frontend
Разделение сервисов улучшило поддержку и масштабируемость, к тому же, я получил ценные знания. Надеюсь, статья будет полезна тем, кто разворачивает подобные конфигурации на Java и Angular.
445 открытий3К показов