You are on page 1of 34

Oracle Data

Warehousing
CSIS 4320 Data Warehousing
Lab 4

Reporting on Data Warehouse

Role of metadata
Querying Oracle metadata
SQL analytical processing
Advanced calculations

Role of Metadata

For using the data warehouse


For building the data warehouse
For administering the data warehouse
Notice though from the text
86% fully recognized metadata is important
However, only 9% actually implemented
Suggesting that it is a difficult process create and maintain data
warehouse metadata

Technical Metadata
Metadata is meant for the IT professionals perform the
development and administration of the data warehouse
Technical metadata helps to understand DW model and
perform query
Answer questions such as

What database tables exist?


How are tables related to each other?
What are the keys and indexes?
What are column names and descriptions?

Oracle Metadata
Oracle metadata is the description about the data itself in the
database
Metadata repository
Metadata is scattered across the system

Oracle presents metadata in forms of data dictionary, which


consists of a number of views
Different privilege has access on different metadata

Oracle Metadata
Oracle APEX Object Browser provides convenient graphical
user interface (GUI) to view some metadata
As we have experienced in Lab 1

As DW professionals, we can see more metadata through


querying Oracle data dictionary
USER_*
For example: USER_TABLES and USER_INDEXES

Which are views Oracle provided for user to access metadata

Querying Oracle Metadata


To see what tables are available under OLAPTRAIN schema
Query view USER_TABLES

Querying Oracle Metadata


To see table columns for a table
Query view USER_TAB_COLUMNS

Querying Oracle Metadata


Okay, your turn (copy, paste, and run)
To see primary key and foreign key constraints
select *
from user_constraints
where constraint_type in ('P', 'R')
and table_name in ('CHANNELS', 'CUSTOMERS',
'PRODUCTS', 'TIMES', 'SALES_FACT')
order by constraint_type, table_name;

To see all constraints for a table


select * from user_constraints where table_name = 'PRODUCTS';

To see constraint columns


select * from user_cons_columns where table_name = 'PRODUCTS';

Querying Oracle Metadata


To see indexes for a table
select * from user_indexes where table_name = 'PRODUCTS';
select * from user_indexes where table_name = 'SALES_FACT';

To see index columns


select * from user_ind_columns where table_name = 'PRODUCTS';
select * from user_ind_columns where table_name = 'SALES_FACT';

Querying Oracle Metadata


To see table comments
Any descriptive comments on tables to help us understand the
business perspective of the tables?
select * from user_tab_comments
where table_name in ('CHANNELS', 'CUSTOMERS', 'PRODUCTS',
'TIMES', 'SALES_FACT')
order by table_name;

To see column comments


At least some tables have descriptive comments on columns
select * from user_col_comments
where table_name in ('CHANNELS', 'CUSTOMERS', 'PRODUCTS',
'TIMES', 'SALES_FACT')
order by table_name;

Querying Oracle Metadata


In summary
Question

View Name

What tables exist?

USER_TABLES

What are column names?

USER_TAB_COLUMNS

What are the keys and constraints?

USER_CONSTRAINTS

What are the constraint columns?

USER_CONS_COLUMNS

What are the indexes?

USER_INDEXES

What are the index columns?

USER_IND_COLUMNS

Are there descriptions for tables?

USER_TAB_COMMENTS

Are there descriptions for columns?

USER_COL_COMMENTS

There are MANY data dictionary views


SELECT VIEW_NAME FROM ALL_VIEWS WHERE VIEW_NAME LIKE 'USER_%';

SQL Analytical Processing


Oracle has enhanced SQLs analytical processing capabilities
A family of aggregate and analytic SQL functions

Aggregate and analytic functions are a fundamental part of


data warehousing
Helps answer business queries
Make querying and reporting easier and faster

Preparing a Business Report


Prepare a business report with aggregate function
Find quarterly sales revenue across different product categories,
in order by the amount of revenue for 2007
Run following query formed by SUM:
(copy, paste, and run in your APEX environment)
SELECT t.calendar_quarter_name quarter, p.category_name
category,
TO_CHAR(SUM(s.sales),'L999G999G990D00') revenue
FROM times t, products p, sales_fact s
WHERE t.day_key = s.day_key AND p.item_key = s.product
AND s.day_key BETWEEN TO_DATE('01-JAN-2007','dd-MON-yyyy')
AND TO_DATE('31-DEC-2007','dd-MON-yyyy')
GROUP BY t.calendar_quarter_name, p.category_name
ORDER BY t.calendar_quarter_name, sum(s.sales);

Preparing a Business Report


Here is the result with aggregate function SUM

Quarter 4

Quarter 1

(middle section was chopped off)

Adding Totals with ROLLUP


Now, to see the totals for different quarters and the grand
total in the same report
Use the ROLLUP function
SELECT t.calendar_quarter_name quarter, p.category_name
category,
TO_CHAR(SUM(s.sales),'L999G999G990D00') revenue
FROM times t, products p, sales_fact s
WHERE t.day_key = s.day_key AND p.item_key = s.product
AND s.day_key BETWEEN TO_DATE('01-JAN-2007','dd-MON-yyyy')
AND TO_DATE('31-DEC-2007','dd-MON-yyyy')
GROUP BY ROLLUP(t.calendar_quarter_name, p.category_name)
ORDER BY t.calendar_quarter_name, sum(s.sales);

Adding Totals with ROLLUP

Quarter 4

Quarter 1

Here is the result with ROLLUP function

Cross-Tabular with CUBE


Further, to see not only quarterly totals, but also totals for the
different product categories for the selected period
Use the CUBE function
SELECT t.calendar_quarter_name quarter, p.category_name category,
TO_CHAR(SUM(s.sales),'L999G999G990D00') revenue
FROM times t, products p, sales_fact s
WHERE t.day_key = s.day_key AND p.item_key = s.product
AND s.day_key BETWEEN TO_DATE('01-JAN-2007','dd-MON-yyyy')
AND TO_DATE('31-DEC-2007','dd-MON-yyyy')
GROUP BY CUBE(t.calendar_quarter_name, p.category_name)
ORDER BY t.calendar_quarter_name, sum(s.sales);

Cross-Tabular with CUBE

Subtotals for
Categories

Quarter 1

Here is the result with CUBE function

Cross-Tabular with CUBE


The result with CUBE function is ready for generating a crosstabular report like the one shown below by programming or
software applications
(I copied data in Excel manually)

Adding Label with GROUPING


You may have noticed from ROLLUP and CUBE result
Totals and subtotals have no labels

Use GROUPING function to describe the total row


E.g., GROUPING(t.calendar_quarter_name)
Returns 1, if its for totals or subtotals, a grouping row
Returns 0, otherwise

Then, use DECODE function to add label accordingly


DECODE(GROUPING(t.calendar_quarter_name),
0, t.calendar_quarter_name
1, 'TOTAL'
)

If its a normal row,


display original quarter name.
Else, if its a total row, label it
with TOTAL.

Adding Label with GROUPING


Use the GROUPING function
SELECT DECODE(GROUPING(t.calendar_quarter_name),
0, t.calendar_quarter_name,
1, 'TOTAL'
) quarter,
DECODE(GROUPING(p.category_name),
0, p.category_name,
1, 'TOTAL'
) category,
TO_CHAR(SUM(s.sales),'L999G999G990D00') revenue
FROM times t, products p, sales_fact s
WHERE t.day_key = s.day_key AND p.item_key = s.product
AND s.day_key BETWEEN TO_DATE('01-JAN-2007','dd-MON-yyyy')
AND TO_DATE('31-DEC-2007','dd-MON-yyyy')
GROUP BY CUBE(t.calendar_quarter_name, p.category_name)
ORDER BY t.calendar_quarter_name, sum(s.sales);

Adding Label with GROUPING

Subtotals for
Categories

Quarter 1

Here is the result with GROUPING function

Combining with GROUPING SETS


Functions ROLLUP and CUBE will generate every possible
combination of totals for every level
There will be 2n sets of total, n is the number of columns

For example, we used two columns: quarter and category

So, CUBE will generate 2n = 4 sets of total


Set 1: for each quarter with each category (4*8=32)
Set 2: for each quarter (4)
Set 3: for each category (8)
Set 4: for the grand total (1)
32 + 4 + 8 + 1 = 45 rows

Combining with GROUPING SETS

Set 3

Set 1

Set 2

Set 4

Combining with GROUPING SETS


If three columns are used
4 quarters, 2 channels, and 8 categories
CUBE will generate 23 = 8 sets of total

Set 1: for each combination of three columns (4*2*8=64)


Set 2: for each quarter with each channel (4*2=8)
Set 3: for each channel with each category (2*8=16)
Set 4: for each category with each quarter (8*4=32)
Set 5: for each quarter (4)
Set 6: for each channel (2)
Set 7: for each category (8)
Set 8: for the grand total (1)
64+8+16+32+4+2+8+1 = 135 rows

Combining with GROUPING SETS


To combine particular subtotals in a data cube, but not all that
are possible
Use the GROUPING SETS function
SELECT DECODE(GROUPING(t.calendar_quarter_name),
0, t.calendar_quarter_name, 1, 'TOTAL') quarter,
DECODE(GROUPING(c.class_name),
0, c.class_name, 1, '--all') channel,
DECODE(GROUPING(p.category_name),
0, p.category_name, 1, 'TOTAL') category,
TO_CHAR(SUM(s.sales),'L999G999G990D00') revenue
FROM times t, products p, channels c, sales_fact s
WHERE t.day_key = s.day_key AND p.item_key = s.product AND c.channel_key = s.channel
AND s.day_key BETWEEN TO_DATE('01-JAN-2007','dd-MON-yyyy')
AND TO_DATE('31-DEC-2007','dd-MON-yyyy')
GROUP BY GROUPING SETS(c.class_name, CUBE(t.calendar_quarter_name, p.category_name))
ORDER BY t.calendar_quarter_name, c.class_name, sum(s.sales);

Combining with GROUPING SETS


Here is the result with GROUPING SETS function

Advanced Calculations
Business information processing requires advanced
calculations
Ranking
Relative contributions to a total

Ranking
To see an additional column that shows the rank of any
revenue number within the quarter
SELECT DECODE(GROUPING(t.calendar_quarter_name),
0, t.calendar_quarter_name, 1, 'TOTAL') quarter,
DECODE(GROUPING(t.calendar_quarter_name) + GROUPING(p.category_name),
0, RANK() OVER (PARTITION BY t.calendar_quarter_name ORDER BY SUM(s.sales)),
1, null) ranking,
DECODE(GROUPING(c.class_name),
0, c.class_name, 1, '--all') channel,
DECODE(GROUPING(p.category_name),
0, p.category_name, 1, 'TOTAL') category,
TO_CHAR(SUM(s.sales),'L999G999G990D00') revenue
FROM times t, products p, channels c, sales_fact s
WHERE t.day_key = s.day_key AND p.item_key = s.product AND c.channel_key = s.channel
AND s.day_key BETWEEN TO_DATE('01-JAN-2007','dd-MON-yyyy')
AND TO_DATE('31-DEC-2007','dd-MON-yyyy')
GROUP BY GROUPING SETS(c.class_name, CUBE(t.calendar_quarter_name, p.category_name))
ORDER BY t.calendar_quarter_name, c.class_name, sum(s.sales);

Ranking
Here is the result with RANK function

Relative Contribution
To calculate the contribution of every product category to the
total revenue based on a given time period
SELECT DECODE(GROUPING(t.calendar_quarter_name),
0, t.calendar_quarter_name, 1, 'TOTAL') quarter,
DECODE(GROUPING(t.calendar_quarter_name) + GROUPING(p.category_name),
0, RANK() OVER (PARTITION BY t.calendar_quarter_name ORDER BY SUM(s.sales)),
1, null) ranking,
DECODE(GROUPING(c.class_name),
0, c.class_name, 1, '--all') channel,
DECODE(GROUPING(p.category_name),
0, p.category_name, 1, 'TOTAL') category,
TO_CHAR(SUM(s.sales),'L999G999G990D00') revenue,
TO_CHAR(100 * RATIO_TO_REPORT(SUM(s.sales))
OVER (PARTITION BY (TO_CHAR(GROUPING(p.category_name) || t.calendar_quarter_name))), '990D0') percent
FROM times t, products p, channels c, sales_fact s
WHERE t.day_key = s.day_key AND p.item_key = s.product AND c.channel_key = s.channel
AND s.day_key BETWEEN TO_DATE('01-JAN-2007','dd-MON-yyyy')
AND TO_DATE('31-DEC-2007','dd-MON-yyyy')
GROUP BY GROUPING SETS(c.class_name, CUBE(t.calendar_quarter_name, p.category_name))
ORDER BY t.calendar_quarter_name, c.class_name, sum(s.sales);

Relative Contribution
Here is the result with RATIO_TO_REPORT function

Aggregate and Analytic Functions


Function

Description

ROLLUP

Group the selected rows, and returns a single row of summary for
each group.

CUBE

Group the selected rows based on the values of all possible


combinations, and returns a single row of summary for each group.

GROUPING

Distinguish a null representing the set of all values in a aggregate


row.

GROUPING SETS

Specify multiple groupings of data and prune the aggregates not


needed.

RANK

Calculate the rank of a value in a group of values.

RATIO_TO_REPORT

Compute the ratio of a value to the sum of a set of values.

You might also like