Nous utilisons des cookies pour vous garantir la meilleure expérience sur notre site. Si vous continuez à utiliser ce dernier, nous considèrerons que vous acceptez l'utilisation des cookies. J'ai compris ! ou En savoir plus !.
banniere

Le portail francophone de la géomatique


Toujours pas inscrit ? Mot de passe oublié ?
Nom d'utilisateur    Mot de passe              Toujours pas inscrit ?   Mot de passe oublié ?

Annonce

Suite à un problème technique intervenu entre le 22 et le 23 mars, nous avons du procéder dans la soirée du 25 mars, à la restauration de la base de données du 24 mars (matinée).

En clair, nous avons perdu vos contributions et inscriptions du dimanche 24 et du lundi 25 mars.
Nous vous prions de nous excuser.

#1 Wed 14 December 2016 16:10

legannec
Participant occasionnel
Lieu: Sainte-Marie-Aux-Mines
Date d'inscription: 8 Aug 2011
Messages: 39

trigger : mise à jour d'une donnée entre deux tables

Bonjour,

J'ai un léger problème pour mettre à jour une donnée dans une table A depuis une nouvelle donnée d'une table B.

Nous sommes dans la thématique d'un parc d'éclairage public, le but est de récupérer une date d'intervention de changement d'ampoule sur un point lumineux.

Dans un schéma ep, on trouve :

une table ep_support avec un champ code_point_lumineux contenant un identifiant unique pour chaque objet et un champ date_lampe qui comprend la dernière date de changement d'ampoule.

une autre table ep_entretien avec à nouveau le champ code_point_lumineux pour la mise en relation et un champ date_intervention à remplir lors d'un changement d'ampoule.

L'objectif est de remonter automatiquement la dernière date de changement d'ampoule de la table ep_entretien vers la table ep_support

Ce qui m’amène à deux difficultés :

- d'abord le trigger que je n'arrive pas à faire fonctionner lorsque l'on ajoute une nouvelle intervention :

Code:

-- Trigger: date_entretien on ep.ep_entretien

-- DROP TRIGGER date_entretien ON ep.ep_entretien;

CREATE TRIGGER date_entretien
  AFTER INSERT ON ep.ep_entretien
  FOR EACH ROW
  EXECUTE PROCEDURE retourne_date();
  
-- Function: retourne_date()

-- DROP FUNCTION retourne_date();

CREATE OR REPLACE FUNCTION retourne_date() RETURNS trigger AS
$BODY$
BEGIN
update ep_support SET date_lampe = new.date_intervention
where ep_support.code_point_lumineux = ep_entretien.code_point_lumineux;
return new ;
END;

 $BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION retourne_date()
  OWNER TO postgres;

- ensuite, pour un point lumineux avec un identifiant unique il pourrait avoir eu plusieurs changement d'ampoule à des dates différents, comment récupérer uniquement la dernière date d'intervention ?

Merci d'avoir pris le temps de lire ce post,


legannec, Sigiste à la com'com du Val d'Argent

Hors ligne

 

#2 Wed 14 December 2016 16:52

jmarsac
Participant assidu
Lieu: NICE
Date d'inscription: 26 Oct 2005
Messages: 566
Site web

Re: trigger : mise à jour d'une donnée entre deux tables

Bonjour,

Si je comprends bien :
- la table ep_support contient autant d'enregistrements que de supports avec comme clé primaire la colonne code_point_lumineux
- la table ep_entretien contient autant d'enregistrements que d'interventions (donc plusieurs enregistrements pour le même point lumineux identifié de manière unique par la colonne code_point_lumineux

Il faut utiliser NEW.code_point_lumineux au lieu de ep_entretien.code_point_lumineux

Code:

Code:

-- Trigger: date_entretien on ep.ep_entretien

-- DROP TRIGGER date_entretien ON ep.ep_entretien;

CREATE TRIGGER date_entretien
  AFTER INSERT ON ep.ep_entretien
  FOR EACH ROW
  EXECUTE PROCEDURE retourne_date();
  
-- Function: retourne_date()

-- DROP FUNCTION retourne_date();

CREATE OR REPLACE FUNCTION retourne_date() RETURNS trigger AS
$BODY$
BEGIN

UPDATE ep_support SET date_lampe = NEW.date_intervention
WHERE ep_support.code_point_lumineux = NEW.code_point_lumineux;

RETURN new ;
END;

 $BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION retourne_date()
  OWNER TO postgres;

Concernant la question des changements d'ampoule multiples sur le même point lumineux, elle est sans objet étant donné que le trigger traite toujours la dernière intervention (celle qui vient d'être insérée.)

Dernière modification par jmarsac (Wed 14 December 2016 16:57)


Jean-Marie
Azimut

Hors ligne

 

#3 Wed 14 December 2016 18:26

JD
Moderateur
Date d'inscription: 8 Aug 2013
Messages: 722

Re: trigger : mise à jour d'une donnée entre deux tables

jmarsac a écrit:

Concernant la question des changements d'ampoule multiples sur le même point lumineux, elle est sans objet étant donné que le trigger traite toujours la dernière intervention (celle qui vient d'être insérée.)


En supposant que les dates d'intervention soient rentrées dans l'ordre chronologique, ce qui est souvent le cas.

Hors ligne

 

#4 Wed 14 December 2016 18:38

jmarsac
Participant assidu
Lieu: NICE
Date d'inscription: 26 Oct 2005
Messages: 566
Site web

Re: trigger : mise à jour d'une donnée entre deux tables

Oui, c'est ce que j'ai (peut-être abusivement) supposé en oubliant de l'indiquer. Merci de l'avoir précisé.

Dernière modification par jmarsac (Wed 14 December 2016 19:12)


Jean-Marie
Azimut

Hors ligne

 

#5 Thu 15 December 2016 10:57

legannec
Participant occasionnel
Lieu: Sainte-Marie-Aux-Mines
Date d'inscription: 8 Aug 2011
Messages: 39

Re: trigger : mise à jour d'une donnée entre deux tables

Bonjour et merci pour vos retours !

Malheureusement, il reste un problème :

Erreurs de commit :

Code:

Impossible de valider les changements pour la couche ep_entretien

Erreurs : ERREUR : 1 attribut non-ajouté.
  
Erreur du fournisseur de données :
      Erreur PostGIS lors de l'ajout d'entité : ERREUR:  la relation « ep_support » n'existe pas
    LINE 1: UPDATE ep_support SET date_lampe = NEW.date_intervention
                   ^
    QUERY:  UPDATE ep_support SET date_lampe = NEW.date_intervention
    WHERE ep_support.code_point_lumineux = NEW.code_point_lumineux
    CONTEXT:  fonction PL/pgsql retourne_date(), ligne 4 à instruction SQL

Ce que je n’avais pas précisé, c'est la façon dont est récupéré le code_point_lumineux dans la table ep_entretien : c'est tout simplement un autre trigger basé sur un critère de distance :

Code:

-- Trigger: entretien on ep.ep_entretien

-- DROP TRIGGER entretien ON ep.ep_entretien;

CREATE TRIGGER entretien
  BEFORE INSERT OR UPDATE
  ON ep.ep_entretien
  FOR EACH ROW
  EXECUTE PROCEDURE retourne_code();

-- Function: retourne_code()

-- DROP FUNCTION retourne_code();

CREATE OR REPLACE FUNCTION retourne_code()
  RETURNS trigger AS
$BODY$

BEGIN

select into new.code_point_lumineux ep_support."code_point_lumineux",  st_distance(new.geom, ep_support.geom)
from ep.ep_support
order by 2 
LIMIT 1;
return NEW;
END;

 $BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION retourne_code()
  OWNER TO postgres;

Peut-être que que le problème de relation est lié ? et/ou alors que c'est au niveau du déclenchement du trigger ?...

...des idées ?


legannec, Sigiste à la com'com du Val d'Argent

Hors ligne

 

#6 Thu 15 December 2016 11:13

Ben22
Participant actif
Lieu: 33
Date d'inscription: 11 May 2016
Messages: 95

Re: trigger : mise à jour d'une donnée entre deux tables

peut-être manque t-il l'indication du schéma dans l'update de la fonction ?  :

Code:

Code:

Code:

-- Trigger: date_entretien on ep.ep_entretien

-- DROP TRIGGER date_entretien ON ep.ep_entretien;

CREATE TRIGGER date_entretien
  AFTER INSERT ON ep.ep_entretien
  FOR EACH ROW
  EXECUTE PROCEDURE retourne_date();
  
-- Function: retourne_date()

-- DROP FUNCTION retourne_date();

CREATE OR REPLACE FUNCTION retourne_date() RETURNS trigger AS
$BODY$
BEGIN

UPDATE ep.ep_support SET date_lampe = NEW.date_intervention
WHERE ep_support.code_point_lumineux = NEW.code_point_lumineux;

RETURN new ;
END;

 $BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION retourne_date()
  OWNER TO postgres;

Edit :

Si tu souhaites que seule la dernière date d'intervention soit prise en compte :

Code:

CREATE OR REPLACE FUNCTION retourne_date() RETURNS trigger AS
$BODY$
BEGIN
update ep.ep_support SET date_lampe =(SELECT max(date_intervention)
                                    FROM ep.ep_intervention 
                                    WHERE code_point_lumineux = NEW.code_point_lumineux) As t1
WHERE ep_support.code_point_lumineux = NEW.code_point_lumineux;

RETURN new ;
END;

 $BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;

Dernière modification par Ben22 (Thu 15 December 2016 11:36)

Hors ligne

 

#7 Thu 15 December 2016 11:37

legannec
Participant occasionnel
Lieu: Sainte-Marie-Aux-Mines
Date d'inscription: 8 Aug 2011
Messages: 39

Re: trigger : mise à jour d'une donnée entre deux tables

C'était exactement ça Ben22, le trigger et sa fonction tournent !
Merci encore à vous 3 !


legannec, Sigiste à la com'com du Val d'Argent

Hors ligne

 

#8 Thu 15 December 2016 12:26

jmarsac
Participant assidu
Lieu: NICE
Date d'inscription: 26 Oct 2005
Messages: 566
Site web

Re: trigger : mise à jour d'une donnée entre deux tables

Envisager peut-être de redéfinir la variable [¡]search_path[/¡]


Jean-Marie
Azimut

Hors ligne

 

Pied de page des forums

Powered by FluxBB