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 : Général » [Débutant][8.2] Aide syntaxe Fonction SQL » 01/07/2009 13:31:37

Merci beaucoup pour tous ces éclaircissements.

Bonne journée
lo²

#2 Re : Général » [Débutant][8.2] Aide syntaxe Fonction SQL » 01/07/2009 12:28:41

Ca y est, j'ai le résultat escompté mais faut-il forcément passer par la création d'un type reprenant l'ensemble des champs remontés par la procédure ?

CREATE FUNCTION P0600 (
IN V0 INTEGER
, IN V1 VARCHAR(5)
, IN V2 VARCHAR(5)
, IN V3 VARCHAR(8)
, IN V4 VARCHAR(8)
)
RETURNS setof p0600_t AS
$$
DECLARE 
rec p0600_t%rowtype;
I1 VARCHAR(5000);
begin
I1 := 'SELECT F0600.F0600_00, F0600_01, F0600_02, F0600_03, F0600_04, F0600_05, F0600_06, F0600_08, F0600_11, F0600_12,
F0601.F0601_00, F0601.F0602_00, F0601.F0603_00, F0601.F0606_00, F0600_13, F0600_16, F0600_17, F0600_18, F0600.F0603_00, F0600.F0606_00,
F0600_19, F0600_20, F0600_21, F0600_22, F0600_23, F0600_24
FROM F0600 AS F0600
LEFT OUTER JOIN F0609 AS F0609 ON F0609.F0600_00 = F0600.F0600_00
LEFT OUTER JOIN F0601 AS F0601 ON F0601.F0601_00 = F0609.F0601_00
WHERE F0600.F0001_00 =  ''' || V1 || ''' AND F0600.F0002_00 = ''' || V2 || '''';
IF (V0 = 1) THEN
I1 := I1 || ' AND ((F0601_03 >= ' || V3 || ' AND F0601_03 < ' || V4 || ')
AND F0601.F0601_00 IS NOT NULL AND F0601.F0602_00 IS NOT NULL AND F0601.F0603_00 IS NOT NULL AND F0601.F0606_00 IS NOT NULL)';
ELSE
I1 := I1 || ' AND (F0601.F0601_00 IS NULL OR F0601.F0602_00 IS NULL OR F0601.F0603_00 IS NULL OR F0601.F0606_00 IS NULL)';
END IF;
FOR rec IN EXECUTE I1
LOOP
RETURN NEXT rec;
END LOOP; 
END;
$$
LANGUAGE 'plpgsql';

#3 Re : Général » [Débutant][8.2] Aide syntaxe Fonction SQL » 01/07/2009 12:11:40

En effet, ça passe beaucoup mieux.

Par contre, le résultat me donne un <unnamed portal 1>.
Quelle est la modification à apporter dans ma fonction pour un avoir le même résultat qu'une requête exécutée simplement ?

#4 Re : Général » [Débutant][8.2] Aide syntaxe Fonction SQL » 01/07/2009 11:25:55

rooh l'erreur de newbie ^^ et merci pour la précision à propos des limites d'utilisation de SQL.

Maintenant j'aimerai récupérer l'ensemble des enregistrements retournée par la procédure avec un :

select P0600(0, '00000', '00000', '20090601', '20090630');

mais voici le message d'erreur qui en résulte :

ERROR:  function p0600(integer, unknown, unknown, unknown, unknown) does not exist at character 8
HINT:  No function matches the given name and argument types. You might need to add explicit type casts.

Visiblement, il semblerait que cela provienne des paramètres de la procédure qui sont en CHARACTER et convertis en BPCHAR une fois créée dans la base.

#5 Re : Général » [Débutant][8.2] Aide syntaxe Fonction SQL » 01/07/2009 11:00:21

Visiblement tout le monde parle en plpgsql et en grattant un peu plus, il se pourrait qu'il n'y ait pas tant de modifs à apporter que ça.

Voici le code en pgplsql :

CREATE FUNCTION P0600 (
IN V0 SMALLINT
, IN V1 CHARACTER(5)
, IN V2 CHARACTER(5)
, IN V3 CHARACTER(8)
, IN V4 CHARACTER(8)
)
RETURNS refcursor AS
$$
DECLARE 
rec refcursor;
I1 VARCHAR(5000);
begin
I1 := 'SELECT F0600.F0600_00, F0600_01, F0600_02, F0600_03, F0600_04, F0600_05, F0600_06, F0600_08, F0600_11, F0600_12,
F0601.F0601_00, F0601.F0602_00, F0601.F0603_00, F0601.F0606_00, F0600_13, F0600_16, F0600_17, F0600_18, F0600.F0603_00, F0600.F0606_00,
F0600_19, F0600_20, F0600_21, F0600_22, F0600_23, F0600_24
FROM F0600 AS F0600
LEFT OUTER JOIN F0609 AS F0609 ON F0609.F0600_00 = F0600.F0600_00
LEFT OUTER JOIN F0601 AS F0601 ON F0601.F0601_00 = F0609.F0601_00
WHERE F0600.F0001_00 =  ''' || V1 || ''' AND F0600.F0002_00 = ''' || V2 || '''';
IF (V0 = 1) THEN
I1 := I1 || ' AND ((F0601_03 >= ' || V3 || ' AND F0601_03 < ' || V4 || ')
AND F0601.F0601_00 IS NOT NULL AND F0601.F0602_00 IS NOT NULL AND F0601.F0603_00 IS NOT NULL AND F0601.F0606_00 IS NOT NULL)';
ELSE
I1 := I1 || ' AND (F0601.F0601_00 IS NULL OR F0601.F0602_00 IS NULL OR F0601.F0603_00 IS NULL OR F0601.F0606_00 IS NULL)';
END IF;
OPEN ref FOR EXECUTE I1;
RETURN ref;
END;
$$
LANGUAGE 'plpgsql';

et le message d'erreur (au niveau de OPEN ref):

ERROR:  syntax error at or near "ref" at character 1105

#6 Re : Général » [Débutant][8.2] Aide syntaxe Fonction SQL » 01/07/2009 10:49:21

Merci pour cette réponse rapide.

La procédure qui est en exemple provient d'un projet existant qui tourne sur Iseries. Il existe une trentaine de procédures stockées.
J'ai regardé la syntaxe du langage plpgsql mais je trouvais qu'il y avait pas mal de diiférence dans la syntaxe, dans le sens où j'aimerais que lors de la mise en place du projet, le code de création de base (tables, procedures...) soit le plus uniforme possible.

Est-il possible en utilisant la syntaxe SQL d'arriver à ce type de procédure ou faut-il obligatoirement passer par plpgsql ?

#7 Général » [Débutant][8.2] Aide syntaxe Fonction SQL » 01/07/2009 10:37:18

lo²
Réponses : 12

Bonjour à tous,

Je me trouve devant un problème de syntaxe sur ma création de procédure. Visiblement, le problème viendrait du DECLARE non reconnu en LANGUAGE SQL mais ça me surprend.

Voici le code :

CREATE FUNCTION P0600 (
IN V0 SMALLINT
, IN V1 CHAR(5)
, IN V2 CHAR(5)
, IN V3 CHAR(8)
, IN V4 CHAR(8)
) RETURNS refcursor as
$$
DECLARE 
ref refcursor;
I1 VARCHAR(5000);
BEGIN
SET I1 = 'SELECT F0600.F0600_00, F0600_01, F0600_02, F0600_03, F0600_04, F0600_05, F0600_06, F0600_08, F0600_11, F0600_12,
	F0601.F0601_00, F0601.F0602_00, F0601.F0603_00, F0601.F0606_00, F0600_13, F0600_16, F0600_17, F0600_18, F0600.F0603_00, F0600.F0606_00,
	F0600_19, F0600_20, F0600_21, F0600_22, F0600_23, F0600_24
	FROM F0600 AS F0600
	LEFT OUTER JOIN F0609 AS F0609 ON F0609.F0600_00 = F0600.F0600_00
	LEFT OUTER JOIN F0601 AS F0601 ON F0601.F0601_00 = F0609.F0601_00
	WHERE F0600.F0001_00 =  ''' || V1 || ''' AND F0600.F0002_00 = ''' || V2 || '''';
IF V0 = 1 THEN 
	SET I1 = I1 || ' AND ((F0601_03 >= ' || V3 || ' AND F0601_03 < ' || V4 || ')
	AND F0601.F0601_00 IS NOT NULL AND F0601.F0602_00 IS NOT NULL AND F0601.F0603_00 IS NOT NULL AND F0601.F0606_00 IS NOT NULL)';
ELSE
	SET I1 = I1 || ' AND (F0601.F0601_00 IS NULL OR F0601.F0602_00 IS NULL OR F0601.F0603_00 IS NULL OR F0601.F0606_00 IS NULL)';
END IF;
OPEN ref FOR I1;
RETURN ref;
END;
$$
LANGUAGE 'SQL';

Voici le message d'erreur :

ERROR:  syntax error at or near "refcursor" at character 152

Merci pour votre aide

Pied de page des forums

Propulsé par FluxBB