Да, я знаю о DatabaseMetadata.getIndexInfo
, но, похоже, он не выполняет то, что я хочу.
У меня есть два пользователя / схемыдавайте назовем их A
и B
.
В A
есть таблица с именем TAB
.Пользователь B
создал индекс для A.TAB
, назовем этот индекс IND
.
Информация, которую я хочу , такова: какие индексы есть в таблице TAB
в схеме A
(он же с владельцем A
).Мне плевать на владельца индексов, просто они на этом конкретном столе.
Экспериментируя с getIndexInfo
Я обнаружил следующие вещи:
- первыйаргумент
catalog
, похоже, полностью игнорируется драйвером Oracle JDBC. - второй аргумент
schema
ограничивает , какие статистические данные таблицы возвращаются и владелец индекса unique
и approximate
делают (примерно) то, что должны (за исключением того, что при approximate=false
фактически выполняется оператор статистики обновления).
Отследив SQL, который драйвер JDBC выполняет на getIndexInfo(null, "A", "TAB", false, true)
, я получил следующее:
select null as table_cat,
owner as table_schem,
table_name,
0 as NON_UNIQUE,
null as index_qualifier,
null as index_name, 0 as type,
0 as ordinal_position, null as column_name,
null as asc_or_desc,
num_rows as cardinality,
blocks as pages,
null as filter_condition
from all_tables
where table_name = 'TAB'
and owner = 'A'
union
select null as table_cat,
i.owner as table_schem,
i.table_name,
decode (i.uniqueness, 'UNIQUE', 0, 1),
null as index_qualifier,
i.index_name,
1 as type,
c.column_position as ordinal_position,
c.column_name,
null as asc_or_desc,
i.distinct_keys as cardinality,
i.leaf_blocks as pages,
null as filter_condition
from all_indexes i, all_ind_columns c
where i.table_name = 'TAB'
and i.owner = 'A'
and i.index_name = c.index_name
and i.table_owner = c.table_owner
and i.table_name = c.table_name
and i.owner = c.index_owner
order by non_unique, type, index_name, ordinal_position
Как вы можете видеть и table_name
и i.owner
ограничено до TAB
.Это означает, что этот запрос только вернет индексную информацию, которой владеет тот же пользователь, что и таблица.
Я могу придумать три возможных обходных пути:
- всегда создавайте индекс и таблицу в одной и той же схеме (т.е. пусть они имеют одного и того же владельца).К сожалению, это не всегда вариант.
- Запрос с
schema
, установленным на null
.Это было бы ужасно, как только две схемы содержали одно и то же имя таблицы (потому что по невозможно определить, какая таблица (то есть, какой владелец таблицы) является данной схемой). - executeэтот SQL напрямую (используя
executeQuery()
).Я бы предпочел не опускаться до этого уровня, если только это не является абсолютно неизбежным.
Ни один из этих обходных путей не выглядит мне особенно приятным, но если ничего не работает, мне, возможно, придется вернуться к прямому SQLвыполнение.
И база данных, и драйвер JDBC находятся по адресу 11.2.0.2.0.
Так что в основном мои вопросы:
- Это ошибка вДрайвер JDBC, или есть какая-то логика, о которой я не знаю?
- Существует ли простой и достаточно переносимый способ заставить Oracle предоставлять мне нужную информацию?