-
-
Notifications
You must be signed in to change notification settings - Fork 720
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
Added feature variations #297
Conversation
Hi Juan! Thanks for using Unleash and for contributing to the project. We are currently exploring how to add A/B and multi-variant testing support to Unleash, and your suggestions are much welcome. So far we have an experimental implementation developed in-house on top of the current Unleash client libraries, both for Java and Node. When in use, it looks something like this: Variation variation = unleash.startExperiment("someNewFeature"); // Activate toggle and initiate tracking
if (variation.isEnabled("someVariant")) {
// Serve some variant
} else if (variation.isEnabled("anotherVariant")) {
// Serve another variant
} else {
// Serve control/disabled
} The idea is to provide a separate The biggest challenge is how to manage the tracking side-effect and reporting of experimentation metrics. Different companies use different tracking and reporting solutions, and we think it is important that people can plug in the solution of their choice. Experiments may eventually become a whole new section in the Unleash UI, fully supported throughout the whole stack. How is still in the open, and maybe @ivarconr can share some of his thoughts on that. |
I love that you ignite this discussion via a pull request! From your suggestion it is a bit unclear to me how variants and strategies are connected? And how did you imagine to use the variants in the client SDKs? It also feels a bit intrusive to always require a toggle to have at least to variants. As @vsandvold points out, we have been using Unleash to control our MultiVariate Experiments internally for som time now on Java and more recently on node projects. We have been using a custom strategy, and wrapped client SDKs to enable experiments. What we have learned so far is that experiments are not quite the same as feature toggles and they probably are used in a different phase, than a controlled feature rollout. The biggest difference is the requirements around how you allocate (and potentially segement) users and how you expose this data to the analytics tool used. There are also statistical requirements to the amount of users in each variant. It does make sense to be able to control experiments with Unleash and I believe as @vsandvold points out, that experiments is a different section. Possibly you would also define some configurable options used to define new variants on the fly, without having to change the implementation in the client applications. I also imagine that the strategies concept can work for experiments also, but you would probably have experiments specific strategies. |
Thanks for the input @vsandvold & @ivarconr.
I think your vision here is great. Let me explain what I'm trying to achieve on that side that could also answer @ivarconr's questions: I'm targeting Google Optimize server-side experimentation by borrowing their From a person setting up an AB test:
My intention is that toggles should either have more than one variant or no variants at all. That's how an experiment toggle could optionally be identified.
Maybe you're using toggles in a special way? From a conceptual model's perspective, I see Experiments as a special case of Feature Toggles. Possibly I got it from LaunchDarkly. I agree they are meant to serve different purposes, but the commonalities are evident from this point of view:
I have not put much thought on a statistical model and a report component for unleash, but I see a lot of potential with current framework. Having an experiments manager in a different section makes sense from a user experience perspective. If you think I may be cluttering too much ideas in a god model, please stop me.
🤔 Do you mean others than simple weighting strategies? Have any example in mind? |
lib/db/feature-toggle-store.js
Outdated
@@ -96,6 +98,9 @@ class FeatureToggleStore { | |||
enabled: data.enabled ? 1 : 0, | |||
archived: data.archived ? 1 : 0, | |||
strategies: JSON.stringify(data.strategies), | |||
variations: data.variations | |||
? JSON.stringify(data.variations) | |||
: '[]', |
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 would prefer to have the database migrate script (which is missing from this changeset) to default this column to an empty array.
Thanks, this was the missing link for me. Thinking about this as a pipeline really makes sense. I think this can work very well with the modified client API explained by @vsandvold. What do you think?
No not really. It's just code, and we are meant to iterate on it. And I'm very interested in finding ways to add first class support for experimentation in Unleash. What we have done internally might not be the best approach. I have already discussed with @vsandvold to make this the priority for v4 of Unleash. All outside help of any help is highly appreciated!
Would it make sense to have a 'default' variation if none is not defined, in order to make it more predictable to the client code?
There is two critical factors I'm thinking about:
Also we have found the need to be able to specify/override variations for specific users. This makes it much easier for the teams to verify that the various variations works as expected. In the future it might also be interesting to make sure that the same user is not assigned to multiple experiments at the same time that might push the same KPIs. But this should not be the focus in the first iteration of this imho. Do you know whether Google Optimize has the ability to discover users attending multiple experiments at the same time? Summary
Still a bit unclear to me:
|
I think @vsandvold's explanation is a good starting point. However, I would simplify it with something like how Optimizely does. Maybe the following way could allow more comparison flexibility: any variation = unleash.experiment("an.experiment.key", context, ...); // run strategies
if (variation === 'someVariant') {
// Serve some variant
} else if (variation === 'anotherVariant') {
// Serve another variant
} else {
// Serve control/disabled
} In any case, I'm fine with the signature you decide to go on.
Yes, strategies seems a very good option to give clients the right elements for both targeting and variation allocation. I believe experimentation strategies are highly reusable via parametrization as it currently works. In this sense, lets have two types of strategies:
When a plain toggle: boolean strategies are computed as usual to resolve for
I don't think it makes sense. However you made me realize that the minimum amount of variations if added should be one. We can assume that, if the experiment is on for a single variation, both a baseline and a variation will be tested. Regarding the variation cases you expose:
You mean a user on same page that runs multiple experiments? I have not tried it, but I would guess they do. Should be a matter of signaling each experiment-variation: ga('set', 'exp', 'experiment1.variationA');
ga('set', 'exp', 'experiment2.anotherVariation');
...
// Events
ga('send', 'pageview');
Yes! That could be a useful feature to have when you consider your experiment needs more information than just a simple variation name. We may need to warn users against modifying these values after an experiment toggle is turned on. |
I think it makes sense to return a more complex object than just a string. This would allow us to add mote features later. It also makes sense, from our experience, to advice the user to dedicate one variant as the control group. This will make it easier to compare metrics from control against variants. Something in the line of: Variant variant = unleash.experiment("an.experiment.key", context, ...);
if (variant.getName() === 'control') {
// Serve control
} else if (variant.getName() === 'someVariant') {
// Serve variant
} else if (variant.getName() === 'otherVariant') {
// Serve other variant
} else {
// Serve default, could be same behavior result as control, but no experiment-related metrics-tracking will be enabled.
} I think you suggestion in this PR is plausible and could be the way forward in order to introduce real support for experimental toggles. I also believe our internal A/B testing approach based on strategies can benefit and be simplified of variants where part of the toggle definition. Next steps:
Also; |
@vsandvold would you have capacity to do some PoC-ing with the java client to see if our current internal version could play well with the suggested format from this PR? |
@ivarcon Not for the next few weeks, I'm afraid, unless I find some time in between other tasks at work. I think it has a lot of promise though, so please it up :-) |
There's a scenario I've been unable to solve for while implementing this in the node.js client and I believe needs the appropriate discussion. Say you want to target and allocate according to the following: 1 If you were to implement this in the current proposal you will need two strategies one for line 1 (A) and one for lines 2-5 (B). The problem with this approach is that you cannot reuse inner AND strategies, so developers will need to create new complex strategies (e.g. B) every time they need a slightly different set of conditions. Do you guys have any idea on how to solve it? I have one but don't want to bias you. |
@elhoyos That's a very relevant use case. We could treat A and B as different segments, the first targeting developers and the second a specific group of users. That may be a suitable abstraction for OR and AND combinations, one that ideally should be reinforced visually by the UI. Another way of grouping strategies could follow a stricter segment definition like "team, organization, rest of the world", with a more predefined setup of rules for each segment (like 100% team rollout, 50% organization, and 2% external). But I'm just throwing idea around. Please tell us what you have in mind :-) |
Is this not exactly what grouping of strategies would solve, discussed in #229 ? Her we talk about introducing "strategy groups". A strategy group could have one or more strategies. Within a strategy group all strategies are ANDed, effectively scoping the targeted users for all strategies added in the group. Strategy-groups should be ORed as they should not affect each other. Your example works if there only exist one variant, but what happens if there is 3 variants? Which one should be used in dev? As you suggested earlier there might be required to have some kind of "special" strategies where one can override variant for specific context attributes such as userId. Tehn the first group could be:
|
Thank you both for your input. I was thinking to have something similar as the "ANDing" strategy you both suggest. Following the referenced issue is the way to go. |
I will have a go at adding AND to clients and UI. |
What's the status here? 🙏 |
This is scheduled for v4.x release. I finally seem to have some more time to dedicate to this project. I am in the process of figuring out how to handle "multiple environments" / "grouping of strategies". I think this also will affect how we solve variations. |
Multi-variants and environments definitely seem to be the last big key features that would bring Unleash up to par with the big players. |
I will work on variants in the coming weeks. Environment support will come after that. |
Thank you. Appreciate the effort you're putting into this! |
needed to do a lot of re-basing and adjust format a bit, work continue in #379 |
Here's a proposal adding variations in a feature toggle to support further experiments.
Any suggestion or guidance is very welcome.