web-dev-qa-db-fra.com

Utiliser une période variable dans un intervalle dans Postgres

J'ai une relation qui maintient des données historiques mensuelles. Ces données sont ajoutées au tableau le dernier jour de chaque mois. Un service que j'écris peut alors être appelé en spécifiant un mois et un nombre de mois avant pour lesquels récupérer les données historiques. Je fais cela en créant des variables startDate et endDate, puis en renvoyant des données entre les deux. Le problème que j'ai est que startDate est un nombre variable de mois avant endDate, et je ne peux pas comprendre comment utiliser une période variable dans un intervalle.

Voici ce que j'ai:

    DECLARE
      endDate   TIMESTAMP := (DATE_TRUNC('MONTH',$2) + INTERVAL '1 MONTH') - INTERVAL '1 DAY';
      startDate TIMESTAMP := endDate - INTERVAL $3 'MONTH';

Je sais que la ligne de startDate n'est pas correcte. Comment cela se fait-il correctement?

42
Belizzle

Utilisez cette ligne:

startDate TIMESTAMP := endDate - ($3 || ' MONTH')::INTERVAL;

et notez l'espace avant MONTH. Fondamentalement: vous construisez une chaîne avec comme 4 MONTH et le diffuser avec ::type dans un intervalle approprié.

Edit: J'ai trouvé une autre solution: vous pouvez calculer avec interval comme ceci:

startDate TIMESTAMP := endDate - $3 * INTERVAL '1 MONTH';

Cela me semble un peu plus agréable.

80
A.H.

Ce code n'a rien à voir directement avec votre situation, mais il illustre comment utiliser des variables dans l'arithmétique INTERVAL. Le nom de ma table est "calendrier".

CREATE OR REPLACE FUNCTION test_param(num_months integer)
  RETURNS SETOF calendar AS
$BODY$

    select * from calendar
    where cal_date <= '2008-12-31 00:00:00'
    and cal_date > date '2008-12-31' - ($1 || ' month')::interval;

$BODY$
  LANGUAGE sql VOLATILE
  COST 100
  ROWS 1000;