Hvad mere er, intet indikerer et behov for PL/pgSQL til at begynde med. En almindelig (forberedt) SELECT
statement kan gøre det. Eller en SQL-funktion, hvis du vil bevare den i databasen. Se:
Og vedrørende:
Definer inklusive/eksklusiv øvre/nedre grænse præcist for at undgå overraskende resultater i hjørnekassen. Når du sammenligner et timestamp
kolonne til en date
, er sidstnævnte tvunget til tidsstemplet, der angiver dagens første forekomst:YYYY.MM.DD 00:00:00
.
Din forespørgsel siger:
measurement_timestamp <= lastDate AND measurement_timestamp >= firstDate
... som ville omfatte alle firstDate
, men ekskluder alle lastDate
undtagen det første (almindelige) tilfælde kl. 00:00 . Typisk ikke hvad du ønsker. I betragtning af din formulering, formoder jeg, at dette er, hvad du virkelig ønsker:
CREATE OR REPLACE FUNCTION get_measurements_by_node_and_date(node_id integer
, firstDate date
, lastDate date)
RETURNS TABLE (measurement_id integer
, node_id integer
, carbon_dioxide float8
, hydrocarbons float8
, temperature float8
, humidity float8
, air_pressure float8
, measurement_timestamp timestamp)
LANGUAGE sql STABLE AS
$func$
SELECT m.id
, m.node_id
, m.carbon_dioxide
, m.hydrocarbons
, m.temperature
, m.humidity
, m.air_pressure
, m.measurement_timestamp -- AS measure -- just documentation
FROM public.measurements_lora m
WHERE m.node_id = _node_id
AND m.measurement_timestamp >= firstDate::timestamp
AND m.measurement_timestamp < (lastDate + 1)::timestamp -- ①!
$func$;
① Dette inkluderer alle lastDate
og effektivt. Du kan bare tilføje/fratrække et integer
værdi til/fra en date
at tilføje / trække dage fra
. Den eksplicitte cast til ::timestamp
er valgfri, da dato ville blive tvunget automatisk i udtrykket. Men da vi prøver at rydde op i forvirringen her ...
Relateret:
Bortset fra 1:
Nej. timestamp
værdier er ikke formateret, punktum. De er blot tidsstempelværdier (internt gemt som antallet af mikrosekunder siden epoken). Visningen er fuldstændig adskilt fra værdien og kan justeres på hundrede og én måde uden at ændre værdien . Slip af med denne misforståelse for bedre at forstå, hvad der foregår. Se:
Bortset fra 2:
Om SQL BETWEEN
s lumske karakter :
Bortset fra 3:
Overvej lovlige identifikatorer med små bogstaver i Postgres. first_date
i stedet for firstDate
. Se:
Relateret:
- PostgreSQL-funktion returnerer en datakube
- Postgresql forsøger at bruge execute-format i en funktion, men får kolonne not found-fejlen, når streng-format gives i coalesce