Запросить таблицы и столбцы на основе данных таблицы - PullRequest
2 голосов
/ 26 марта 2012

Не зная имени таблицы и столбцов, я хочу запросить базу данных, получить имена таблиц и столбцов, а затем запросить данные таблицы.

У меня есть схема базы данных Oracle, подобная следующей:

Item таблица:

Item_id, Item_type, 
=================
1   box
2   book
3   box

Book таблица:

Item_id, title,     author
===========================
2   'C# Programer', 'Joe'

Box таблица:

Item_id, Size
=====================
1,  'Large' 
3,  'X Large'

Column_mapping таблица

Item_type, column_name, display_order
=====================================
box,       Size,    1
book,      title,   1
book,      author   2

Table_mapping таблица:

Item_type,  Table_name
========================
box,        Box
book,       Book

Я бы хотел оператор SQL, который бы дал что-то вроде следующих результатов:

Item_id, Item_type  column1  column2
====================================
1,  box,        'Large',       <null>
2,  book,       'C# Programer', 'Joe'
3,  box,        'X Large',     <null>

Когда я попробовал упрощенный запрос

select * 
from 
   (select Table_name
    from Table_mapping
    where Item_type = 'box')
where 
   Item_id = 1; 

Я получаю ошибку, что Item_id является недействительным идентификатором

и если я попытаюсь

select * 
from 
    (select Table_name
     from Table_mapping
     where Item_type = 'box');

Я просто получаю

Table_name
===========
Box

Я не уверен, как поступить.

Ответы [ 3 ]

3 голосов
/ 26 марта 2012

Один из способов - объединить обе таблицы, а затем использовать объединение столбцов, которые могут содержать данные из любой таблицы

SELECT 
    i.Item_id,
    i.Item_type,
    COALESCE(b.title, bx.size)  column1,
     b.author   column2
FROM
   Item i
   LEFT JOIN Book b
   ON i.item_id = b.item_id
   LEFT JOIN Box bx
   ON i.item_id = bx.item_id

В зависимости от размера ваших наборов данных вы можете добавить фильтр в объединение, например,

   LEFT JOIN Book b
   ON i.item_id = b.item_id
       and i.item_type = 'book'
   LEFT JOIN Box bx
   ON i.item_id = bx.item_id
       and i.item_type = 'box'

Посмотрите, как это работает на этом SQLFiddle

Если вы хотите что-то сделать на основе данных в table_mapping или column_mapping, вам нужно использовать динамический SQL

0 голосов
/ 26 марта 2012

ORACLE на самом деле сохраняет имена таблиц и столбцов в своем словаре данных, поэтому вам не нужно хранить эти данные отдельно. Попробуйте это, чтобы получить имена таблиц:

SELECT table_name FROM user_tables;

Затем сделайте это, чтобы получить столбцы для каждой таблицы:

SELECT column_name FROM user_tab_columns WHERE table_name = 'MYTABLE';

Как только вы это сделаете, вам нужно будет создать хранимую процедуру для выполнения динамического SQL. Я не думаю, что вы можете сделать это простым запросом.

0 голосов
/ 26 марта 2012

В основном это два отдельных запроса. Один для коробок и один для книг. Вы можете использовать объединение, чтобы объединить наборы результатов вместе.

select i.Item_id, i.Item_type, b.size, null
from Item i inner join Box b on i.Item_id=b.Item_id
where i.Item_type = "box"
UNION
select i.Item_id, i.Item_type, b.title, b.author
from Item i inner join Book b on i.Item_id=b.Item_id
where i.Item_type = "book"
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...