sql >> Databasteknik >  >> RDS >> PostgreSQL

Hur returnerar man endast arbetstid från bokningar i PostgreSql?

Du kan använda funktionen gener_series() för att maskera icke kontorstid:

with gaps as (
    select
        upper(during) as start,
        lead(lower(during),1,upper(during)) over (ORDER BY during) - upper(during) as gap
    from (
        select during
        from reservation
        union all
        select
            unnest(case
                when pyha is not null then array[tsrange(d, d + interval '1 day')]
                when date_part('dow', d) in (0, 6) then array[tsrange(d, d + interval '1 day')]
                when d::date = '2012-11-14' then array[tsrange(d, d + interval '9 hours'), tsrange(d + interval '18 hours', d + interval '1 day')]
                else array[tsrange(d, d + interval '8 hours'), tsrange(d + interval '18 hours', d + interval '1 day')]
            end)
        from generate_series(
            '2012-11-14'::timestamp without time zone, 
            '2012-11-14'::timestamp without time zone + interval '2 week', 
            interval '1 day'
        ) as s(d) 
        left join pyha on pyha = d::date
    ) as x 
)
select *
    from gaps
where gap > '0'::interval
order by start

Låt mig förklara några knepiga delar:

  • du behöver inte infoga datum för lör/sön i pyha tabell eftersom du kan använda date_part('dow', d) fungera. Använd pyha bord endast för helgdagar. 'dow' returnerar 0 eller 6 för sön respektive lör.
  • helgdagar och lör/sön kan representeras som enstaka intervall (0..24). Veckodagar måste representeras av två intervall (0..8) och (18..24) därav unnest() och array[]
  • du kan ange startdatum och längd i funktionen gener_series()

Baserat på din uppdatering av frågan lade jag till en annan when till case :

when d::date = '2012-11-14' then array[tsrange(d, d + interval '9 hours'), tsrange(d + interval '18 hours', d + interval '1 day')]

Tanken är att skapa olika intervall för startdatum (d::date = '2012-11-14' ):(0..9) och (18..24)




  1. En första titt på den nya SQL Server Cardinality Estimator

  2. Hur NOW() fungerar i MariaDB

  3. Hur ändrar jag formateringen för mina returvärden i den här funktionen?

  4. Funktion för att returnera dynamisk uppsättning kolumner för given tabell