什么是 A/B 测试?
A/B 测试,也称为拆分测试,是一种营销实验,可以在其中拆分受众以测试广告系列的多个变体并确定哪个效果更好。换句话说,可以向一半观众展示内容/功能/行为的版本 A,而向另一半观众展示版本 B。
为什么不使用第三方服务?
确实将第 3 方 X 用于 A/B。
对于 X,观察到以下问题:
- 由于服务器端标记的高延迟
- 特征复杂度
- 分割部分的跟踪和影响测量。
- 成本高
它提供什么?
该服务(作为微服务实现)将使客户能够进行 A/B 测试。可以对多个特征(返回值)进行任意数量的实验。
设计时要牢记可扩展性和进一步增强功能。
常用功能包括:
- 能够在受限的基础上控制功能上线(特定用户)
- 为随机 (%) 用户启用任何功能
- 根据具有复杂逻辑的用户配置文件/特定参数评估功能
- 能够在受限的基础上控制前端功能(UI 元素)
- 在任何实验中添加/编辑特征
- 使段相互排斥的能力
- 能够找出哪个用户属于特定细分
- 此类实验可能产生的所有其他分析
技术栈:
Springboot
Java 8
Maven
Mysql
Groovy
架构设计:
这是上面实体保存的内容的简短描述。所有实体都扩展 BasEntity 以获取所有实体的公共列。
- 实验:所有实验都将保存在这里,并带有唯一名称和可选描述。
- Feature:一个实验可以有多个特征,这些特征将保存在这个表中,具有唯一的名称,可选的描述和 experiment_id 作为实验表的外键。 值是该功能将以 json 格式返回给客户端的内容。 Whitelisted_users 将包含 user_id 列表作为逗号分隔列表,它将告诉哪些用户分配给此功能。
- 逻辑:由于每个实验都可以有一定的条件来划分用户段,所以这个条件会保存在逻辑表的条件栏中。(我们稍后会来实现)
- User_Feature_Mapping:因为我们可能希望一旦用户被分配到某个功能,它将在未来的 api 调用中保持相同的功能。换句话说,我们可能希望保持一致性而不是每次都评估逻辑(条件)。
流程设计:
现在将了解以上 2 个流程的含义:
usePreCalculated标志在这里很重要,因为它意味着我们是要重用 User_Feature_Mapping 表中包含的值还是再次评估逻辑表中的条件。
- 如果为假,将检查实验的每个特征的 whitelisted_list。如果退出则返回值,否则将评估逻辑然后相应地返回特征值;
- 如果为真,将首先检查 user_feature_mapping 表是否存在 user_id 和 experiment_id。如果是,那么返回该值。如果没有,那么将按照上面的步骤(步骤 1)
注意:每次评估逻辑时,都会将结果保存在user_feature_mapping表中
如何评估条件?
将常规代码存储在逻辑表的条件列中。以下只是一个示例:
import groovy.lang.GroovyShell;
public class GroovyDemo {
public static void main(String[] args) {
System.out.println("This represents some random code");
String groovyScript = "println 'first line of Groovy output'\n" +
"println 'second line of Groovy output'";
GroovyShell groovyShell = new GroovyShell();
// instead of passing a String you could pass a
// URI, a File, a Reader, etc... See GroovyShell javadocs
groovyShell.evaluate(groovyScript);
System.out.println("This represents some more random code");
}
}
选择 groovy shell 是因为它具有绝对的灵活性。可以执行复杂的功能,甚至可以使用存储为文本的代码调用外部方法和 api。当用例很复杂时,这很有用,例如想根据某些只能由第三方 api 实现的用户属性或参数来分配用户段。
例如,如果想将A/B分成90:10,可以对user_id进行模10运算,并将结果0分配给B段,剩下的分配给A段。可以多次更改比例甚至逻辑无需重新部署。
API列表:
- /experiment POST -> 创建一个实验
- /experiment/{experiment_name} PUT -> 编辑实验
- /experiment/{experiment_name} GET -> 获取实验的详细信息
- /experiment/{experiment_id}/feature POST -> 向实验添加特征
- /feature/{feature_id} PUT -> 编辑特征
- /feature/{feature_id}/whitelist PUT -> 编辑特定功能的白名单用户列表
- /experiment/evaluate/{experiment_name} POST -> 主要 api。评估实验并返回 json 格式的响应