Автор статьи Александр В., Senior Java разработчик
Автор статьи Александр В., Senior Java разработчик

В начале 2000-х Java Enterprise (тогда - J2EE) ассоциировалась с тяжёлыми серверами приложений, многослойной архитектурой и огромным количеством шаблонного кода. Разработка enterprise-приложений требовала глубокого понимания сложных спецификаций, а сам процесс был медленным, бюрократичным и далёким от гибкости.

Именно в этот период на сцену вышел Spring Framework — сначала как скромная альтернатива, а затем как настоящая революция в Java-мире. Он предложил радикально иной подход: простоту, ориентированность на бизнес-логику и свободу от излишней инфраструктурной навязчивости.

Цель данной статьи — рассмотреть Spring не как данность, а как эволюционирующий инструмент. Мы проследим, как менялись его идеи, подходы и архитектурные парадигмы: от борьбы с J2EE до микросервисов, реактивности и cloud-native-приложений. Каждая эпоха диктовала свои вызовы - и Spring неоднократно перерождался, чтобы оставаться актуальным.

Мы разделили статью на 7 частей — 7 версий нашего любимого фреймворка. Для каждой версии мы сделали небольшое приложение на тему «Пользователь и уведомление». Мы приложили максимум усилий для того, чтобы каждое приложение отражало дух того времени, когда данная версия Spring была наиболее востребована. В конце каждой части вы найдёте ссылку на репозиторий с примерами кода, который можно запустить с помощью docker-compose. В репозитории также будет находиться postman-коллекция, которую можно импортировать в postman и поэкспериментировать с отправлением http-запросов. Устраивайтесь поудобнее – мы начинаем.


Статья будет полезна:

  • Разработчикам, использующим Spring, но не знакомым с его историей;

  • Архитекторам, принимающим решения о выборе или миграции стека;

  • Техлидам и аналитикам, оценивающим долгосрочную поддержку и риски legacy-систем;

  • Студентам и начинающим инженерам, желающим понять, почему Spring стал де-факто стандартом в Java-экосистеме;

  • Безумцам, по уши влюблённым в Spring (таким, как мы)

Откуда вырос Spring: проблемы J2EE и рождение IoC

Род Джонсон — автор и основоположник Spring Framework
Род Джонсон — автор и основоположник Spring Framework

Чтобы понять, почему Spring вызвал такой резонанс, необходимо вернуться к миру J2EE начала 2000-х - эпохе EJB 2.x, гигантских XML-дескрипторов и жёстко прописанных контрактов. Enterprise JavaBeans (EJB) требовали от разработчика реализовывать специфические интерфейсы (Home, Remote), писать boilerplate-код и зависеть от тяжёлых контейнеров приложений, таких как WebLogic или WebSphere. Даже простейший компонент превращался в монолит из десятков строк шаблонного кода и конфигурации.

В этом контексте Род Джонсон (Rod Johnson), тогда — консультант по enterprise-разработке, написал книгу Expert One-on-One J2EE Design and Development (2002), в которой критиковал сложность и избыточность J2EE. В приложении к книге он представил прототип фреймворка, позже ставший Spring Framework. Его главная идея была проста: разработка должна быть проще, тестирование - легче, а зависимости - управляемыми.

Из этой критики родились ключевые принципы Spring:

  1. Inversion of Control (IoC) / Dependency Injection (DI) — зависимости внедряются извне, а не создаются компонентами самостоятельно. Это делает код слабосвязанным и легко тестируемым.

  2. POJO-first подход — обыкновенные Java-объекты без наследования от специфических классов или реализации enterprise-интерфейсов.

  3. Aspect-Oriented Programming (AOP) — чёткое разделение кросс-функциональных задач (логирование, транзакции, безопасность) от бизнес-логики.

  4. Лёгкость инфраструктуры — Spring мог работать даже вне полноценного сервера приложений, что радикально упрощало разработку и тестирование.

Хотя Dependency Injection как концепция не была изобретена Spring (её популяризации способствовали работы Мартина Фаулера), именно Spring сделал DI практичным, массовым и доступным большинству Java-разработчиков.

Эти идеи, казавшиеся тогда еретическими для enterprise-мира, быстро нашли отклик у разработчиков. Spring не просто упростил J2EE — он переосмыслил, как вообще должны строиться enterprise-приложения.


Эволюция Spring Framework по поколениям

Spring Framework 1.x (2004–2006): фундамент нового мира

Начало 2000-х стало кризисной точкой для корпоративной Java: EJB 2.x, тяжёлые контейнеры, громоздкие XML-конфигурации и неуклюжая архитектура делали даже базовую разработку мучительной. В 2002 году Род Джонсон в книге "Expert One-on-One J2EE Design and Development" предложил альтернативу — легковесную, гибкую, POJO-ориентированную инфраструктуру, которая ставит разработчика, а не контейнер, в центр процесса. Код из этой книги лег в основу Spring Framework. Первая предварительная версия (Spring 0.9) появилась в июне 2003 года, а официальный релиз Spring Framework 1.0 состоялся 24 марта 2004 года.

Spring Framework 1.x — Контроллер
Spring Framework 1.x — Контроллер

Ключевые нововведения:

  • IoC и DI: Введены BeanFactory и ApplicationContext — контейнеры, автоматически управляющие жизненным циклом объектов через инверсию управления и dependency injection.

  • AOP на прокси: Прозрачная прокси-модель для декларативного внедрения сквозной функциональности (логирование, транзакции, безопасность).

  • Spring MVC (архитектурный задел): Веб-фреймворк, построенный вокруг DispatcherServlet, заложил основополагающую архитектуру (контроллеры, маппинг запросов, разрешение представлений), которая используется до сих пор.

Экосистема

  • Фреймворк поставлялся как единый JAR-файл (spring.jar) с внутренней логической модульностью. Разделение на отдельные артефакты (spring-core, spring-beans и др.) появилось позже.

  • В 2003 году стартовал независимый проект Acegi Security (позже станет Spring Security), который предложил более гибкую модель безопасности, чем EJB, и быстро стал стандартом для Spring-приложений.

Ограничения

  • Только XML-конфигурация: В крупных проектах это приводило к нечитаемым конфигурационным файлам.

  • Ограниченная модель AOP: прокси-ориентированный подход не перехватывал внутренние вызовы методов одного бина (self-invocation), поэтому аспекты не работали в таких сценариях

  • MVC только зарождалось: архитектура уже была, но экосистема вокруг него минимальна, отсутствовали аннотации, тестирование и расширения.

  • Незрелая интеграция: не было Spring Data, Batch или Integration — всё это появится позже. Работа с внешними системами полностью ложилась на разработчика.

Ссылка на репозиторий с кодом: https://github.com/madela-team/Java/tree/master/spring-evolution/spring-1x 

Работа с базами данных в Spring 1.x
Работа с базами данных в Spring 1.x

Spring Framework 2.x (2006–2009): эпоха аннотаций и зрелости

К середине 2000-х XML-конфигурации разрослись до неуправляемых масштабов. Появление аннотаций в Java 5 (2004) дало разработчикам надежду на более декларативный стиль программирования. Spring 2.x стал переходным этапом к аннотационному миру — ключевой поворот произошёл с релизом Spring 2.5 (ноябрь 2007).

Фактически следующая версия Spring 3.0 появилась в декабре 2009 года, но линейка Spring 2.x продолжала поддерживаться. Последняя версия: 2.5.6.SEC03 - 9 сентября 2011

Spring Framework 2.x — Контроллер
Spring Framework 2.x — Контроллер

Ключевые нововведения:

  • Новые XML namespaces (Spring 2.0):

  • <tx:>, <aop:>, <context:> Это сделало XML более структурированным и читаемым, но не избавило от его избыточности.

  • Аннотационная модель (Spring 2.5):

  • @Component, @Service, @Repository, @Controller

  • @ Autowired, @ Qualifier — позволили значительно сократить объём XML и упростили конфигурацию.

  • Декларативные транзакции: @Transactional появилась уже в 2.0 (2006) , её полноценное использование для Spring-бинов связано с <tx:annotation-driven />. Практическое распространение аннотаций резко выросло после версии 2.5 и связано с появлением стереотипных аннотаций: @Component, @Service, @Repository, @Controller

  • Усиленный AOP: Встроенный AOP остался прокси-ориентированным. Для сложных сценариев (включая модификацию приватных полей, конструкторов) появилась опциональная, но глубокая интеграция с AspectJ (аспекты времени компиляции или загрузки - LTW).

  • Зрелый Spring MVC-стек: Хэндлеры, конвертеры, вью-резолверы, interceptors — фреймворк стал конкурентом Struts и JSF.

Экосистема

  • Spring Batch (инициирован и активно развивался в 2007; 1.0.0 стал доступен публично в 2008) — стандарт пакетной обработки (job, step, retry, транзакции).

  • Spring Security — Acegi был переименован в Spring Security в конце 2007 года,  официально войдя в состав экосистемы.

  • ORM-интеграции: Улучшенная поддержка Hibernate, JPA, JDBC.

  • Единая архитектура DAO: Унифицированные шаблоны для работы с БД (например, JdbcTemplate) и единая модель обработки исключений (DataAccessException) упростили доступ к данным — эти принципы позже повлияли на дизайн Spring Data.

Ограничения

  • Гибридная конфигурация: XML и аннотации сосуществовали, создавая неоднородность.

  • Только блокирующий веб: Spring MVC работал в модели «один поток на запрос», без асинхронности.

  • Ограниченный AOP: Для мощных аспектов требовался AspectJ с LTW или специальной компиляцией.

  • XML всё ещё был необходим: инфраструктурные компоненты продолжали требовать конфигурации в XML.

Ссылка на репозиторий с кодом: https://github.com/madela-team/Java/tree/master/spring-evolution/spring-2x

XML-конфигуратор для авторизации в Spring 2.x
XML-конфигуратор для авторизации в Spring 2.x

Spring Framework 3.x (2009–2013): JavaConfig и эра REST

Индустрия стремительно переходила к REST, JSON и лёгким HTTP-API. Одновременно XML-конфигурации постепенно переставали удовлетворять требованиям гибкости и поддерживаемости. Spring 3.x стал ответом на вызовы новой эпохи: современным веб-стандартам и желанию перенести конфигурацию в код.

Spring Framework 3.x — Контроллер
Spring Framework 3.x — Контроллер

Ключевые нововведения:

  • JavaConfig (Spring 3.0):

  • @Configuration
     public class AppConfig {
         @Bean
         public UserService userService() {
             return new UserService();
         }
     }

  • Конфигурация стала частью кода — с типобезопасностью, рефакторингом и IDE-поддержкой. С версией 3.1 JavaConfig стал полноценной альтернативой XML.

  • Spring Expression Language (SpEL) — выражения в аннотациях и конфигурации: #{...}, @Value, условия, динамическая маршрутизация.

  • Полноценная REST-поддержка:

  • @RequestBody, @ResponseBody (Полное идеологическое оформление REST-контроллеров с аннотацией @RestController появится уже в Spring 4.0)

  • MessageConverters для автоматической сериализации

  • RestTemplate — удобный HTTP-клиент.

  • Усиленная поддержка Bean Validation (JSR-303) в Spring MVC: упрощённое внедрение валидации в контроллеры;

  • Появление расширяемых HandlerMethodArgumentResolver (3.1), позволивших дополнять MVC собственной логикой обработки параметров

Экосистема

  • Spring Data (2010–2011): Революция в работе с данными — заложена универсальная репозиторная модель (CrudRepository, JpaRepository). Поддержка NoSQL появлялась постепенно: MongoDB, Redis, Neo4j и др.

  • Spring Security: развивалась method-level security (например, @PreAuthorize), а OAuth и интеграции с соцпровайдерами в ту эпоху чаще закрывались отдельными портфельными проектами — Spring Security OAuth и Spring Social (Facebook*, Twitter, LinkedIn, GitHub).

  • Spring Integration: Реализация Enterprise Integration Patterns.

  • Подготовка к Spring Boot: В версиях 3.0–3.2 появились @Configuration и @Bean (3.0), Environment (3.0), @Profile (3.1) и общая абстракция ApplicationContextInitializer (3.1). Эти механизмы позже стали основой для автоконфигурации Spring Boot.

Работа с базами данных через Hibernate в Spring 3.x
Работа с базами данных через Hibernate в Spring 3.x

Ограничения

  • MVC остаётся блокирующим: До Spring MVC 3.2 модель была строго «thread-per-request»; в 3.2 появилась Servlet 3 async-обработка, но это всё ещё не реактивный стек.

  • XML не исчез полностью: В реальных проектах обе модели конфигурации сосуществовали.

  • AOP по-прежнему сложен: Большинство использовало только прокси-подход. AspectJ по-прежнему сложен в использовании (LTW/CTW).

  • Нет поддержки реактивных паттернов — они появятся только в 5.x.

Итог:

Spring 3.x стал первой по-настоящему современной версией — с JavaConfig, REST-first подходом и унифицированной моделью доступа к данным.

Ссылка на репозиторий с кодом: https://github.com/madela-team/Java/tree/master/spring-evolution/spring-3x

Новая конфигурация приложения
Новая конфигурация приложения

Spring Framework 4.x (2013–2017): Java 8, микросервисы и путь к реактивности

Контекст

  • Java 8 принёс лямбды, Optional, Stream API и новое Date/Time API. Сохранение совместимости с Java 6 (минимальная версия для 4.x) было вынужденным компромиссом, который откладывал повсеместное использование возможностей Java 8 внутри самого фреймворка - многие разработчики критиковали это ограничение.

  • Микросервисы вытесняли монолиты.

  • Spring Boot 1.0 (2014) радикально упростил запуск приложений.

Spring 4.x стал платформой, поддерживающей эти тренды.

Spring 4.x — Контроллер
Spring 4.x — Контроллер

Ключевые нововведения:

  • Полная поддержка Java 8 (при сохранении совместимости с Java 6/7): Spring 4.0 - первая версия с полноценной поддержкой Java 8 (lambdas в callback API, java.time, repeatable annotations), при этом из-за baseline Java 6 публичные API фреймворка не могли массово перейти на Optional/Stream.

  • Spring Messaging: Унифицированная модель для WebSocket и STOMP.

  • WebSocket и real-time: Поддержка SockJS, STOMP over WebSocket — основа для чатов и уведомлений.

  • Улучшенный MVC: Асинхронные модели обработки запросов, основанные на Callable и DeferredResult (с версии Spring 3.2), получили в 4.x дальнейшее развитие и доработку (таймауты, обработка ошибок). Также была добавлена поддержка WebSocket и улучшена сериализация.

Экосистема

  • Spring Boot 1.x: Автоконфигурация, стартеры, fat-jar — сделал Spring доступным даже новичкам.

  • Spring Cloud (2015+): Config Server, Eureka, Ribbon, Feign, Hystrix, Zuul — классическая архитектура микросервисов на основе Netflix OSS, который со временем всё чаще заменяли альтернативами (Gateway, Resilience4j и др.).

  • Spring Data: Зрелая поддержка реляционных и NoSQL БД, Pageable, интеграция с  QueryDSL.

  • Spring Security 4.x (особенно 4.2+) : Конфигурация через JavaConfig стала стандартом (@EnableWebSecurity), добавлена поддержка современных алгоритмов хеширования, улучшена встроенная поддержка OAuth 2.0.

Появление Spring Boot 1.x
Появление Spring Boot 1.x

Ограничения

  • MVC остаётся блокирующим, реактивный стек отсутствует: Spring MVC 4.x - это по-прежнему Servlet-стек. Асинхронность делали через Callable и DeferredResult, но по факту это была лишь обёртка: нормального контроля нагрузки и настоящей неблокирующей обработки на уровне фреймворка не было.

  • Экосистема усложнилась: большое число автоконфигураций в Boot и зависимостей Spring Cloud, плотная привязка к Netflix OSS.

  • XML ещё поддерживался, но в новых проектах её практически полностью вытеснили JavaConfig и аннотации благодаря Spring Boot.

Итог:

Spring 4.x — это мост между эпохой монолитов и новой парадигмой микросервисов и реактивности.

Ссылка на репозиторий с кодом: https://github.com/madela-team/Java/tree/master/spring-evolution/spring-4x

Новая конфигурация приложения через YAML
Новая конфигурация приложения через YAML

Spring Framework 5.x (2017–2022): реактивность, WebFlux и новая архитектура

К 2017 году стало понятно: классическая модель “один запрос — один поток” начинает дорого обходиться там, где много ожидания ввода-вывода — например, тысячи одновременных HTTP-соединений, стриминг, работа с медленными внешними сервисами. Параллельно оформились Reactive Streams и экосистема вокруг реактивного подхода, а Spring решил дать этому отдельный, полноценный веб-стек.

На этом фоне родился Spring 5.0 — один из самых масштабных релизов за всю историю.

Spring 5.x — Реактивное программирование: контроллер
Spring 5.x — Реактивное программирование: контроллер

Ключевые нововведения:

  • Spring WebFlux — второй, независимый веб-стек рядом с Spring MVC. Он изначально рассчитан на неблокирующую обработку и умеет “притормаживать” поток данных, если потребитель не успевает (это и есть back pressure по Reactive Streams). Работает, в том числе, на Netty и на Servlet 3.1+ контейнерах.

  • Project Reactor - реактивное ядро Spring: основные типы - Mono (0..1 элемент) и Flux (0..N).

  • WebClient — асинхронный, реактивный HTTP-клиент. Стал предпочтительным для новых проектов, особенно реактивных. RestTemplate остался поддерживаемым, но не рекомендуется для новых разработок.

  • Поддержка Java 9+: Spring 5.x мог работать на новых версиях Java, используя новые возможности виртуальной машины (новые сборщики мусора, улучшенный NIO), однако не требовал и не использовал модульную систему Java (JPMS).

Экосистема

  • Spring Security 5: Новая OAuth2-модель, реактивная безопасность, Argon2.

  • Spring Data: Реактивные репозитории, R2DBC, реактивные драйверы для MongoDB, Redis, Cassandra.

  • Spring Cloud: реактивный Spring Cloud Gateway, интеграции WebClient, постепенный уход от Netflix OSS.

  • Spring Boot 2.x: Поддержка WebFlux, Micrometer, улучшенный Actuator.

Реактивное программирование в Spring 5.x: WebFlux
Реактивное программирование в Spring 5.x: WebFlux

Ограничения

  • Два веб-стека: MVC и WebFlux вызывали путаницу в выборе архитектуры. Иногда WebFlux брали “потому что это модно”, хотя система была обычной и синхронной

  • Сложность реактивного программирования: нужно понимать, где у тебя блокировки, как устроены цепочки, и почему “просто завернуть всё во Flux” не делает систему быстрее.

  • Незрелость реактивных драйверов: R2DBC и драйверы для БД развивались медленно и не всегда были стабильными.

  • Сложная миграция legacy: Spring 5 требовал минимум Java 8, но XML-конфигурация осталась полностью поддерживаемой.

Итог:

Spring 5.x — это большой поворот: фреймворк добавил полноценный реактивный стек и дал инструменты для систем с большим количеством одновременного I/O. А дальше уже логично вырос Spring 6 / Boot 3 с переходом на Jakarta EE

Ссылка на репозиторий с кодом: https://github.com/madela-team/Java/tree/master/spring-evolution/spring-5x

Реактивное программирование в Spring 5.x: Сервис
Реактивное программирование в Spring 5.x: Сервис

Spring Framework 6.x (2022–2024): переход на Jakarta, Java 17+ и AOT-революция

Spring Framework 6 стал ответом на изменения, которые накопились в Java-экосистеме за предыдущие годы. Это поколение зафиксировало новый технологический базис: Jakarta EE вместо Java EE, современную JVM и ориентацию на AOT и native-сценарии.

Предпосылки перехода

  1. Jakarta EE вместо javax.*
    После передачи Java EE в Eclipse Foundation и выхода Jakarta EE 9 произошло ключевое изменение — смена пространства имён с javax.* на jakarta.*. Это затронуло весь enterprise-стек: сервлеты, JPA, валидацию, JMS и связанные библиотеки. Spring 6 стал первой мажорной версией, которая полностью работает в мире Jakarta EE 9+ и не поддерживает старые javax.* API.

  2. Java 17 как минимальная версия.
    Spring Framework 6 требует Java 17. Это позволило:

  • использовать новые языковые возможности (records, sealed classes, pattern matching),

  • отказаться от устаревшей совместимости,

  • упростить кодовую базу

  • опираться на современные возможности языка и JVM без дополнительных ограничений.

3. Рост интереса к AOT и native-запуску В cloud-native и serverless-мире стали критически важны:

  • быстрый старт приложения;,

  • более предсказуемое потребление памяти;

  • снижение зависимости от reflection.

Это потребовало изменений на уровне фреймворка, а не только инструментов сборки.

4. Техническая чистка. За долгие годы в Spring накопилось значительное количество устаревших и давно помеченных как deprecated API. Версия 6.x стала точкой, в которой эти элементы были системно удалены.

Ключевые нововведения в ядре

1. Переход на jakarta.*
 Все основные API были переведены на Jakarta EE:

  • javax .servlet → jakarta.servlet

  • javax.persistence → jakarta.persistence

  • javax.validation → jakarta.validation

  • javax.jms → jakarta.jms (Jakarta Messaging)

Spring 6 стал первой мажорной версией, полностью совместимой с Jakarta EE 9+.

Замена javax. на jakarta.
Замена javax. на jakarta.

2. Требование Java 17 как минимальной версии. Это позволило:

  • использовать records, sealed classes, pattern matching;

  • убрать совместимость с устаревшими JVM;

  • оптимизировать внутренние алгоритмы под современные GC и JIT.

3. AOT и подготовка к native-режиму

Spring Framework 6 содержит инфраструктуру для AOT-подхода, которая активно используется в Spring Boot 3.

На этапе сборки:

  • анализируется конфигурация и граф бинов;

  • заранее генерируются необходимые прокси и метаданные;

  • уменьшается объём reflection в рантайме.

Это сделало возможным запуск Spring-приложений в виде нативных бинарников — с очень быстрым холодным стартом.

4. Упрощение и очистка API Spring 6 удалил множество устаревших классов и методов из эпох 2.x–5.x, упростив внутренние абстракции.

5. Обновления веб-стеков

  • WebFlux: оптимизации производительности в связке с Reactor и Netty;

  • MVC: полная адаптация к Jakarta Servlet API и усиленная безопасность сериализации.

Экосистема вокруг версии

1. Spring Boot 3.x

Spring Boot 3 стал основной точкой входа в экосистему Spring 6. Он:

  • работает на Jakarta EE и Java 17;

  • поддерживает AOT и native-сборки;

  • развивает observability-подход (метрики, трассировка, логирование).

2. Spring Security 6.x

Spring Security полностью перешёл на jakarta.*. Параллельно был выпущен Spring Authorization Server 1.0, который заменил устаревшие решения для OAuth2 Authorization Server и упростил конфигурацию безопасности.

3. Spring Data (релизы 2023.x)

Spring Data получил:

  • полную Jakarta-совместимость;

  • обновлённые реактивные и NoSQL-драйверы;

  • улучшения в API аудита и стриминга данных.

4. Spring Modulith 1.0 Spring Modulith предложил инструменты для построения модульных монолитов:

  • явные архитектурные границы;

  • доменные события,

  • контроль зависимостей между модулями;

  • генерацию документации.

Проект стал альтернативой преждевременной декомпозиции на микросервисы.

5. Spring Cloud 2023.x

  • Spring Cloud адаптирован под Spring Boot 3 и Jakarta EE.

  • Роль Netflix OSS значительно снизилась, акцент сместился на собственные компоненты экосистемы (Gateway, конфигурация, интеграции).

Проблемы и ограничения версии

  • Миграция на Jakarta оказалась болезненной: Требовала массового обновления зависимостей (Hibernate, Vaadin, JMS-провайдеров) и ручной переработки импортов.

  • AOT всё ещё требует ручной настройки: Многие сторонние библиотеки нуждаются в явных hint’ах для native-сборки.

Итог по поколению 6.x

Spring Framework 6 зафиксировал переход экосистемы на современный базис:

  • Jakarta EE вместо javax.*;

  • Java 17 как минимальный стандарт;

  • готовность к AOT и native-запуску;

  • обновлённую и очищенную архитектуру.

Это поколение стало фундаментом для Spring Boot 3 и дальнейшего развития платформы в сторону cloud-native и serverless-сценариев.

Ссылка на репозиторий с кодом: https://github.com/madela-team/Java/tree/master/spring-evolution/spring-6x

Spring Framework 7.x (2025): виртуальные потоки, Jakarta EE 11 и Spring нового поколения

Небольшая оговорка про Spring 7.x. На момент написания статьи Spring Framework 7.0 (GA) и Spring Boot 4.0 сравнительно недавно вышли. Ниже мы фиксируем архитектурные тенденции и заявленные фичи, а не итоги десятилетия эксплуатации. Реальная ценность и ограничения этого поколения станут полностью понятны только после N-ого количества времени продакшен-опыта.

Spring 7.x отражает очередной сдвиг в Java-экосистеме. Если Spring 6 зафиксировал новый базис (Jakarta EE и Java 17), то Spring 7 делает акцент на модель исполнения: как именно выполняется код, управляются потоки и ресурсы.

Spring Framework 7.x — Поддержка Java 21. Пример: поддержка виртуальных потоков
Spring Framework 7.x — Поддержка Java 21. Пример: поддержка виртуальных потоков

Ключевые технологические предпосылки:

  1. Виртуальные потоки (Project Loom, JDK 21+)
     Virtual Threads позволяют писать привычный блокирующий код без жёсткой привязки к количеству системных потоков. Это снижает стоимость блокировок и упроща��т масштабирование приложений с большим числом параллельных операций.

  2. Созревание AOT и native-подходов AOT и native-сборки перестали быть экспериментом. От фреймворка ожидается предсказуемое поведение, минимальная динамика и сокращённое использование reflection.

  3. Jakarta EE 11
     Новые версии спецификаций (Servlet 6.1, JPA 3.2, Validation 3.x) требуют синхронизации фреймворков с актуальными стандартами enterprise-Java.

  4. Поддержка современных JDK (21–25)
     Spring 7 ориентирован на новые версии JVM, при этом сохраняет совместимость с Java 17 как минимальной поддерживаемой версией.

Ключевые нововведения в Spring Framework 7

1. Virtual Threads в Spring MVC

Spring MVC адаптирован для работы в среде виртуальных потоков:

  • корректно работают контроллеры, Security Context и MDC;

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

При использовании серверов с поддержкой Virtual Threads (Tomcat 10.1+, Jetty 12+) это позволяет строить масштабируемые системы без перехода на реактивную модель.

2. Более зрелая AOT-инфраструктура

AOT-подход стал стабильнее:

  • большинство типовых сценариев работают без ручных подсказок;

  • уменьшена доля reflection;

  • улучшена совместимость с native-сборками.

Нативные образы дают быстрый старт и более компактное потребление памяти, но по-прежнему требуют осознанной архитектуры.

3. Поддержка Jakarta EE 11

Полная синхронизация с новейшими спецификациями, включая:

  • Servlet 6.1,

  • JPA 3.2,

  • Bean Validation 3.x.

Это обеспечивает совместимость с современными контейнерами и инфраструктурой.

4. Null-safety на уровне API (JSpecify)

Внедрение аннотаций JSpecify позволяет:

  • явно описывать nullable-контракты;

  • улучшать статический анализ;

  • повышать качество API и документации;

  • упрощать интеграцию с Kotlin.

5. Встроенная поддержка устойчивости

Spring 7 расширяет базовую поддержку resilience-паттернов:

  • @Retryable — повторные попытки с настраиваемой задержкой и экспоненциальной компенсацией;

  • @ConcurrencyLimit — ограничение параллелизма на уровне метода;

  • интеграция с инфраструктурой потоков и контекстов

Активируются через @EnableResilientMethods — без подключения Resilience4j или Spring Retry.

6. Декларативные HTTP-клиенты

HTTP interface clients стали полноценным инструментом::

  • интерфейсы с аннотациями @GetExchange, @PostExchange;

  • генерация клиентов без ручной реализации;

  • единая настройка таймаутов, версий и политики повторов.

Это снижает потребность в сторонних HTTP-клиентах для типовых интеграций, не исключая их использования.

Примечание: в ранних milestone-версиях использовалась аннотация @HttpServiceClient, но до GA она была удалена: в ходе обратной связи от сообщества и внутренних обсуждений в команде Spring было решено отказаться от этого API в пользу более простого и гибкого подхода на базе уже существующего HttpServiceProxyFactory (из пакета org.springframework.web.service.invoker)

7. Нативное версионирование REST API

Поддержка версий встроена прямо в маппинги контроллеров: @RequestMapping / @GetMapping(value = "/users", version = "2").

Поддерживаются стратегии:

  • через путь (/api/v2/...),

  • заголовки (X-API-Version),

  • параметры запроса (?version=2),

  • media type (Accept: application/json; version=2).

Стратегии настраиваются через ApiVersionStrategy / ApiVersionInserter и работают как в MVC, так и в WebFlux.

Версионирование API в Spring 7.x
Версионирование API в Spring 7.x

8. Улучшенная асинхронность: несколько TaskDecorator

Теперь можно использовать несколько TaskDecorator, которые автоматически объединяются в цепочку. Это упрощает распространение контекста безопасности, логирования и метрик.

9. Упрощённое тестирование MVC: RestTestClient

Аналог WebTestClient, но без реактивных зависимостей.

Идеален для интеграционных тестов блокирующих приложений на Spring MVC + Virtual Threads.

10. WebFlux

  • получил обновления зависимостей (Reactor, Netty) и улучшения в стабильности и совместимости с Jakarta EE 11.

Экосистема вокруг версии

1. Spring Boot 4.x

  • Глубокая интеграция с Virtual Threads: достаточно включить spring.threads.virtual.enabled=true — HTTP-стек и многие автосконфигурированные клиенты начинают работать на виртуальных потоках;

  • Jackson 3, Micrometer 2, новые starters и модульная автоконфигурация (вместо одного огромного spring-boot-autoconfigure.jar);

  • Нативные образы как основной deployment-сценарий.

  • Улучшенный AOT / native-путь: обновлённые плагины, поддержка нового формата reachability metadata GraalVM, тесная интеграция с buildpacks.

2. Spring Security 7.x

  • Фильтры и цепочки адаптированы под виртуальные потоки;

  • Обновлённая поддержка OAuth 2.0 и упрощённая модель Authorization Server;

  • Повышены криптографические стандарты (включая Argon2).

3. Spring Data

  • Оптимизация репозиториев под Virtual Threads;

  • улучшенная поддержка AOT и совместимость с реактивными и блокирующими стеками, включая R2DBC, MongoDB и Redis.

4. Spring Modulith 1.2+

  • Интеграция с Observability (Micrometer 2) и Loom

5. Spring Cloud для JDK 21/25

  • ориентация на JDK 21+, отказ от legacy-компонентов Netflix OSS, интеграция с новыми HTTP-клиентами.

Проблемы и ограничения версии

  • Virtual Threads не решают все проблемы: Некоторые драйверы (особенно JDBC) и библиотеки всё ещё плохо совместимы с Loom.

  • Миграция с Spring 5/6 сложна:
    Требуется переход на Jakarta EE, Spring Boot 4, обновление Security, Data и AOT-конфигураций.

  • Экосистема третьих сторон отстаёт, Native-режим остаётся чувствительным к сторонним библиотекам с активным reflection.

Итог по поколению 7.x

Spring Framework 7.x фокусируется не столько на новых API, сколько на новой модели исполнения:

  • виртуальные потоки как основной механизм масштабирования;

  • зрелый AOT и native-подход;

  • синхронизация с Jakarta EE 11 и современными JDK;

  • постепенное упрощение архитектуры.

Ссылка на репозиторий с кодом: https://github.com/madela-team/Java/tree/master/spring-evolution/spring-7x


Как изменялась архитектура Java-приложений вместе со Spring

1. Эволюция архитектурных парадигм — от монолита к осознанной модульности
 Spring не просто следовал за трендами — он часто формировал их, предоставляя инструменты раньше, чем появлялись теоретические модели:

  • Классический монолит (2003–2010)
     Spring 1.x–3.x дал разработчикам возможность писать чистые, тестируемые монолиты без EJB-зависимостей. DI и AOP позволили изолировать бизнес-логику от инфраструктуры, что стало первым шагом к гибкой архитектуре.

  • Модульный монолит (2011–2023)
     По мере роста систем стало ясно: не все приложения выигрывают от микросервисов. Spring 4.x–5.x с поддержкой компонентного сканирования, доменных пакетов и слабосвязанных слоёв позволил выделять логические границы внутри монолита.
     Spring Modulith (2023) официально закрепил эту практику, добавив инструменты для валидации архитектурных ограничений, генерации документации и обмена доменными событиями без физического разнесения сервисов.

  • Микросервисы (2014–2020)
     С выходом Spring Boot 1.0 и Spring Cloud Spring стал стандартным выбором для микросервисной архитектуры.
     Boot устранил зависимость от серверов приложений, а Cloud предложил готовые решения для конфигурации, сервис-дискавери и отказоустойчивости.

  • Cloud Native (2018–н.в.)
     Spring Boot 2.x+ интегрировал health checks, metrics, distributed tracing (через Micrometer и OpenTelemetry), внешнюю конфигурацию и graceful shutdown — это перестало быть “надстройкой” и стало стандартным поведением приложения.

  • Осознанная модульность (2023–н.в.)
     Опыт показал: микросервисы вводят операционную сложность, которую не все команды могут осилить. В ответ Spring предложил модульный монолит как стратегию: гибкость микросервисов без их накладных расходов. Modulith позволяет откладывать декомпозицию до тех пор, пока она действительно нужна.

2. Как технологии Spring формировали современный ландшафт

  • DI/IoC → Превратил Java из «инфраструктурно-зависимого» языка в платформу для компонуемого, тестируемого кода.

  • AOP → Позволил вынести транзакции, безопасность, аудит и логирование в инфраструктурный слой, создавая чистую бизнес-логику без шаблонного кода.

  • REST в Spring MVC (3.x) → Ускорил переход от SOAP и тяжёлых ESB к лёгким, человеко-читаемым HTTP-API. @RestController и MessageConverters сделали Spring стандартом для REST. 

  • Messaging и события (4.x+) → Spring Integration, Spring AMQP, Spring Cloud Stream и позже Modulith заложили основу для event-driven архитектуры, даже внутри монолита.

  • Observability (Boot 2.5+) → Метрики, трейсы и логи стали частью фреймворка, а не задачей для DevOps. Это ускорило «shift-left» мониторинга.

3. Влияние Spring Boot на shift-left и DevOps-культуру

 Spring Boot изменил распределение ответственности:

  • Shift-left: Разработчик теперь получает production-ready приложение «из коробки» — с логированием, метриками, health checks, конфигурацией через environment. Это сокращает зависимость от инфраструктурных команд.

  • DevOps-дружелюбность: Fat-jar (Spring Boot Loader), self-contained приложения, внешняя конфигурация и Actuator endpoints упростили:

  • упаковку в Docker,

  • развёртывание в Kubernetes,

  • интеграцию в CI/CD-пайплайны. Spring Boot сделал облачные практики (health checks, конфигурацию, метрики, наблюдаемость) стандартом разработки Java-приложений.


Что используют сегодня и как выбирать стек (2025)

1. MVC vs WebFlux vs Virtual Threads — что реально актуально?

  • MVC + Virtual Threads становится предпочтительной архитектурой для новых императивных приложений, если вы готовы использовать Loom-совместимый сервер и настроить виртуальные потоки. Это даёт масштабируемость, близкую к реактивным системам, при сохранении привычного блокирующего стиля кода

  • WebFlux — остаётся выбором для специфических сценариев:

  • high-throughput IO-bound систем (тысячи параллельных соединений),

  • стриминг-данных (SSE, WebSocket),

  • систем с жёсткими требованиями к latency под нагрузкой.

  • Классический блокирующий MVC без Virtual Threads остаётся поддерживаемым, но для новых проектов его стоит избегать: Loom даёт ощутимый прирост масштабируемости без переписывания бизнес-логики.

2. Jakarta и Java 21/25: новая норма

  • Jakarta EE 10/11 — Spring 6.x перешёл на Jakarta EE 9/10, а Spring 7.x — на Jakarta EE 11. Переход на jakarta.* стал обязательным, и javax.* больше не поддерживается.

  • Java 21 (LTS) — минимальная версия для всех новых проектов. Spring 7.x активно использует records, sealed classes, virtual threads.

  • Java 25 — станет целевой платформой для дальнейших улучшений, включая structured concurrency.

3. Когда обновлять legacy, а когда оставить?

Обновлять стоит, если:

  • приложение на Spring ≤ 5.3 (без Jakarta);

  • есть потребность в native-образах (GraalVM) или быстром старте (serverless);

  • используется уязвимая версия Spring Security, Hibernate или Jackson.

Оставить старую версию, если:

  • обновление невозможно из-за ограничений платформы. В таких случаях разумно удерживать текущую стабильную версию и планировать миграцию по мере появления Jakarta-совместимых библиотек.;

  • миграция экономически нецелесообразна (внутренний инструмент с низкой критичностью);

  • есть жёсткая зависимость от legacy-библиотек без Jakarta-версий (например, старые JMS-провайдеры).

4. Must-have модули Spring в 2025 году

  • Spring Boot 4 — основа всего стека: AOT, native, observability, Virtual Threads.

  • Spring Modulith — для архитектурной дисциплины в монолитах (если не микросервисы).

  • Spring Security 7 — современная, Loom-совместимая, с OAuth 2.2 и улучшенной криптографией.

  • Spring Data — с поддержкой Virtual Threads, реактивных драйверов и улучшенных спецификаций.

  • Micrometer + Observability — обязательны для cloud-native и production-мониторинга.

  • Spring AOT — критичен для native и serverless-сценариев.


Куда движется Spring дальше

Эти направления не являются зафиксированной roadmap’ой, однако на основе релизов Spring 7.x, Boot 4.x и активности команды Spring можно выделить несколько стратегических векторов развития платформы.

  1. Virtual Threads + structured concurrency
    Следующие поколения Spring будут глубже интегрироваться с Project Loom и structured concurrency, делая параллелизм не только эффективным, но и безопасным: предотвращен��е утечек, упрощённая отладка, корректная обработка исключений в асинхронных цепочках.

  2. AOT и нативная компиляция — новая норма
    Минимизация reflection и runtime-магии.

  3. Минимизация инфраструктурного overhead
    Больше статического анализа, меньше неявных зависимостей.

  4. Observability как first-class citizen
    Диагностика на уровне фреймворка, а не sidecar-инфраструктуры.

  5. Интеграция с AI/ML-инструментами (осторожный тренд)
    Spring AI предлагает стандартные паттерны, не превращая Spring в ML-платформу.


Заключение

Spring отражает эволюцию всей Java-платформы: от борьбы с EJB 2.x до виртуальных потоков и native-образов.

Понимание этой истории помогает:

  • принимать осознанные архитектурные решения,

  • не смешивать несовместимые модели,

  • эффективнее диагностировать проблемы в production.

Spring остаётся не просто фреймворком, а экосистемой, формирующей будущее Java-разработки.

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