Cette erreur "Impossible d'activer les contraintes. Une ou plusieurs lignes contiennent des valeurs qui violent les contraintes de type non null, unique ou de clé externe" peut être rencontrée dans les grilles personnalisées ou dans les reportings vers fenêtres.
A ces endroits du programme, Mercator extrait les données demandées en demandant que le schéma de la base de données soit inclus. Cela permet à Mercator de connaître les définitions de colonnes de type caractères - char(x) - et de déduire à partir de x une largeur de colonne par défaut dans la grille. Ce schéma contient aussi la définition des clés primaires.
Pour contourner le problème, il suffit en général de modifier quelque peu la requête.
Par exemple, cette requête produit cette erreur :
select cli.c_id,cli.c_nom,pieds_v.journal,pieds_v.piece,stock.s_id,stock.s_modele,lignes_v.q,sum(dispo.dispo) as dispo
from lignes_v inner join pieds_v on (pieds_v.id=lignes_v.id) and (pieds_v.journal=lignes_v.journal) and (pieds_v.piece=lignes_v.piece)
inner join cli on (pieds_v.id_cli=cli.c_id)
inner join stock on (lignes_v.id_article=stock.s_id)
inner join dispo on (dispo.id_stock=stock.s_id)
where type=3
group by cli.c_id,cli.c_nom,pieds_v.journal,pieds_v.piece,stock.s_id,stock.s_modele,lignes_v.q
Car le schéma impose que C_ID et S_ID soient uniques, puisqu'ils sont la clé primaire de leur table respective. Or cette requête ramène plusieurs lignes avec le même C_ID et/ou avec le même S_ID.
Dans ce cas, il suffit de remplacer : (ces égalités sont trouvées dans les jointures)
- cli.c_id par pieds_v.id_cli
- stock.s_id par lignes_v.id_article
select pieds_v.id_cli,cli.c_nom,pieds_v.journal,pieds_v.piece,lignes_v.id_article,stock.s_modele,lignes_v.q,sum(dispo.dispo) as dispo
from lignes_v inner join pieds_v on (pieds_v.id=lignes_v.id) and (pieds_v.journal=lignes_v.journal) and (pieds_v.piece=lignes_v.piece)
inner join cli on (pieds_v.id_cli=cli.c_id)
inner join stock on (lignes_v.id_article=stock.s_id)
inner join dispo on (dispo.id_stock=stock.s_id)
where type=3
group by pieds_v.id_cli,cli.c_nom,pieds_v.journal,pieds_v.piece,lignes_v.id_article,stock.s_modele,lignes_v.q
Autre exemple
Cette requête renvoie plusieurs lignes identiques.
select fou.f_id, fou.d_nom
from FOU
where exists(select * from CLI where (cli.C_ID_FOU=fou.F_ID) and (cli.C_ID_FOU=@C_ID_FOU))
Dans ce cas, il suffit d'ajouter distinct.
select distinct fou.f_id, fou.d_nom
from FOU
where exists(select * from CLI where (cli.C_ID_FOU=fou.F_ID) and (cli.C_ID_FOU=@C_ID_FOU))