当你需要为你的单元测试想出有用的测试数据时,你是否也经常没有灵感?不要担心,Java Faker来救你了!在这篇博客中,你将学习如何生成你的测试数据。在这篇博客中,你将学习如何生成你的测试数据。
1. 简介
编写测试数据是编写测试时最难的任务之一。通常你会在使用数字的时候看到123,或者在需要名字的时候看到John Doe。但这也意味着,测试将总是以相同的数据运行。这一方面是一件好事,因为你的测试需要稳定,但另一方面也是一个遗憾,因为你也想找到错误。而当使用随机测试数据时,这种情况更有可能发生。 Java Faker是一个基于Ruby的faker gem和Perl的Data::Faker库的库。它将为你生成假数据。还有其他的Java库,它还基于其他语言的现有伪造者。
2. 添加依赖性
作为一个实验项目,你将创建一个基本的Spring Boot应用程序。只要导航到start.spring.io,用Java 17创建一个Spring Boot应用程序。当然,Java Faker也可以用于普通的Java应用程序。剩下要做的唯一一件事,就是将javafaker的依赖性添加到pom中。
<
dependency
>
<
groupId
>com.github.javafaker</
groupId
>
<
artifactId
>javafaker</
artifactId
>
<
version
>1.0.2</
version
>
<
scope
>test</
scope
>
</
dependency
>
3. 第一次测试
Java Faker提供了许多可以使用的数据伪造器。完整的列表可以在这里找到,带有一些例子的演示应用程序可以在这里找到。在你创建的第一个例子中,你创建了一个Faker实例,从那一刻起,你可以选择一个faker并生成数据。使用地址制作器来生成一个名字、一个姓氏和一个街道名称。
@Test
void
addressFaker() {
Faker faker =
new
Faker();
String firstName = faker.address().firstName();
String lastName = faker.address().lastName();
String streetName = faker.address().streetName();
System.out.println(
"First name: "
+ firstName);
System.out.println(
"Last name: "
+ lastName);
System.out.println(
"Street name: "
+ streetName);
}
例如,输出结果如下,但每次运行时都会发生变化。
First name: Mika
Last name: Terry
Street name: Wisoky Walk
4. 本地化的伪造者
在前面的例子中,你注意到生成的是英文名字。但是如果你想要更多的特定地区的名字呢?这也是可能的,但要注意的是,并不是每一个伪造者都能在每种语言中使用。你所在地区的列表可以在这里找到。唯一的区别是,你需要在实例化Faker的时候提供locale。我们试一下中文
@Test
void addressCNFaker() {
Faker faker = new Faker(new Locale("zh-cn"));
String firstName = faker.address().firstName();
String lastName = faker.address().lastName();
String streetName = faker.address().streetName();
System.out.println("First name: " + firstName);
System.out.println("Last name: " + lastName);
System.out.println("Street name: " + streetName);
}
输出
First name: 琪
Last name: 任
Street name: 丁旁
试一下阿拉伯语,特别是我们国际化产品测试中
First name: عبير
Last name: المالكيّ
Street name: شارع جرير
邮政编码:
@Test
public void givenJavaFakersWithDifferentLocals_thenHeckZipCodesMatchRegex() {
Faker ukFaker = new Faker(new Locale("en-GB"));
Faker usFaker = new Faker(new Locale("en-US"));
System.out.println(String.format("American zipcode: %s", usFaker.address().zipCode()));
System.out.println(String.format("British postcode: %s", ukFaker.address().zipCode()));
Pattern ukPattern = Pattern.compile(
"([Gg][Ii][Rr] 0[Aa]{2})|((([A-Za-z][0-9]{1,2})|"
+ "(([A-Za-z][A-Ha-hJ-Yj-y][0-9]{1,2})|(([A-Za-z][0-9][A-Za-z])|([A-Za-z][A-Ha-hJ-Yj-y]"
+ "[0-9]?[A-Za-z]))))\\s?[0-9][A-Za-z]{2})");
Matcher ukMatcher = ukPattern.matcher(ukFaker.address().zipCode());
assertTrue(ukMatcher.find());
Matcher usMatcher = Pattern.compile("^\\d{5}(?:[-\\s]\\d{4})?$")
.matcher(usFaker.address().zipCode());
assertTrue(usMatcher.find());
}
5. 使用FakeValuesService的随机字符串
使用FakeValuesService,你可以生成几个包含随机数据的字符串。在接下来的章节中,将展示其中的一些功能。
5.1 使用Numerify的随机字符串
通过numerify,你可以生成一个包含随机数的字符串。首先,你需要创建一个FakeValuesService实例,包含一个locale和一个RandomService。numerify方法将返回一个字符串,其中的哈希值(#)被替换成数字。对于每一个哈希值,都有一个数字被替换。
@Test
void
fakeValuesServiceNumerify() {
FakeValuesService fakeValuesService =
new
FakeValuesService(
new
Locale(
"nl-NL"
),
new
RandomService());
String randomNumber = fakeValuesService.numerify(
"number##"
);
System.out.println(
"Random number is: "
+ randomNumber);
}
5.2 使用字母化的随机字符串
与numerify类似,letterify将允许你通过问号的方式来替换字符串中的字符。
@Test
void
fakeValuesServiceLetterify() {
FakeValuesService fakeValuesService =
new
FakeValuesService(
new
Locale(
"nl-NL"
),
new
RandomService());
String randomLetters = fakeValuesService.letterify(
"somestring??"
);
System.out.println(
"Random letters are: "
+ randomLetters);
}
5.3 使用Bothify的随机字符串
使用Bothify可以实现数字和字母的结合。使用bothify,你可以将随机数字和字符结合起来。
@Test
void
fakeValuesServiceBothify() {
FakeValuesService fakeValuesService =
new
FakeValuesService(
new
Locale(
"nl-NL"
),
new
RandomService());
String randomNumbersLetters = fakeValuesService.bothify(
"some string with numbers ## and letters ??"
);
System.out.println(
"Random numbers and letters are: "
+ randomNumbersLetters);
}
5.4 用Regexify生成随机字符串
当上述所有这些还不够时,你也可以用regexify根据正则表达式生成字符串。下一个正则表达式将选择列表a、b或c中的一个或多个字符,后面是任何空白字符和一个数字。
@Test
void
fakeValuesServiceRegexify() {
FakeValuesService fakeValuesService =
new
FakeValuesService(
new
Locale(
"nl-NL"
),
new
RandomService());
String randomBasedRegex = fakeValuesService.regexify(
"[abc]+\\s\\d"
);
System.out.println(
"Random string based on a pattern: "
+ randomBasedRegex);
}
6.扩展
如我们想扩充下物资名称,在源代码中找到zh-CN.yml,增加对应字符串
@Test
public void testMaterial() {
assertThat(faker.commerce().material(), matchesRegularExpression("\\w+"));
int sum=0;
for (int i=1; i<=10;i++){
Faker faker = new Faker(new Locale("zh-cn"));
String materialName = faker.commerce().material();
System.out.println(materialName);
}
}
输出:
雨衣(分体式)
漂白粉
单兵净水器
夏衬衫(男)
泛光灯
躯体固定气囊
7. 总结
Java Faker是一个易于使用的数据生成器库。它将你从为你的测试编制测试数据的负担中解脱出来。此外,它将在每次运行时生成其他数据,这可能会揭示你的应用程序中的错误。该库的文档可以做得更好,但另一方面,该库也很容易使用,所以这毕竟不应该是一个大问题。