ScopedValue.runWhere not returning scope

Marcin Grzejszczak marcin.grzejszczak at gmail.com
Wed Jun 12 09:02:31 UTC 2024


> This API fails the test I provided:

>    final ScopedValue aScopedValue = ...;
>    final var x = aScopedValue.get();
>    ScopedValue.openScope(aScopedValue, someValue);
>    final var y = aScopedValue.get();

>    assert(x == y); // Always succeeds

> In other words, scoped values would no longer be strictly scoped.
> That's what the "scoped" means in the name "scoped values". Strict
> scoping is a fundamental property.

I mean you have not closed the scopes so no wonder it works as you
presented. I'm literally suggesting an option to allow manual control of
scopes. Of course people can mess up the opening and closing of scopes, I
do understand that.

Anyways, the equivalent of...

ScopedValue.runWhere(scopedValue, 1 () -> {
        codeToRun(); // scoped value equal to  1
        ScopedValue.runWhere(scopedValue, 2, () -> {
          codeToRun(); // scoped value equal to  1
        });
        // scoped value equal to 1
      });
// scoped value not having a value

... would be:

 try(Scope scope1 = ScopedValue.openScope(scopedValue, 1)) {
    codeToRun(); // scoped value equal to 1
    try(Scope scope2 = ScopedValue.openScope(scopedValue, 2)) {
      codeToRun(); // scoped value equal to 2
    }
   // scoped value equal to 1
}
// scoped value not having a value

I'm happy that we agree that there has to be an interop between TL and SV,
so here I have no other comments.

Pozdrawiam / Best regards,
Marcin Grzejszczak

https://marcin.grzejszczak.pl
https://toomuchcoding.com


wt., 11 cze 2024 o 12:35 Andrew Haley <aph-open at littlepinkcloud.com>
napisał(a):

> On 6/11/24 11:32, Marcin Grzejszczak wrote:
>
>  >> So why not produce an example of how it would be used? As far as I can
>  >> see, your proposal fails to ensure the property in the case I posted/
>  >
>  > I've created samples at the very beginning with the before and after
>  > interceptor. I obviously know that I could rewrite the interceptor
>  > to become an around one but my point is that it's not an ideal
>  > solution to require instrumentors to rewrite everything. Also I
>  > still see this whole discussion as having two ways of doing the same
>  > thing. Current approach:
>  >
>  > ScopedValue.runWhere(scopedValue, someValue, () -> {
>  >        codeToRun();
>  >      });
>  >
>  > Proposed approach:
>  >
>  > try(Scope scope = ScopedValue.openScope(scopedValue, someValue)) {
>  >    codeToRun();
>
> This API fails the test I provided:
>
>     final ScopedValue aScopedValue = ...;
>     final var x = aScopedValue.get();
>     ScopedValue.openScope(aScopedValue, someValue);
>     final var y = aScopedValue.get();
>
>     assert(x == y); // Always succeeds
>
> In other words, scoped values would no longer be strictly scoped.
> That's what the "scoped" means in the name "scoped values". Strict
> scoping is a fundamental property.
>
>  > }
>  >
>  > I understand that in the proposed approach one can mess things up, I
>  > really do. But library instrumentors and tracing library creators
>  > would benefit from that sort of API.
>
> If we were planning to deprecate thread-local variables I think this
> argument might have some merit. But we're not. They're not going away.
>
>  > Also I've asked a different question... What if the users want to
>  > leverage the ScopedValues to get the current span information (or
>  > current principal from security point of view) but also they are
>  > using TL based libraries? How would the interop look like?
>
> As the JEP says, scoped values do not replace all uses of thread-local
> variables. There are still some cases where thread-local variables
> will be used, and this looks like one of them.
>
>  > Let's assume that they put into the current scope a span that they
>  > want to have within that scope, we would need all the tracer
>  > libraries (and security components and others that use the same
>  > mechanism) to be ScopeValue aware. Would they first try to read SV
>  > and then if that's not there a TL?
>
> Yes, I think so.
>
>  > They would need to most likely read SV and populate TL if the SV
>  > value is present so that other components that still rely on TL
>  > would work. That would have to also work the other way round, if a
>  > TL based library sets a value (e.g. span) then maybe the ScopedValue
>  > should be created with a scope for that new value?
>
> I'm not sure how that'd work in general, but there's nothing to stop
> entry points for a library from doing so, and it might be a good idea.
> Something like:
>
>      if (someThreadLocal.get() != NOTHING) {
>          where(someScopedValue, someThreadLocal.get()).run(realEntry);
>      } else {
>          realEntry.run();
>      }
>
> --
> Andrew Haley  (he/him)
> Java Platform Lead Engineer
> Red Hat UK Ltd. <https://www.redhat.com>
> https://keybase.io/andrewhaley
> EAC8 43EB D3EF DB98 CC77 2FAD A5CD 6035 332F A671
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.org/pipermail/loom-dev/attachments/20240612/e24ec2e8/attachment-0001.htm>


More information about the loom-dev mailing list