Передача поля как параметра в процедуру

Rezec

По пиву? (socket80)
Передача поля как параметра в процедуру

[sql]PROCEDURE W_USER_INFO_SEARCH (
pi_string IN VARCHAR2,
pi_field IN VARCHAR2,
mycurs OUT TYPES.cursortype
)
IS
BEGIN
OPEN mycurs FOR
SELECT W_SYS_USERS_PRIVATE.*
FROM W_SYS_USERS_PRIVATE
WHERE
LOWER(pi_field) LIKE LOWER(pi_string)
;
END; -- Procedure[/sql]

pi_field - это поле. Процедура ничего не возвращает т.к. наверное не воспринимает переменную как поле. Что делать?
 

K&T

Guest
Явно дело не в параметре, похоже сам селект кривой, да и вообще похорошему если надо что-то возвращать, то лучше писать FUNCTION
 

K&T

Guest
Если сомневаешься в том что все прилетает, вкрути перед селектом dbms_output и посмотри что за селект вообще собирается.
 

Rezec

По пиву? (socket80)
SQL не кривой, т.к. если pi_string = '%' то курсор возвращает все данные из таблицы а если pi_string = 'male' то тогда нули.
 

Rezec

По пиву? (socket80)
Возможно что pi_field надо обявить не как VARCHAR2, а как то по другому
 

K&T

Guest
Так а что за селект собирается внутри ты не проверил? Собери его сначало в какой нибудь варчар, а потом уже выполняй и гони в курсор. Все что соберется вытяни наверх OUT параметром. Иначе придется долго гадать в чем проблема.
 

K&T

Guest
Вкратце так:
PROCEDURE W_USER_INFO_SEARCH( pi_string IN VARCHAR2, pi_field IN VARCHAR2, mycurs OUT TYPES.cursortype, temp_sql out varchar2 ) IS
BEGIN

temp_sql := 'SELECT W_SYS_USERS_PRIVATE . *
FROM W_SYS_USERS_PRIVATE
WHERE LOWER( '||pi_field||' )
LIKE LOWER( '||pi_string||' )';

OPEN mycurs FOR SELECT W_SYS_USERS_PRIVATE . *
FROM W_SYS_USERS_PRIVATE
WHERE LOWER( pi_field )
LIKE LOWER( pi_string ) ;

END ;

Вот и смотри что за селект вернется в temp_sql.
 

K&T

Guest
Да все ясно, так работать и не будет, надо делать через EXECUTE IMMEDIATE, так что можешь и не смотреть.
 

K&T

Guest
Вот так точно заработает.

PROCEDURE W_USER_INFO_SEARCH (pi_string IN VARCHAR2,
pi_field IN VARCHAR2,
mycurs OUT TYPES.cursortype)
IS
BEGIN
BEGIN
EXECUTE IMMEDIATE 'SELECT W_SYS_USERS_PRIVATE . * FROM W_SYS_USERS_PRIVATE WHERE LOWER( '||pi_field||' )
LIKE LOWER( '||pi_string||' )' BULK COLLECT INTO mycurs
EXCEPTION
WHEN OTHERS THEN
.....
END;
END ;


mycurs - зачем нужен курсор, все равно пока процедура не отработает OUT параметр не вернется.
Наверное надо как, то смодифицировать эту штуку ввиде TABLE of OBJECT или RECORDS
 

Rezec

По пиву? (socket80)
Процедура не компилится указывыет на ... BULK ... что это не тут стоит
 

Rezec

По пиву? (socket80)
Вобщем придется отказаться от динамического sql
 

K&T

Guest
Зачем отказываться, надо просто ";" поставить после BULK COLLECT INTO mycurs и все компелиться. Да вот еще, а что за тип TYPES.cursortype. Может так статься что в такую штуку не накопить результаты селекта, по причне нессоответствия типов данных.
 

K&T

Guest
А что за таблица W_SYS_USERS_PRIVATE надо по ней вточност создать TYPE one_rec AS OBJECT, а потом еще один
TYPE one_rec_list AS TABLE OF one_rec. После чего смело объявляй твой mycurs как one_rec_list и все стопудово работает. Только что проверял.
 

Rezec

По пиву? (socket80)
TYPES.cursortype - это курсоровый тип а INTO с курсором кажись не работает
 

Rezec

По пиву? (socket80)
Автор оригинала: K&T
А что за таблица W_SYS_USERS_PRIVATE надо по ней вточност создать TYPE one_rec AS OBJECT, а потом еще один
TYPE one_rec_list AS TABLE OF one_rec. После чего смело объявляй твой mycurs как one_rec_list и все стопудово работает. Только что проверял.
Навароты пошли :), попробую позже для себя, шефу не нравится dinamyc sql, небезопасно говорит.
 

K&T

Guest
Точно не работает, плюнь ты на курсор работай с коллекциями. На худой конец можно преобразовать колекшен в курсор посредством CAST
 
Сверху