-- FUNCTION: public.widget_PieChart_OverAllRevenue(date, text, integer)

-- DROP FUNCTION IF EXISTS public."widget_PieChart_OverAllRevenue"(date, text, integer);

CREATE OR REPLACE FUNCTION public."widget_PieChart_OverAllRevenue"(
	"fromDate" date,
	"filterType" text,
	"locationId" integer DEFAULT NULL::integer)
    RETURNS TABLE("Date" date, "Name" text, "Count" numeric) 
    LANGUAGE 'plpgsql'
    COST 100
    VOLATILE PARALLEL UNSAFE
    ROWS 1000

AS $BODY$
declare
f record;
intervaldata interval;
ftype text;
currentdate date;
fromdate date;
begin
intervaldata:= case when "filterType"='day' then '1 D' when "filterType"='month' then '1 Month' when "filterType"='year' then '1 Year' end;
ftype:= case when "filterType"='day' then 'month'::text  when "filterType"='month' then 'year'::text when "filterType"='year' then 'year'::text end;
currentdate:= case when  "filterType"='year' then date_trunc(ftype, "fromDate")  - '2 Y'::interval else date_trunc(ftype, "fromDate") end ;
fromdate:=case when "filterType"='day' and  current_date > "fromDate"  then   (date_trunc('month', "fromDate"::date) + interval '1 month' - interval '1 day')::date
 when  "filterType"='month' and   "fromDate" < current_date then  date_trunc('Year', "fromDate"::date) + interval '1 Year' - interval '1 month' 
 
else "fromDate" end;

 raise notice 'intervaldata %', intervaldata;
 raise notice 'ftype %', ftype;
  raise notice 'currentdate %', currentdate;
create  Temp TABLE temp_table 
(
	startdate date,
   	enddate date, 
	dname text,
  	countdata numeric
 ) ON COMMIT DELETE ROWS;
 
create  Temp TABLE temp_date_table 
( startdate date,
   enddate date
 ) ON COMMIT DELETE ROWS;
 for f in 
 select   generate_series( currentdate  , fromdate,  intervaldata)  weeks 
    loop 
           insert into temp_date_table (startdate,enddate)
		   select f.weeks::text::date ,(f.weeks+ intervaldata)::text::date ;
		   --raise notice 'datetable %', f.weeks::text::date;
   end loop;
for f in 
 select   generate_series( currentdate  , fromdate,  intervaldata)  weeks 
    loop 
	raise notice 'currentdate %', f.weeks::text::date;
	raise notice 'fromdate %', fromdate::date;
	insert into temp_table (startdate,enddate,dname,countdata)

with actappointmentamount as (
	
	select  A.appointmentamount::bigint appointmentamount from (
   select    sum(coalesce(AP."Total",0)) appointmentamount
		
from "Appointment" ap
   where ap."Status" <> 'C' 
	and	(Ap."AppointmentDate" >= f.weeks::text::date and Ap."AppointmentDate" < (f.weeks+ intervaldata)::text::date)
	and case when ("locationId" is null) or ("locationId"=0) then 1=1 else AP."LocationId"= "locationId" end
	  	)a
)

,appointmentamount as (
select 
	
	coalesce(A.appointmentamount,0) as "AppointmentAmount" from actappointmentamount A 
)
,actadmissionamount as (
	
	select  a."Total" "AdmissionAmount" from (
select sum(coalesce(adr."Cost",0)) "Total"									  
												  
from  "Receipt" adr 	 
	 join "Admission" ad on  adr."AdmissionId" = ad."AdmissionId" and ad."Active" <> false
	join "Provider" pr on pr."ProviderId"= ad."ProviderId"
	where  	
	 adr."ReceiptTypeId"=1  and adr."Active"<>false  and adr."AdmissionId" is not null
		and adr."CreatedDate"::date >= f.weeks::text::date and adr."CreatedDate"::date <= (f.weeks+ intervaldata)::text::date	
		and case when ("locationId" is null) or ("locationId"=0) then 1=1 else ad."LocationId"= "locationId" end
	)a
	
)

,refadmissionamount as (
	select  a."Total" "AdmissionRefAmount" from (
select sum(coalesce(adr."Cost",0)) "Total" 
from  "Receipt" adr 	 
	 join "Admission" ad on  adr."AdmissionId" = ad."AdmissionId" and ad."Active" <> false
	join "Provider" pr on pr."ProviderId"= ad."ProviderId"
	where 
	  adr."IsRefunded" = true   and adr."Active"<>false  and adr."AdmissionId" is not null
		and adr."CreatedDate"::date >= f.weeks::text::date and adr."CreatedDate"::date <= (f.weeks+ intervaldata)::text::date	
	and case when ("locationId" is null) or ("locationId"=0) then 1=1 else ad."LocationId"= "locationId" end	
	
	)a
	
)
,admissionamount as (
select 
	coalesce(A."AdmissionAmount",0) - coalesce(B."AdmissionRefAmount",0) "AdmissionAmount"
   from actadmissionamount A ,refadmissionamount B 
	

)

,LabAmount as ( 
select a."TotalAmount" "LabAmount" from(
	select sum(coalesce(ar."NetAmount",0)) "TotalAmount"
from "LabBookingHeader" ar
where ar."Active" <> false and (ar."CreatedDate"::date >= f.weeks::text::date and ar."CreatedDate"::date < (f.weeks+ intervaldata)::text::date)	
and case when ("locationId" is null) or ("locationId"=0) then 1=1 else ar."LocationId"= "locationId" end
	)a
)

,PharmaSaleAmount as (
	
select a."Total"
	"PharmaSaleAmount" from (
select sum(coalesce(ar."OverallNetAmount",0)) "Total"
from "PharmacySaleHeader" ar
where ar."SaleDate"::date >= f.weeks::text::date and ar."SaleDate"::date <= (f.weeks+ intervaldata)::text::date	
and case when ("locationId" is null) or ("locationId"=0) then 1=1 else ar."LocationId"= "locationId" end
	
	)a

)
,PharmaReturnAmount as (
select a."Total" "PharmaReturnAmount" from(
select sum(coalesce(ar."OverallNetAmount",0)) "Total"
from "SaleReturnHeader" ar
left join "PharmacySaleHeader" srh on srh."PharmacySaleHeaderId" = ar."PharmacySaleHeaderId"
 where ar."ReturnDate" ::date >= f.weeks::text::date and ar."ReturnDate" ::date <= (f.weeks+ intervaldata)::text::date	
)a

)

,PharmaAmount as (
select 

	coalesce(a."PharmaSaleAmount",0) - coalesce(b. "PharmaReturnAmount",0) as  "PharmaAmount" 
from PharmaSaleAmount a ,PharmaReturnAmount b 
	

)
,finaldata as (select 
case when "Total" = 0 then 0 else round("AppointmentAmount"/"Total"*100,2) end "AppointmentAmount",
case when "Total" = 0 then 0 else round("AdmissionAmount"/"Total"*100,2) end "AdmissionAmount",
case when "Total" = 0 then 0 else round("LabAmount"/"Total"*100,2) end "LabAmount", 
case when "Total" = 0 then 0 else round("PharmacyAmount"/"Total"*100,2) end "PharmacyAmount",
"Total" 
from (
select distinct 
	ap."AppointmentAmount",
	ad."AdmissionAmount",
	lb."LabAmount",
sum(pa."PharmaAmount") over() "PharmacyAmount",	
coalesce(ap."AppointmentAmount",0)+coalesce(ad."AdmissionAmount",0)+coalesce(lb."LabAmount",0)
+coalesce(sum(pa."PharmaAmount") over(),0) "Total"

from  appointmentamount ap , admissionamount ad ,LabAmount lb ,PharmaAmount pa ) a)

select date_trunc('month', current_date)::date startdate ,f.weeks enddate,
       unnest(array['AppointmentAmount','AdmissionAmount','LabAmount', 'PharmacyAmount']) as "Name",
       unnest(array[ coalesce("AppointmentAmount",0),coalesce("AdmissionAmount",0),coalesce("LabAmount",0), coalesce("PharmacyAmount",0)]) as "Count" 
from finaldata;
end loop;
	RETURN QUERY
	with finalData as (select A.endDate,A.dname,sum(coalesce(A.countdata,0) )::numeric countdata from temp_table A group by A.endDate,A.dname)
	
	select A.startdate,B.dname,coalesce(B.countdata,0) from temp_date_table A
	left join finalData B on A.startdate=B.endDate;
	
	drop table temp_table;
	drop table temp_date_table;				
END;
$BODY$;

ALTER FUNCTION public."widget_PieChart_OverAllRevenue"(date, text, integer)
    OWNER TO postgres;
