Skip to content

Commit 8002be5

Browse files
authored
Merge pull request IvorySQL#989 from rophy/fix/981
fix: allow parenthesized expressions in SELECT INTO statements
2 parents c51d958 + 701929d commit 8002be5

File tree

3 files changed

+160
-1
lines changed

3 files changed

+160
-1
lines changed

src/pl/plisql/src/expected/plisql_simple.out

Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -139,3 +139,80 @@ begin
139139
raise notice 'val = %', val;
140140
end; $$;
141141
NOTICE: val = 42
142+
-- Check SELECT INTO with parenthesized expressions (IvorySQL issue #981)
143+
do $$
144+
declare
145+
x int := 50;
146+
result numeric;
147+
begin
148+
-- Test parenthesized expression at start of SELECT list
149+
select (100 - x) * 0.01 into result from dual;
150+
raise notice 'Test 1 (parentheses): %', result;
151+
152+
-- Test without parentheses (should still work)
153+
select 100 - x into result from dual;
154+
raise notice 'Test 2 (no parentheses): %', result;
155+
156+
-- Test multiple parenthesized expressions
157+
select (100 - x) * (0.01 + x) into result from dual;
158+
raise notice 'Test 3 (multiple parentheses): %', result;
159+
160+
-- Test nested parentheses
161+
select ((100 - x) * 0.01) into result from dual;
162+
raise notice 'Test 4 (nested parentheses): %', result;
163+
end; $$;
164+
NOTICE: Test 1 (parentheses): 0.50
165+
NOTICE: Test 2 (no parentheses): 50
166+
NOTICE: Test 3 (multiple parentheses): 2500.50
167+
NOTICE: Test 4 (nested parentheses): 0.50
168+
-- Edge case: nested SELECT with parenthesized expressions
169+
do $$
170+
declare
171+
result int;
172+
begin
173+
select (select (10 + 5) from dual) into result from dual;
174+
raise notice 'Nested SELECT: %', result;
175+
end; $$;
176+
NOTICE: Nested SELECT: 15
177+
-- Edge case: function call in parentheses (not just arithmetic)
178+
create function test_func(int) returns int language plisql
179+
as $$begin return $1 * 2; end$$;
180+
/
181+
do $$
182+
declare
183+
result int;
184+
begin
185+
select (test_func(25)) into result from dual;
186+
raise notice 'Function in parens: %', result;
187+
end; $$;
188+
NOTICE: Function in parens: 50
189+
-- Edge case: CASE expression in parentheses
190+
do $$
191+
declare
192+
x int := 10;
193+
result int;
194+
begin
195+
select (case when x > 5 then x * 2 else x end) into result from dual;
196+
raise notice 'CASE in parens: %', result;
197+
end; $$;
198+
NOTICE: CASE in parens: 20
199+
-- Edge case: SELECT with CAST in parentheses
200+
do $$
201+
declare
202+
result varchar;
203+
begin
204+
select (cast(123 as varchar)) into result from dual;
205+
raise notice 'CAST in parens: %', result;
206+
end; $$;
207+
NOTICE: CAST in parens: 123
208+
-- Edge case: Complex nested expression
209+
do $$
210+
declare
211+
x int := 10;
212+
y int := 5;
213+
result numeric;
214+
begin
215+
select ((x + y) * (x - y)) / 2.0 into result from dual;
216+
raise notice 'Complex expression: %', result;
217+
end; $$;
218+
NOTICE: Complex expression: 37.5000000000000000

src/pl/plisql/src/pl_gram.y

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2668,7 +2668,13 @@ stmt_execsql : K_IMPORT
26682668
if (tok == '=' || tok == COLON_EQUALS ||
26692669
tok == '[' || tok == '.')
26702670
word_is_not_variable(&($1), @1, yyscanner);
2671-
if (tok == '(' || tok == ';')
2671+
/*
2672+
* Check for SELECT keyword - must be treated as EXECSQL even
2673+
* when followed by '(' to allow parenthesized expressions
2674+
* like SELECT (100 - x) * 0.01 INTO ...
2675+
*/
2676+
if ((tok == '(' || tok == ';') &&
2677+
pg_strcasecmp($1.ident, "select") != 0)
26722678
{
26732679
PLiSQL_stmt_call *new;
26742680

src/pl/plisql/src/sql/plisql_simple.sql

Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -125,3 +125,79 @@ begin
125125
raise notice 'val = %', val;
126126
end; $$;
127127

128+
-- Check SELECT INTO with parenthesized expressions (IvorySQL issue #981)
129+
130+
do $$
131+
declare
132+
x int := 50;
133+
result numeric;
134+
begin
135+
-- Test parenthesized expression at start of SELECT list
136+
select (100 - x) * 0.01 into result from dual;
137+
raise notice 'Test 1 (parentheses): %', result;
138+
139+
-- Test without parentheses (should still work)
140+
select 100 - x into result from dual;
141+
raise notice 'Test 2 (no parentheses): %', result;
142+
143+
-- Test multiple parenthesized expressions
144+
select (100 - x) * (0.01 + x) into result from dual;
145+
raise notice 'Test 3 (multiple parentheses): %', result;
146+
147+
-- Test nested parentheses
148+
select ((100 - x) * 0.01) into result from dual;
149+
raise notice 'Test 4 (nested parentheses): %', result;
150+
end; $$;
151+
152+
-- Edge case: nested SELECT with parenthesized expressions
153+
do $$
154+
declare
155+
result int;
156+
begin
157+
select (select (10 + 5) from dual) into result from dual;
158+
raise notice 'Nested SELECT: %', result;
159+
end; $$;
160+
161+
-- Edge case: function call in parentheses (not just arithmetic)
162+
create function test_func(int) returns int language plisql
163+
as $$begin return $1 * 2; end$$;
164+
/
165+
166+
do $$
167+
declare
168+
result int;
169+
begin
170+
select (test_func(25)) into result from dual;
171+
raise notice 'Function in parens: %', result;
172+
end; $$;
173+
174+
-- Edge case: CASE expression in parentheses
175+
do $$
176+
declare
177+
x int := 10;
178+
result int;
179+
begin
180+
select (case when x > 5 then x * 2 else x end) into result from dual;
181+
raise notice 'CASE in parens: %', result;
182+
end; $$;
183+
184+
-- Edge case: SELECT with CAST in parentheses
185+
do $$
186+
declare
187+
result varchar;
188+
begin
189+
select (cast(123 as varchar)) into result from dual;
190+
raise notice 'CAST in parens: %', result;
191+
end; $$;
192+
193+
-- Edge case: Complex nested expression
194+
do $$
195+
declare
196+
x int := 10;
197+
y int := 5;
198+
result numeric;
199+
begin
200+
select ((x + y) * (x - y)) / 2.0 into result from dual;
201+
raise notice 'Complex expression: %', result;
202+
end; $$;
203+

0 commit comments

Comments
 (0)