Warning: mkdir(): No space left on device in /var/www/tgoop/post.php on line 37

Warning: file_put_contents(aCache/aDaily/post/java_fillthegaps/--): Failed to open stream: No such file or directory in /var/www/tgoop/post.php on line 50
Java: fill the gaps@java_fillthegaps P.535
JAVA_FILLTHEGAPS Telegram 535
Scoped Value (preview)

Неделю назад вышла java 21. Cегодня разберу интересную фичу в стадии превью — Scoped Value.

Ближайший аналог Scoped Value — ThreadLocal. Это когда мы объявляем переменную

ThreadLocal<Integer> value;

и для каждого потока будет своё независимое значение value.

В бизнес-логике это редко нужно, но фреймворки активно пользуются этим классом. Spring Security использует ThreadLocal для хранения информации о текущем пользователе. Давайте на этом кейсе посмотрим недостатки ThreadLocal, и что предлагает ScopedValue.

Как работает секьюрити:

1️⃣ Когда приходит новый запрос, Spring вытаскивает информацию о пользователе и записывает в ThreadLocal переменную:

public static ThreadLocal<Principal> PRINCIPAL = …

void serve(Request request, Response response) {

var principal = ADMIN;
PRINCIPAL.set(principal);
…}

2️⃣ Бизнес-логика. В любом месте кода можно узнать, кто выполняет запрос:

var principal = PRINCIPAL.get();

Обычно каждый запрос обрабатывается в своём потоке, поэтому данные между запросами не пересекаются.

3️⃣ В конце работы с запросом удаляем информацию из ThreadLocal переменной

Что в итоге:

Не надо передавать Principal в параметрах
Надо явно очищать значение ThreadLocal переменной в конце работы
В любом месте можно вызвать set/remove и всё сломать
Подход несовместим с виртуальными потоками

Scoped Value намерен решить проблемы выше. Как это выглядит:

public static ScopedValue<Principal> PRINCIPAL = …

void serve(Request request, Response response) {

var principal = ADMIN;
ScopedValue.where(PRINCIPAL, principal)
.run(() -> process(request, response));
…}

Переменная PRINCIPAL со значением principal будет доступна только внутри конкретного вызова метода process. Достать значение внутри process:

var principal = PRINCIPAL.get();

Кроме run есть метод call, который возвращает значение из переданной функции:

var result = ScopedValue.where(Server.PRINCIPAL, guest)
.call(() -> getResult());

Сначала кажется, что для java синтаксис Scoped Value очень необычный — как будто переменная главнее основного действия. Но такое в java уже есть, вспомните try-with-resources.

Что получаем:

Видимость переменной задаётся для конкретного вызова метода
У ScopedValue нет метода set, переменную нельзя обнулить/поменять внутри блока
Код совместим с виртуальными потоками

Что вызывает вопросы:

🤔 Сценарии использования

Неизменяемый аналог ThreadLocal, совместимый с Project Loom точно нужен, но не вижу смысла задавать область видимости настолько гранулярно

🤔 Нельзя использовать несколько ScopedValue без использования вложенности. Хотя это легко реализовать по аналогии с try-with-resources

Где использовать: пока вижу только как замену ThreadLocal при переходе на виртуальные потоки.

Фича сейчас в стадии превью, посмотрим, как она будет развиваться. Если будет, конечно:)
👍70🔥1410



tgoop.com/java_fillthegaps/535
Create:
Last Update:

Scoped Value (preview)

Неделю назад вышла java 21. Cегодня разберу интересную фичу в стадии превью — Scoped Value.

Ближайший аналог Scoped Value — ThreadLocal. Это когда мы объявляем переменную

ThreadLocal<Integer> value;

и для каждого потока будет своё независимое значение value.

В бизнес-логике это редко нужно, но фреймворки активно пользуются этим классом. Spring Security использует ThreadLocal для хранения информации о текущем пользователе. Давайте на этом кейсе посмотрим недостатки ThreadLocal, и что предлагает ScopedValue.

Как работает секьюрити:

1️⃣ Когда приходит новый запрос, Spring вытаскивает информацию о пользователе и записывает в ThreadLocal переменную:

public static ThreadLocal<Principal> PRINCIPAL = …

void serve(Request request, Response response) {

var principal = ADMIN;
PRINCIPAL.set(principal);
…}

2️⃣ Бизнес-логика. В любом месте кода можно узнать, кто выполняет запрос:

var principal = PRINCIPAL.get();

Обычно каждый запрос обрабатывается в своём потоке, поэтому данные между запросами не пересекаются.

3️⃣ В конце работы с запросом удаляем информацию из ThreadLocal переменной

Что в итоге:

Не надо передавать Principal в параметрах
Надо явно очищать значение ThreadLocal переменной в конце работы
В любом месте можно вызвать set/remove и всё сломать
Подход несовместим с виртуальными потоками

Scoped Value намерен решить проблемы выше. Как это выглядит:

public static ScopedValue<Principal> PRINCIPAL = …

void serve(Request request, Response response) {

var principal = ADMIN;
ScopedValue.where(PRINCIPAL, principal)
.run(() -> process(request, response));
…}

Переменная PRINCIPAL со значением principal будет доступна только внутри конкретного вызова метода process. Достать значение внутри process:

var principal = PRINCIPAL.get();

Кроме run есть метод call, который возвращает значение из переданной функции:

var result = ScopedValue.where(Server.PRINCIPAL, guest)
.call(() -> getResult());

Сначала кажется, что для java синтаксис Scoped Value очень необычный — как будто переменная главнее основного действия. Но такое в java уже есть, вспомните try-with-resources.

Что получаем:

Видимость переменной задаётся для конкретного вызова метода
У ScopedValue нет метода set, переменную нельзя обнулить/поменять внутри блока
Код совместим с виртуальными потоками

Что вызывает вопросы:

🤔 Сценарии использования

Неизменяемый аналог ThreadLocal, совместимый с Project Loom точно нужен, но не вижу смысла задавать область видимости настолько гранулярно

🤔 Нельзя использовать несколько ScopedValue без использования вложенности. Хотя это легко реализовать по аналогии с try-with-resources

Где использовать: пока вижу только как замену ThreadLocal при переходе на виртуальные потоки.

Фича сейчас в стадии превью, посмотрим, как она будет развиваться. Если будет, конечно:)

BY Java: fill the gaps


Share with your friend now:
tgoop.com/java_fillthegaps/535

View MORE
Open in Telegram


Telegram News

Date: |

While the character limit is 255, try to fit into 200 characters. This way, users will be able to take in your text fast and efficiently. Reveal the essence of your channel and provide contact information. For example, you can add a bot name, link to your pricing plans, etc. Concise bank east asia october 20 kowloon There have been several contributions to the group with members posting voice notes of screaming, yelling, groaning, and wailing in different rhythms and pitches. Calling out the “degenerate” community or the crypto obsessives that engage in high-risk trading, Co-founder of NFT renting protocol Rentable World emiliano.eth shared this group on his Twitter. He wrote: “hey degen, are you stressed? Just let it out all out. Voice only tg channel for screaming”. Find your optimal posting schedule and stick to it. The peak posting times include 8 am, 6 pm, and 8 pm on social media. Try to publish serious stuff in the morning and leave less demanding content later in the day.
from us


Telegram Java: fill the gaps
FROM American