Question

I have a requirement to create a view that is to be used to generate reports. The view will take a users table and join it up with an orders table and a workflow table based on the user ID and the order ID. The view is complicated by the fact that I need to join the orders table a number of times as I need to join based on a couple of different order statuses.

I need to able to get a count of the amount of orders with an open status per user, a count of the amount of orders with a status of "returned", "on hold" or "returned - faulty" and a count of the number of orders in each district for each user.

Getting all of the data together is fine I have just set up a simple select with a join for each count requirement as below. My problem is that this will return counts on all of the records in tables and I need to be able to restrict it to orders within a certain time that will be parametrized.

I need some help getting the a time restriction onto the joins.

select u.FIRST_NAME || ' ' || u.LAST_NAME as ASSIGNED_TO,
u.ID,
j4.TOTAL_AREA1,
j1.total,
j2.TOTAL_OPENED,
j3.TOTAL_RETURNED

from users u
left outer join
(      
 select u1.FIRST_NAME || ' ' || u1.LAST_NAME as ASSIGNED_TO,
        u1.ID,
        COUNT(o1.ORDER_KEY) as total
 from users u1,
  orders o1,
  WORKFLOW_WORKITEM ww1    

 where
        o1.ORDER_KEY = ww1.ENTITY_KEY_NUM
        AND ww1.ENTITY_NAME = 'Order'
        AND ww1.ASSIGNED_TO = U1.ID

 GROUP BY u1.FIRST_NAME,
        u1.LAST_NAME,
        u1.id) j1
on 
j1.ID = u.ID


left outer join 
(      
 select u1.FIRST_NAME || ' ' || u1.LAST_NAME as ASSIGNED_TO,
        u1.ID,
        COUNT(o1.ORDER_KEY) as TOTAL_OPENED
 from users u1,
      ORDERS o1,
      WORKFLOW_WORKITEM ww1    

 where
        o1.CASE_KEY = ww1.ENTITY_KEY_NUM
        AND ww1.ENTITY_NAME = 'Order'
        AND ww1.ASSIGNED_TO = U1.ID
        AND ww1.STATUS_CODE='S_ORD_CA_021'

 GROUP BY u1.FIRST_NAME,
        u1.LAST_NAME,
        u1.id) j2
on 
j2.ID = u.ID
left outer join 
(      
 select u1.FIRST_NAME || ' ' || u1.LAST_NAME as ASSIGNED_TO,
        u1.ID,
        COUNT(o1.ORDER_KEY) as TOTAL_RETURNED
 from users u1,
      ORDERS o1,

      WORKFLOW_WORKITEM ww1    

 where
        o1.ORDER_KEY = ww1.ENTITY_KEY_NUM
        AND ww1.ENTITY_NAME = 'Order'
        AND ww1.ASSIGNED_TO = U1.ID
        AND ww1.STATUS_CODE in ('S_ORD_CA_015', 'S_ORD_CA_016', 'S_ORD_CA_017','S_ORD_CA_018')

 GROUP BY u1.FIRST_NAME,
        u1.LAST_NAME,
        u1.id) j3
on 
j3.ID = u.ID


left outer join
(
select  
        u1.ID,
        COUNT(o1.ORDER_KEY) as TOTAL_AREA1

from    users u1,
        ORDERS o1,
        WORKFLOW_WORKITEM ww1,
        domains dm  

where
        o1.ORDER_KEY = ww1.ENTITY_KEY_NUM
        AND ww1.ENTITY_NAME = 'Order'
        AND ww1.ASSIGNED_TO = U1.ID
        and ww1.DOMAIN_ID=dm.ID
    AND dm.CODE='AREA1'

GROUP BY 
        u1.FIRST_NAME,
        u1.LAST_NAME,
        u1.id,
        ww1.DOMAIN_ID,
        dm.DESCRIPTION
       ) j4
on 
j4.ID = u.ID
Was it helpful?

Solution

Basically you want to add something like:

o1.DATE between :param_from and :param_to

in every 'order' subquery. :notation is a standard for oracle parameters, but how parameters will be bound depends on environment that you use to execute your query. So please write what environment/tool you use.

You can try to simplyfy the query (I hope I didn't make any syntax error, I wrote it in notepad...):

select 
    ASSIGNED_USER, 
    UID, 
    count(AREA1) TOTAL_AREA1, 
    count(1) TOTAL,
    count(OPENED) TOTAL_OPENED,
    count (RETURNED) TOTAL_RETURNED
from
    (
    select 
        u1.id UID,
        u1.FIRST_NAME || ' ' || u1.LAST_NAME as ASSIGNED_USER,
        case when dm.CODE='AREA1' then 1 else null end AREA1,
        case when ww1.STATUS_CODE='S_ORD_CA_021' then 1 else null end OPENED,
        case when ww1.STATUS_CODE in 
          ('S_ORD_CA_015', 'S_ORD_CA_016', 'S_ORD_CA_017','S_ORD_CA_018') then 1
            else null end RETURNED
    from users u1
        left outer join WORKFLOW_WORKITEM ww1 on AND ww1.ASSIGNED_TO = U1.ID
            AND ww1.ENTITY_NAME = 'Order'
        left outer join orders o1 on o1.ORDER_KEY = ww1.ENTITY_KEY_NUM
        left outer join domains dm on ww1.DOMAIN_ID=dm.ID
    where 
        o1.DATE between :param_from and :param_to
        -- you can add any other conditions that may 
        -- cut number of selected records
        -- to minimum required to get expected results
    )
group by UID, ASSIGNED_USER;
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top