-
Notifications
You must be signed in to change notification settings - Fork 35
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: Add hook-data concept for hooks. #273
base: main
Are you sure you want to change the base?
Conversation
@@ -31,7 +31,9 @@ Hooks can be configured to run globally (impacting all flag evaluations), per cl | |||
|
|||
### Definitions | |||
|
|||
**Hook**: Application author/integrator-supplied logic that is called by the OpenFeature framework at a specific stage. **Stage**: An explicit portion of the flag evaluation lifecycle. e.g. `before` being "before the [resolution](../glossary.md#resolving-flag-values) is run. **Invocation**: A single call to evaluate a flag. `client.getBooleanValue(..)` is an invocation. **API**: The global API singleton. | |||
**Hook**: Application author/integrator-supplied logic that is called by the OpenFeature framework at a specific stage. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
These were all on one line, which seemed hard to read. So I put a blank line between them to get them on multiple lines.
@@ -81,75 +83,154 @@ see: [dynamic-context paradigm](../glossary.md#dynamic-context-paradigm) | |||
|
|||
> Condition: The provider `metadata` field in the `hook context` **MUST** be immutable. | |||
|
|||
### 4.3. Hook creation and parameters | |||
### 4.3. Hook data |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I prefer not renumbering, but I did in this case as conceptually it makes sense to group all the parameter requirements together. I could move this to retain the existing numbering.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think I prefer moving it to avoid the number thrashing. It's slightly inconvenient that things aren't grouped, but I think it's more important to attempt to maintain stability of the requirement numbers.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I will update it.
|
||
> `Hook data` **MUST** must be created before the first `stage` invoked in a hook for a specific evaluation and propagated between each `stage` of the hook. | ||
|
||
Example showing data between `before` and `after` stage for two different hooks. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am not sure if the diagram is overkill, but a key concept is that data is not shared between hooks and not shared between evaluations.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is diagram-worthy.
Signed-off-by: Ryan Lamb <4955475+kinyoklion@users.noreply.github.com>
c42ef76
to
d391718
Compare
Signed-off-by: Ryan Lamb <4955475+kinyoklion@users.noreply.github.com>
cb5cabb
to
2110b92
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I like this proposal, but I would like to see how it could be implemented in an SDK. Properly scoping hook data may be complicated.
Co-authored-by: Michael Beemer <beeme1mr@users.noreply.github.com> Signed-off-by: Ryan Lamb <4955475+kinyoklion@users.noreply.github.com>
|
||
> The `before` stage **MUST** run before flag resolution occurs. It accepts a `hook context` (required) and `hook hints` (optional) as parameters and returns either an `evaluation context` or nothing. | ||
> The `before` stage **MUST** run before flag resolution occurs. It accepts a `hook context` (required), `hook hints` (optional), and `hook data` (required) as parameters and returns either an `evaluation context` or nothing. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should hook data be optional? I think most implementations could tolerate overloads for the stage functions:
before(HookContext context, HookHints hints);
before(HookContext context, HookData data, HookHints hints);
This would mean that current hooks wouldn't break, I think.
The other option might be to add the hook data
to the hook context
object.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I can think about the hook context. For the LD hooks the context was fully immutable, but for OpenFeature it isn't exactly the case being as the evaluation context within the hook context can change. So that makes it a potential home. It does make the mutability story a bit more complex.
#### Condition 4.3.2 | ||
#### Requirement 4.4.2 | ||
|
||
> `Hook data` **MUST** must be created before the first `stage` invoked in a hook for a specific evaluation and propagated between each `stage` of the hook. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it's implied here, but not explicit, that hook data is scoped only to the hook instance in question. I think it might be worth adding a specific point about that, and perhaps even a recommendation or example of how it might be accomplished in some implementations.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I definitely support this idea. I left a few comments. My biggest question is how we can define this so it's non-breaking for existing hooks.
This PR
Add support for the hook-data concept for hooks. Hook-data allows for per-evaluation data to be propagated between hooks.
This is especially useful for analytics purposes where you may want to measure things that happen between stages, or you want to do something like create a span in one stage and close it in another.
This concept is similar to the
series data
concept for LaunchDarkly hooks. https://github.com/launchdarkly/open-sdk-specs/tree/main/specs/HOOK-hooks#evaluationseriesdataUnlike
series data
the data in this approach is mutable. This is because thebefore
stage already has a return value. We could workaround this by specifying a return structure, but it maybe seems more complex. The data is only passed to a specific hook instance, so mutability is not of great concern.Some functional languages may still need to use an immutable with return values approach.
I can create an OFEP if we think this merits discussion prior to proposal.
Related Issues
Related discussion in a PR comment.
open-feature/java-sdk#1049 (comment)