PostgreSQL La base de donnees la plus sophistiquee au monde.

Forums PostgreSQL.fr

Le forum officiel de la communauté francophone de PostgreSQL

Vous n'êtes pas identifié(e).

#1 Re : Sécurité » Droit refusé sur une vue » 08/06/2020 16:43:25

Ok.
Merci, c'est une bonne idée.
J'en prends note et essayerai de faire le nécessaire.

#2 Re : Sécurité » Droit refusé sur une vue » 08/06/2020 16:15:51

Marc Cousin a écrit :

il faut que l'utilisateur propriétaire de la fonction trigger soit autorisé à manipuler les tables en dessous,

Ok smanetagis est propriétaire de la fonction res_eau_vanne_vue_edit() et a tous les droits sur les tables res_noeud et res_ea_noeud_vanne.

Marc Cousin a écrit :

mais pas l'utliisateur qui travaille sur les vues

Ok grp_aep_admin n'a aucun droit sur les tables res_noeud et res_ea_noeud_vanne.

Marc Cousin a écrit :

Lui devrait juste avoir des droits sur la vue

Ok grp_aep_admin a les droits insert, select, update et delete sur la vue.

Marc Cousin a écrit :

Ça ne marche pas ?

Si, j'ai l'impression que ça fonctionne. L'erreur que j'avais faite est de donner des droits à l'utilisateur sur les deux tables.
Merci beaucoup !

#3 Re : Sécurité » Droit refusé sur une vue » 08/06/2020 15:00:10

C'est nickel pour session_user.
Malheureusement, je crois que dans mon post précédent je me suis un peu enflammé.
En effet, le security definer fonctionne mais je suis pas sûre que c'est ce que je souhaitais. En relisant mon premier post je crois que je n'étais pas assez précis.
En fait, je souhaite que les utilisateurs ayant les droits puissent uniquement insert, update et delete la donnée via la vue et pas directement dans les tables sous-jacentes (res_noeud et res_ea_noeud_vanne). Ces dernières sont filtrées et conditionnées en fonction des métiers des utilisateurs.
En résumer, je veux que le user puisse insert, update et delete depuis la vue et pas depuis les tables sous-jacentes.

Mais là je crois que j'en demande un peu trop ...

#4 Re : Sécurité » Droit refusé sur une vue » 08/06/2020 13:45:15

Ok j'avance.
J'ai du rajouter "public" pour le search_path parce qu'il y avait d'autres déclencheurs sur une table sous-jacente.
Le groupe grp_aep_admin est bien propriétaire de la vue et ça fonctionne comme je le souhaite … enfin presque !
En effet, en disant de mettre USER dans le champs user_postgis j'espérais pouvoir identifier le créateur de la donnée et/ou le modificateur. Avec cette sécurité c'est le groupe qui est le USER.
Avez vous un moyen de contourner ce problème et de connaitre quel utilisateur du groupe à fait la création/modifiaction ?

#5 Re : Sécurité » Droit refusé sur une vue » 08/06/2020 09:46:38

La doc dit :"Pour des raisons de sécurité, search_path doit être configuré pour exclure les schémas modifiables par des utilisateurs indignes de confiance."

CREATE FUNCTION verifie_motdepasse(unom TEXT, motpasse TEXT)
RETURNS BOOLEAN AS $$
DECLARE ok BOOLEAN;
BEGIN
        -- Effectuer le travail sécurisé de la fonction.
        SELECT  (motdepasse = $2) INTO ok
        FROM    motsdepasse
        WHERE   nomutilisateur = $1;

        RETURN ok;
END;
$$  LANGUAGE plpgsql
    SECURITY DEFINER
    -- Configure un search_path sécurisée : les schémas de confiance, puis 'pg_temp'.
    SET search_path = admin, pg_temp;

BEGIN;
CREATE FUNCTION verifie_motdepasse(unom TEXT, motpasse TEXT) ... SECURITY DEFINER;
REVOKE ALL ON FUNCTION verifie_motdepasse(unom TEXT, motpasse TEXT) FROM PUBLIC;
GRANT EXECUTE ON FUNCTION verifie_motdepasse(unom TEXT, motpasse TEXT) TO admins;
COMMIT;

#6 Re : Sécurité » Droit refusé sur une vue » 08/06/2020 09:25:18

Bonjour Marc et merci pour votre réponse.
Je me suis penché sur cette fonctionnalité SECURITY DEFINER mais je vous avoue que cela me dépasse un peu.
J'ai lu la doc mais je comprends pas à quel moment il faut définir le SECURITY DEFINER.
Le fait de devoir configurer search_path me déstabilise aussi. J'utilise le schéma PUBLIC donc celui-ci est parcouru un premier, non ?
Pourriez vous s'il vous plait m'indiquer les emplacements et la définition de ces paramètres dans mon script ?
Merci d'avance,
Vincent

#7 Sécurité » Droit refusé sur une vue » 05/06/2020 16:30:59

Vinz67
Réponses : 13

Bonjour,

J'utilise Postrgre/Postgis avec QGis pour lire la donnée géographique.

J'ai créé une vue modifiable avec deux tables sous-jacentes.
Je suis propriétaire des tables et de la vue.
J'ai donné les droits select, update, insert et delete à un groupe d'utilisateur pour la vue.

Lorsque j'utilise mon compte tout se passe comme je le souhaite. Par contre lorsque j'utilise le compte utilisateur le message suivant s'affiche ; "Erreur PostGIS lors de l'ajout d'entité : ERREUR:  droit refusé pour la relation res_noeud".
Dans la doc j'ai bien vu que : "Notez que l'utilisateur réalisant l'insertion, la mise à jour ou la suppression sur la vue doit avoir les droits correspondants sur la vue. De plus, le propriétaire de la vue doit avoir les droits correspondants sur les relations sous-jacentes mais l'utilisateur réalisant la mise à jour n'a pas besoin de droits sur les relations sous-jacentes."

J'ai besoin d'aide, svp.
Je vous joins mon script SQL pour la création de la vue, de la fonction et du trigger.

 -- View: public.vue_res_eau_vanne

DROP VIEW public.vue_res_eau_vanne CASCADE;

CREATE OR REPLACE VIEW public.vue_res_eau_vanne
WITH (security_barrier=false)
 AS
 SELECT res_noeud.id_noeud,
	res_noeud.the_geom,
    res_ea_noeud_vanne.numero,
    res_ea_noeud_vanne.type,
    res_ea_noeud_vanne.code_insee,
    res_ea_noeud_vanne.adresse,
    res_ea_noeud_vanne.reseau,
    res_ea_noeud_vanne.reseau_type,
    res_ea_noeud_vanne.diametre,
    res_ea_noeud_vanne.materiau,
    res_ea_noeud_vanne.nbre_tours,
    res_ea_noeud_vanne.sens,
    res_ea_noeud_vanne.etat_normal,
    res_ea_noeud_vanne.implantation,
    res_ea_noeud_vanne.annee_pose,
    res_ea_noeud_vanne.date_controle,
    res_ea_noeud_vanne.commentaire,
    res_noeud.angle_lib
   FROM  res_noeud
   JOIN res_ea_noeud_vanne ON res_noeud.id_noeud = res_ea_noeud_vanne.id_noeud_vanne
  WHERE res_noeud.id_reseau = 5 AND res_noeud.type_noeud = 203 AND res_noeud.date_suppression IS NULL;

ALTER VIEW public.vue_res_eau_vanne
    OWNER TO smanetagis;

GRANT ALL ON TABLE public.vue_res_eau_vanne TO smanetagis;
GRANT INSERT, SELECT, UPDATE, DELETE ON TABLE public.vue_res_eau_vanne TO grp_aep_admin;



-- Crée la fonction utilisée par le déclencheur pour rendre modifiable la vue 
--DROP FUNCTION res_eau_vanne_vue_edit() CASCADE;

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

BEGIN	

    IF TG_OP = 'INSERT' THEN
        INSERT INTO public.res_noeud (
									  type_noeud,
									  id_reseau, 
									  the_geom, 
									  angle, 
									  angle_lib, 
									  date_creation, 
									  user_postgis) 
               					 VALUES (
									     203,
									 	 5, 
										 NEW.the_geom,  
										 180-NEW.angle_lib, 
										 NEW.angle_lib, 
										 CURRENT_TIMESTAMP, 
										 USER);
		INSERT INTO res_ea_noeud_vanne (id_noeud_vanne, 
										numero, 
										type, 
										code_insee, 
										adresse, 
										reseau, 
										reseau_type, 
										diametre, 
										materiau, 
										nbre_tours, 
										sens, 
										etat_normal, 
										implantation, 
										annee_pose, 
										date_controle, 
										commentaire)
								VALUES  (currval('res_noeud_id_noeud_seq'::regclass), 
										 new.numero, 
										 new.type, 
										 new.code_insee,
										 new.adresse, 
										 new.reseau, 
										 new.reseau_type, 
										 new.diametre, 
										 new.materiau, 
										 new.nbre_tours,
										 new.sens, 
										 new.etat_normal,
										 new.implantation,
										 new.annee_pose, 
										 new.date_controle,
										 new.commentaire);
        RETURN NEW;
	
    ELSIF TG_OP = 'UPDATE' THEN
		UPDATE public.res_noeud 
								SET the_geom = new.the_geom, 
								angle = 180-NEW.angle_lib, 
								angle_lib = new.angle_lib, 
								date_modification = CURRENT_TIMESTAMP, 
								user_postgis = USER
  					WHERE old.id_noeud = res_noeud.id_noeud;
					
		UPDATE public.res_ea_noeud_vanne 
								SET numero = new.numero, 
								type = new.type, 
								code_insee = new.code_insee, 
								adresse = new.adresse, 
								reseau = new.reseau, 
								reseau_type = new.reseau_type, 
								diametre = new.diametre, 
								materiau = new.materiau, 
								nbre_tours = new.nbre_tours, 
								sens = new.sens, 
								etat_normal = new.etat_normal, 
								implantation = new.implantation, 
								annee_pose = new.annee_pose, 
								date_controle = new.date_controle, 
								commentaire = new.commentaire
  					WHERE  res_ea_noeud_vanne.id_noeud_vanne = old.id_noeud ;
        RETURN NEW;
		
    ELSIF TG_OP = 'DELETE' THEN
        DELETE FROM public.res_noeud WHERE  old.id_noeud = res_noeud.id_noeud;
        DELETE FROM public.res_ea_noeud_vanne WHERE  res_ea_noeud_vanne.id_noeud_vanne = old.id_noeud ;
        RETURN NULL;
    END IF;
END
$BODY$
LANGUAGE plpgsql;

-- Crée le déclencheur qui rend modifiable la vue.
-- Une vue utilisant plusieurs tables n'est pas directement modifiable.
-- Il est donc obligatoire de créer ce déclencheur pour rendre ce type de vue modifiable. 

--DROP TRIGGER res_eau_vanne_vue_edit_trig ON public.vue_res_eau_vanne;
CREATE TRIGGER res_eau_vanne_vue_trig
INSTEAD OF INSERT OR UPDATE OR DELETE 
ON public.vue_res_eau_vanne
FOR EACH ROW 
EXECUTE PROCEDURE res_eau_vanne_vue_edit(); 

Pied de page des forums

Propulsé par FluxBB