From f58042af8abdbc46649e00d7b236e4abf81bf929 Mon Sep 17 00:00:00 2001 From: Keita Jamadam Sugama Date: Mon, 21 Oct 2024 16:27:06 +0900 Subject: [PATCH] temp --- lib/Data/ObjectDriver/SQL.pm | 10 ++++++++++ t/11-sql.t | 21 ++++++++++++++++++++- 2 files changed, 30 insertions(+), 1 deletion(-) diff --git a/lib/Data/ObjectDriver/SQL.pm b/lib/Data/ObjectDriver/SQL.pm index 59a2e8b..b70658c 100644 --- a/lib/Data/ObjectDriver/SQL.pm +++ b/lib/Data/ObjectDriver/SQL.pm @@ -147,6 +147,15 @@ sub as_sql_having { ''; } +sub as_escape { + my ($stmt, $escape_char) = @_; + + # escape_char can be ''(two quotes), or \\ for mysql and \ for others, but it doesn't accept any injections. + die 'escape_char length must be up to two characters' if defined($escape_char) && length($escape_char) > 2; + + return " ESCAPE '$escape_char'"; +} + sub add_where { my $stmt = shift; ## xxx Need to support old range and transform behaviors. @@ -270,6 +279,7 @@ sub _mk_term { $term = "$c $val->{op} " . ${$val->{value}}; } else { $term = "$c $val->{op} ?"; + $term .= $stmt->as_escape($val->{escape}) if $val->{escape} && $op =~ /^(?:NOT\s+)?I?LIKE$/; push @bind, $val->{value}; } } diff --git a/t/11-sql.t b/t/11-sql.t index 48c1e25..9c771bc 100644 --- a/t/11-sql.t +++ b/t/11-sql.t @@ -3,7 +3,7 @@ use strict; use Data::ObjectDriver::SQL; -use Test::More tests => 95; +use Test::More tests => 102; my $stmt = ns(); ok($stmt, 'Created SQL object'); @@ -231,6 +231,25 @@ is($stmt->as_sql_where, "WHERE ((foo = ?) AND (foo = ?) AND (foo = ?))\n"); $stmt->add_where(%terms); is($stmt->as_sql_where, "WHERE ((foo = ?) AND (foo = ?) AND (foo = ?)) AND ((foo = ?) AND (foo = ?) AND (foo = ?))\n"); +## as_escape +$stmt = ns(); +$stmt->add_where(foo => {op => 'LIKE', value => '100%', escape => '\\'}); +is($stmt->as_sql_where, "WHERE (foo LIKE ? ESCAPE '\\')\n"); +is($stmt->bind->[0], '100%'); # escape doesn't automatically escape the value +$stmt = ns(); +$stmt->add_where(foo => {op => 'LIKE', value => '100\\%', escape => '\\'}); +is($stmt->as_sql_where, "WHERE (foo LIKE ? ESCAPE '\\')\n"); +is($stmt->bind->[0], '100\\%'); +$stmt = ns(); +$stmt->add_where(foo => {op => 'LIKE', value => '100%', escape => '!'}); +is($stmt->as_sql_where, "WHERE (foo LIKE ? ESCAPE '!')\n"); +$stmt = ns(); +$stmt->add_where(foo => {op => 'LIKE', value => '100%', escape => "''"}); +is($stmt->as_sql_where, "WHERE (foo LIKE ? ESCAPE '''')\n"); +$stmt = ns(); +$stmt->add_where(foo => {op => 'LIKE', value => '100%', escape => "\\'"}); +is($stmt->as_sql_where, "WHERE (foo LIKE ? ESCAPE '\\'')\n"); + $stmt = ns(); $stmt->add_select(foo => 'foo'); $stmt->add_select('bar');