Skip to content

Commit

Permalink
Add '\' as ESCAPE character for sp_columns_100 for LIKE operator (bab…
Browse files Browse the repository at this point in the history
…elfish-for-postgresql#2935)

There are few occurrences where we use procedure  sp_columns_100  to fetch column metadata. The issue with this procedure is, when the table name contains _ character, we may obtain some unexpected output. This is because in some places we are using using sp_columns_100 incorrectly with a backslash escaping underscores (e.g. “\_“). Underscores are wildcards in sp_columns_100 (and in LIKE in general), but sp_columns_100 does not use a backslash as an escape character.
Till now, sp_columns_100 , was invoking a plpgsql function sp_column_100_internal which used PG’s SIMILAR TO  to operator, which does use a backslash as the default escape character. 

With BABEL-4953, we have updated the definition of sp_columns_100 where we removed redundant function call and implemented the procedure by using TSQL LIKE operator on column name, which will create some problems in other places.

The change in the new version is correct. However, since currently we rely on the incorrect functionality of the escape characters, we are making this temporary change for now. Once, we have fixed the dependencies on this procedure, we need to revert it.

Signed-off-by: Shameem Ahmed <[email protected]>
  • Loading branch information
ahmed-shameem authored Sep 17, 2024
1 parent 77ab175 commit 0ba8d35
Show file tree
Hide file tree
Showing 4 changed files with 164 additions and 2 deletions.
3 changes: 2 additions & 1 deletion contrib/babelfishpg_tsql/sql/babelfishpg_tsql.sql
Original file line number Diff line number Diff line change
Expand Up @@ -500,7 +500,8 @@ BEGIN
END
) as SS_DATA_TYPE
from sys.sp_columns_100_view
where pg_catalog.lower(table_name) like pg_catalog.lower(sys.babelfish_truncate_identifier(@table_name)) COLLATE database_default
-- TODO: Temporary fix to use '\' as escape character for now, need to remove ESCAPE clause from LIKE once we have fixed the dependencies on this procedure
where pg_catalog.lower(table_name) like pg_catalog.lower(sys.babelfish_truncate_identifier(@table_name)) COLLATE database_default ESCAPE '\'
and ((SELECT coalesce(sys.babelfish_truncate_identifier(@table_owner),'')) = '' or table_owner like sys.babelfish_truncate_identifier(@table_owner) collate database_default)
and ((SELECT coalesce(sys.babelfish_truncate_identifier(@table_qualifier),'')) = '' or table_qualifier like sys.babelfish_truncate_identifier(@table_qualifier) collate database_default)
and ((SELECT coalesce(sys.babelfish_truncate_identifier(@column_name),'')) = '' or column_name like sys.babelfish_truncate_identifier(@column_name) collate database_default)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1205,7 +1205,8 @@ BEGIN
END
) as SS_DATA_TYPE
from sys.sp_columns_100_view
where pg_catalog.lower(table_name) like pg_catalog.lower(sys.babelfish_truncate_identifier(@table_name)) COLLATE database_default
-- TODO: Temporary fix to use '\' as escape character for now, need to remove ESCAPE clause from LIKE once we have fixed the dependencies on this procedure
where pg_catalog.lower(table_name) like pg_catalog.lower(sys.babelfish_truncate_identifier(@table_name)) COLLATE database_default ESCAPE '\'
and ((SELECT coalesce(sys.babelfish_truncate_identifier(@table_owner),'')) = '' or table_owner like sys.babelfish_truncate_identifier(@table_owner) collate database_default)
and ((SELECT coalesce(sys.babelfish_truncate_identifier(@table_qualifier),'')) = '' or table_qualifier like sys.babelfish_truncate_identifier(@table_qualifier) collate database_default)
and ((SELECT coalesce(sys.babelfish_truncate_identifier(@column_name),'')) = '' or column_name like sys.babelfish_truncate_identifier(@column_name) collate database_default)
Expand Down
110 changes: 110 additions & 0 deletions test/JDBC/expected/sp_columns_100.out
Original file line number Diff line number Diff line change
Expand Up @@ -168,16 +168,71 @@ varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallin
create table nums(a int, b smallint, c tinyint, d bigint, e bit, f float, g real, h numeric(5,3), i money, j smallmoney)
go

create table test_escape_chars_sp_columns_100(a int);
go

EXEC [sys].sp_columns_100 'vart', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
go
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
~~END~~


-- TODO: Should NOT return any row once the dependencies on sp_columns_100 has been fixed (added '\' as ESCAPE character as temporary fix for now)
EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


drop table nums
go

drop table test_escape_chars_sp_columns_100;
go

Use master
go

Expand Down Expand Up @@ -380,16 +435,71 @@ varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallin
create table nums(a int, b smallint, c tinyint, d bigint, e bit, f float, g real, h numeric(5,3), i money, j smallmoney)
go

create table test_escape_chars_sp_columns_100(a int);
go

EXEC [sys].sp_columns_100 'vart', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
go
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
~~END~~


-- TODO: Should NOT return any row once the dependencies on sp_columns_100 has been fixed (added '\' as ESCAPE character as temporary fix for now)
EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL
GO
~~START~~
varchar#!#varchar#!#varchar#!#varchar#!#smallint#!#varchar#!#int#!#int#!#smallint#!#smallint#!#smallint#!#varchar#!#nvarchar#!#smallint#!#smallint#!#int#!#int#!#varchar#!#smallint#!#smallint#!#smallint#!#smallint#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#varchar#!#int
sp_cols#!#dbo#!#test_escape_chars_sp_columns_100#!#a#!#4#!#int#!#10#!#4#!#0#!#10#!#1#!#<NULL>#!#<NULL>#!#4#!#<NULL>#!#<NULL>#!#1#!#YES#!#0#!#0#!#0#!#0#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#<NULL>#!#38
~~END~~


drop table nums
go

drop table test_escape_chars_sp_columns_100;
go

use master
go

Expand Down
50 changes: 50 additions & 0 deletions test/JDBC/input/sp_columns_100.sql
Original file line number Diff line number Diff line change
Expand Up @@ -95,12 +95,37 @@ go
create table nums(a int, b smallint, c tinyint, d bigint, e bit, f float, g real, h numeric(5,3), i money, j smallmoney)
go

create table test_escape_chars_sp_columns_100(a int);
go

EXEC [sys].sp_columns_100 'vart', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
go

-- TODO: Should NOT return any row once the dependencies on sp_columns_100 has been fixed (added '\' as ESCAPE character as temporary fix for now)
EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO

EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO

EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO

EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL
GO

EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL
GO

EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL
GO

drop table nums
go

drop table test_escape_chars_sp_columns_100;
go

Use master
go

Expand Down Expand Up @@ -206,12 +231,37 @@ go
create table nums(a int, b smallint, c tinyint, d bigint, e bit, f float, g real, h numeric(5,3), i money, j smallmoney)
go

create table test_escape_chars_sp_columns_100(a int);
go

EXEC [sys].sp_columns_100 'vart', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
go

-- TODO: Should NOT return any row once the dependencies on sp_columns_100 has been fixed (added '\' as ESCAPE character as temporary fix for now)
EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO

EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO

EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL, @ODBCVer = 3, @fUsePattern = 1
GO

EXEC sys.sp_columns_100 'test\_escape\_chars\_sp\_columns\_100', 'dbo', NULL, NULL
GO

EXEC sys.sp_columns_100 'test_escape_chars_sp_columns_100', 'dbo', NULL, NULL
GO

EXEC sys.sp_columns_100 'test\_escape_chars\_sp_columns_100', 'dbo', NULL, NULL
GO

drop table nums
go

drop table test_escape_chars_sp_columns_100;
go

use master
go

Expand Down

0 comments on commit 0ba8d35

Please sign in to comment.