我有以下方法检查用户使用的术语是否被列入黑名单。
static checkAgainstBlacklist(blacklistTerms, term) {
return blacklistTerms.some(word =>
(new RegExp(`\\b${word}\\b`, 'i')).test(term)
);
}
奇怪的是,它对带有特殊字符的单词失败:
it('should return true if sentence contains blacklisted term',
inject([BlacklistService], () => {
const blacklistTerms = [
'scat',
'spic',
'forbanna',
'olla',
'satan',
'götverenlerden',
'你它马的',
'幼児性愛者',
];
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'scat')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'scat-website')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'spic')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'website-spic')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'forbanna')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'olla')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'satan-website')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'götverenlerden')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, '你它马的')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, '幼児性愛者')).toEqual(true);
})
);
所有测试均通过这三个测试:
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, 'götverenlerden')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, '你它马的')).toEqual(true);
expect(BlacklistService.checkAgainstBlacklist(blacklistTerms, '幼児性愛者')).toEqual(true);
我该如何修正我的regex命令,使其能够识别这些术语?
[\b
匹配单词边界,但是失败的字符串中的第一个和最后一个字符(n
中的最后一个götverenlerden
除外)不是单词字符,因此该模式不匹配。
您可以通过匹配字符串的开头/结尾或某些分隔符(如空格和标点符号来更改它:
static checkAgainstBlacklist(blacklistTerms, term) {
return blacklistTerms.some(word =>
(new RegExp(
String.raw`(?:^|(?!\w)[\u0000-\u007f])${word}(?:$|(?!\w)[\u0000-\u007f])`,
'im'
)).test(term)
);
}
您可以看到正在使用的字符代码here。本质上,(?!\w)[\u0000-\u007f]
的作用是将字符代码0到字符代码255中的任何字符匹配,该字符<< [not不在0-9或A-Z或a-z或_
的范围内。
(?:^|(?!\w)[\u0000-\u007f])götverenlerden(?:$|(?!\w)[\u0000-\u007f])
https://regex101.com/r/AHRVgA/1[另一种方法是用分隔符(如标点符号,空格等-如上面的模式中的内容)分隔输入字符串,然后检查结果字符串中是否有任何单词包含在
blacklistTerms
中。也就是说,无论您使用自动过滤器的逻辑是什么,用户通常都足够有创造力,以找出在不触发过滤器的情况下传达消息的方法。