@Test public void testLikeNewlineInMatch() { Regex regex = likePattern(utf8Slice("f%b%")); assertTrue(likeVarchar(utf8Slice("foo\nbar"), regex)); }
@ScalarFunction @LiteralParameters({"x", "y"}) @SqlType(LikePatternType.NAME) public static Regex likePattern(@SqlType("varchar(x)") Slice pattern, @SqlType("varchar(y)") Slice escape) { return likePattern(pattern.toStringUtf8(), getEscapeChar(escape), true); }
@Test public void testIsLikePattern() { assertFalse(isLikePattern(utf8Slice("abc"), null)); assertFalse(isLikePattern(utf8Slice("abc#_def"), utf8Slice("#"))); assertFalse(isLikePattern(utf8Slice("abc##def"), utf8Slice("#"))); assertFalse(isLikePattern(utf8Slice("abc#%def"), utf8Slice("#"))); assertTrue(isLikePattern(utf8Slice("abc%def"), null)); assertTrue(isLikePattern(utf8Slice("abcdef_"), null)); assertTrue(isLikePattern(utf8Slice("abcdef##_"), utf8Slice("#"))); assertTrue(isLikePattern(utf8Slice("%abcdef#_"), utf8Slice("#"))); assertThrows(PrestoException.class, () -> isLikePattern(utf8Slice("#"), utf8Slice("#"))); assertThrows(PrestoException.class, () -> isLikePattern(utf8Slice("abc#abc"), utf8Slice("#"))); assertThrows(PrestoException.class, () -> isLikePattern(utf8Slice("abc#"), utf8Slice("#"))); }
private boolean evaluateLikePredicate(LikePredicate node, Slice value, Regex regex) { if (type(node.getValue()) instanceof VarcharType) { return LikeFunctions.likeVarchar(value, regex); } Type type = type(node.getValue()); checkState(type instanceof CharType, "LIKE value is neither VARCHAR or CHAR"); return LikeFunctions.likeChar((long) ((CharType) type).getLength(), value, regex); }
@Test public void testLikeSpacesInPattern() { Regex regex = likePattern(utf8Slice("ala ")); assertTrue(likeVarchar(utf8Slice("ala "), regex)); assertFalse(likeVarchar(utf8Slice("ala"), regex)); regex = castCharToLikePattern(5L, utf8Slice("ala")); assertTrue(likeVarchar(utf8Slice("ala "), regex)); assertFalse(likeVarchar(utf8Slice("ala"), regex)); }
@Test public void testLikeNewlineInPattern() { Regex regex = likePattern(utf8Slice("%o\nbar")); assertTrue(like(utf8Slice("foo\nbar"), regex)); }
public static Regex likePattern(Slice pattern) { return likePattern(pattern.toStringUtf8(), '0', false); }
Regex regex; if (escape == null) { regex = LikeFunctions.likePattern((Slice) pattern); regex = LikeFunctions.likePattern((Slice) pattern, (Slice) escape); if (pattern instanceof Slice && (escape == null || escape instanceof Slice) && !isLikePattern((Slice) pattern, (Slice) escape)) { Slice unescapedPattern = unescapeLiteralLikePattern((Slice) pattern, (Slice) escape); Type valueType = type(node.getValue()); Type patternType = createVarcharType(unescapedPattern.length());
@Test public void testLikeChar() { Regex regex = likePattern(utf8Slice("f%b__")); assertTrue(likeChar(6L, utf8Slice("foobar"), regex)); assertTrue(likeChar(6L, utf8Slice("foob"), regex)); assertFalse(likeChar(7L, utf8Slice("foob"), regex)); assertFunction("cast('foob' as char(6)) LIKE 'f%b__'", BOOLEAN, true); assertFunction("cast('foob' as char(7)) LIKE 'f%b__'", BOOLEAN, false); }
@ScalarFunction @SqlType(LikePatternType.NAME) public static Regex likePattern(@SqlType(StandardTypes.VARCHAR) Slice pattern, @SqlType(StandardTypes.VARCHAR) Slice escape) { return likeToPattern(pattern.toStringUtf8(), getEscapeChar(escape), true); }
@ScalarFunction(value = "like", hidden = true) @LiteralParameters("x") @SqlType(StandardTypes.BOOLEAN) public static boolean likeVarchar(@SqlType("varchar(x)") Slice value, @SqlType(LikePatternType.NAME) Regex pattern) { // Joni can infinite loop with UTF8Encoding when invalid UTF-8 is encountered. // NonStrictUTF8Encoding must be used to avoid this issue. byte[] bytes = value.getBytes(); return regexMatches(pattern, bytes); }
@Test public void testUnescapeValidLikePattern() { assertEquals(unescapeLiteralLikePattern(utf8Slice("abc"), null), utf8Slice("abc")); assertEquals(unescapeLiteralLikePattern(utf8Slice("abc#_"), utf8Slice("#")), utf8Slice("abc_")); assertEquals(unescapeLiteralLikePattern(utf8Slice("a##bc#_"), utf8Slice("#")), utf8Slice("a#bc_")); assertEquals(unescapeLiteralLikePattern(utf8Slice("a###_bc"), utf8Slice("#")), utf8Slice("a#_bc")); } }
@ScalarFunction(value = "like", hidden = true) @LiteralParameters("x") @SqlType(StandardTypes.BOOLEAN) public static boolean likeChar(@LiteralParameter("x") Long x, @SqlType("char(x)") Slice value, @SqlType(LikePatternType.NAME) Regex pattern) { return likeVarchar(padSpaces(value, x.intValue()), pattern); }
@Test public void testLikeNewlineBeforeMatch() { Regex regex = likePattern(utf8Slice("%b%")); assertTrue(like(utf8Slice("foo\nbar"), regex)); }
private Regex getConstantPattern(LikePredicate node) { Regex result = likePatternCache.get(node); if (result == null) { StringLiteral pattern = (StringLiteral) node.getPattern(); if (node.getEscape().isPresent()) { Slice escape = ((StringLiteral) node.getEscape().get()).getSlice(); result = LikeFunctions.likePattern(pattern.getSlice(), escape); } else { result = LikeFunctions.likePattern(pattern.getSlice()); } likePatternCache.put(node, result); } return result; }
@ScalarFunction(value = "like", hidden = true) @SqlType(StandardTypes.BOOLEAN) public static boolean like(@SqlType(StandardTypes.VARCHAR) Slice value, @SqlType(LikePatternType.NAME) Regex pattern) { // Joni can infinite loop with UTF8Encoding when invalid UTF-8 is encountered. // NonStrictUTF8Encoding must be used to avoid this issue. byte[] bytes = value.getBytes(); return regexMatches(pattern, bytes); }
@Test public void testLikeBasic() { Regex regex = likePattern(utf8Slice("f%b__")); assertTrue(like(utf8Slice("foobar"), regex)); }
@Test public void testBackslashesNoSpecialTreatment() { Regex regex = likePattern(utf8Slice("\\abc\\/\\\\")); assertTrue(likeVarchar(utf8Slice("\\abc\\/\\\\"), regex)); }
@ScalarOperator(OperatorType.CAST) @LiteralParameters("x") @SqlType(LikePatternType.NAME) public static Regex castVarcharToLikePattern(@SqlType("varchar(x)") Slice pattern) { return likePattern(pattern); }
@Test public void testLikeNewlineInMatch() { Regex regex = likePattern(utf8Slice("f%b%")); assertTrue(like(utf8Slice("foo\nbar"), regex)); }