Это проблема с ограничениями.
Вот моя версия вашей установки, экстраполированная из того, что вы опубликовали. Обратите внимание, что имя параметра отличается от имени атрибута.
create or replace type folder_t as object
(name varchar2(128))
/
create table folders of folder_t
/
create or replace function getRef
(nome in varchar2)
return ref folder_t
is
fl_r REF folder_t;
begin
select ref(fl)
into fl_r
from folders fl
where fl.name = nome;
return fl_r;
end getRef;
/
Как видите, данные этого теста ...
SQL> insert into folders values (folder_t('temp'))
2 /
1 row created.
SQL> insert into folders values (folder_t('work'))
2 /
1 row created.
SQL>
... Я могу запросить два REF:
SQL> select getRef('temp') from dual
2 /
GETREF('TEMP')
--------------------------------------------------------------------------------
00002802091051432318864AF594741916D743E1291CF597373A4F4D7A93F159DA53A73FC0010372
2D0000
SQL> select getRef('work') from dual
2 /
GETREF('WORK')
--------------------------------------------------------------------------------
0000280209F31778C18D5740FBA0CB90929E1B6FBD1CF597373A4F4D7A93F159DA53A73FC0010372
2D0001
SQL>
Но если я изменю объявление функции, чтобы имя параметра совпадало с именем атрибута, это произойдет:
SQL> create or replace function getRef
2 (name in varchar2)
3 return ref folder_t
4 is
5 fl_r REF folder_t;
6 begin
7 select ref(fl)
8 into fl_r
9 from folders fl
10 where fl.name = name;
11
12 return fl_r;
13 end getRef;
14 /
Function created.
SQL> select getRef('temp') from dual
2 /
GETREF('TEMP')
------------------------------------------------------------
SQL>
Механизм SQL применяет область видимости из таблицы наружу. Поскольку неквалифицированный NAME
соответствует столбцу таблицы, он не проверяет, есть ли параметр с таким именем. Вот почему это хорошая идея, чтобы дать параметрам отдельное имя. Безусловно, я предпочитаю практику добавления префиксов к параметру P_
, поэтому нет вероятности столкновения паретера с локальными переменными или именами объектов.