-- FUNCTION: public.udf_fetchProviderAvailabilityDatesNew(integer, integer, integer, text, text, integer)

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

CREATE OR REPLACE FUNCTION public."udf_fetchProviderAvailabilityDatesNew"(
	providerid integer,
	locationid integer,
	specializationid integer,
	startdate text,
	enddate text,
	consultationtypeid integer)
    RETURNS TABLE("Date" date, "DateNumber" integer, "DayName" character varying, "Status" character) 
    LANGUAGE 'plpgsql'
    COST 100
    VOLATILE PARALLEL UNSAFE
    ROWS 1000

AS $BODY$
begin
return query
with TotalDates as (
SELECT DISTINCT regexp_split_to_table(A."AvailableDate",',') ::date "Dates" ,
	
	A."ProviderId",A."ProviderAvailabilityId",A."LocationId", A."StartDate", A."EndDate", A."LocationId", S."SpecializationId" , A."ConsultationTypeId"
from "ProviderAvailability" A 
JOIN "Location" PL ON A."LocationId" = PL."LocationId" AND PL."Active" = TRUE
JOIN "Provider" PR on A."ProviderId" = PR."ProviderId" AND PR."Active" = TRUE
JOIN "Specialization" S on S."SpecializationId" =A."SpecializationId"  AND S."Active" IS TRUE
--JOIN "Practice" P ON P."PracticeId" = PL."PracticeId" AND P."Active" = TRUE
where A."ProviderId"=providerid AND A."LocationId" = locationid And S."SpecializationId" = specializationid And A."ConsultationTypeId" = consultationTypeId and A."Active" IS TRUE

)
,Availability as (
select A."AvailableDay", A."ProviderAvailabilityId",A."AvailableDate"
	--A."ProviderId"
	--,A."ProviderLocationId"
	,A."LocationId", A."StartDate", A."EndDate", S."SpecializationId", A."ConsultationTypeId"
	--,json_array_elements(case when (A."Availability" is null or A."Availability"='') then '[]' else (A."Availability"::json)end) "Availability"
from "ProviderAvailability" A 
	--left join "ProviderAvailabilitySlot" PAS on PAS."ProviderAvailabilityId" = A."ProviderAvailabilityId"
	JOIN "Location" PL ON A."LocationId" = PL."LocationId" AND PL."Active" = TRUE
	JOIN "Provider" PR on A."ProviderId" = PR."ProviderId" AND PR."Active" = TRUE
	JOIN "Specialization" S on S."SpecializationId" = ANY(PR."Specializations") AND S."Active" IS TRUE
--JOIN "Location" PL ON A."LocationId" = PL."LocationId" AND PL."Active" = TRUE
--JOIN "Practice" P ON P."PracticeId" = PL."PracticeId" AND P."Active" = TRUE
	where A."ProviderId"=providerid AND A."LocationId" = locationid And S."SpecializationId" = specializationid  and A."ConsultationTypeId" = consultationTypeId And A."Active" IS TRUE 
	--and case when providerLocationId is null then 1=1 else A."ProviderLocationId"=providerLocationId end
)
,Avail as (
SELECT unnest(string_to_array(A."AvailableDay", ',')) AS "Day",unnest(string_to_array(A."AvailableDate", ',')) AS "AvailableDate", A."ProviderAvailabilityId",A."LocationId", A."StartDate", A."EndDate", A."SpecializationId"
from Availability A
)

, LeaveAvailability as (
select A."ProviderId",A."LeaveDate",coalesce(A."ProviderAvailabilityId"::text,
(
	select string_agg(D."ProviderAvailabilityId"::text,',') "ProviderAvailabilityId" from "ProviderAvailability" D where D."ProviderId"= providerid and D."LocationId" = locationid
))
	"ProviderAvailabilityId" from "ProviderLeave" A where A."ProviderId"=providerid and A."LocationId" = locationid
)
,LeaveData as (
select A."ProviderId",A."LeaveDate",regexp_split_to_table(A."ProviderAvailabilityId",',') ::int "ProviderAvailabilityId" 
	from LeaveAvailability A
)

,FinalData as (
select DISTINCT C."LeaveDate", A."Dates" "Date", A."ProviderId",A."ProviderAvailabilityId",A."StartDate",A."EndDate"
	--,A."LocationId"
	,extract(ISODOW from "Dates")"DateNo", CASE
WHEN extract(ISODOW from "Dates") =1 THEN 'Monday'
WHEN extract(ISODOW from "Dates") =2 THEN 'Tuesday'
WHEN extract(ISODOW from "Dates")=3 THEN 'Wednesday'
WHEN extract(ISODOW from "Dates")=4 THEN 'Thursday'
WHEN extract(ISODOW from "Dates")=5 THEN 'Friday'
WHEN extract(ISODOW from "Dates")=6 THEN 'Saturday'
WHEN extract(ISODOW from "Dates")=7 THEN 'Sunday' end "Day" ,
case when C."LeaveDate" is not null then 'L'   when "AvailableDate"::date is not null is not null then 'A' else '' end "Status"
from TotalDates A
left join Avail B on "AvailableDate"::date= A."Dates" ::date  and A."ProviderId"=A."ProviderId" and A."ProviderAvailabilityId"=B."ProviderAvailabilityId"
--and A."LocationId"=B."LocationId"
left join LeaveData C on C."LeaveDate"::date =A."Dates" and A."ProviderAvailabilityId"=C."ProviderAvailabilityId"
	where 
A."Dates"::Date between startdate::Date  and enddate::Date 

)

select DISTINCT A."Date",A."DateNo"::int,A."Day"::text::character varying(10),A."Status"::char
from FinalData A
where  trim(A."Status") <> '' 
--A."Date"  >= A."StartDate"::Date or 
--A."Date" <= A."EndDate"::Date 
order by A."Date";
end

$BODY$;

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