DB Express - Primary key d' une table

Signaler
Messages postés
2106
Date d'inscription
mardi 10 décembre 2002
Statut
Modérateur
Dernière intervention
15 décembre 2014
-
Messages postés
1284
Date d'inscription
mardi 28 octobre 2003
Statut
Contributeur
Dernière intervention
3 juillet 2015
-
Salut,

je suis en train de modifier mes compos (partie DB Express) afin de pouvoir gérer plusieurs types de bases de données.

Je suis actuellement en train de réecrire la fonction suivante qui me renvoie la primary key d' une table:

function SQLGetPrimaryKey(aConnection: TSQLConnection; aTableName: String): String;
var
  aQuery: TSQLQuery;
  Column_name: String;
begin
  Result :=  '';
  if aTableName = '' then Exit;

  aQuery := TSQLQuery.Create(Nil);
  aQuery.SQLConnection := aConnection;

  case GetDbxConnectionDriver(aConnection) of
    cdASA: ;

    cdASE: ;

    cdBlackfishSQL: ;

    cdDatasnap: ;

    cdDb2: ;

    cdInformix: ;

    cdInterbase: ;

    cdMSSQL:
      begin
        aQuery.SQL.Clear;
        aQuery.SQL.Add('SELECT i.name AS IndexName,');
        aQuery.SQL.Add('COL_NAME(ic.OBJECT_ID,ic.column_id) AS column_name');
        aQuery.SQL.Add('FROM sys.indexes AS i');
        aQuery.SQL.Add('INNER JOIN sys.index_columns AS ic');
        aQuery.SQL.Add('ON i.OBJECT_ID = ic.OBJECT_ID');
        aQuery.SQL.Add('AND i.index_id = ic.index_id');
        aQuery.SQL.Add('WHERE (i.is_primary_key = 1) and (OBJECT_NAME(ic.OBJECT_ID) LIKE ' + SQLGetStringExpr(aTableName) + ')');
        Column_name := 'column_name';
      end;

    cdMySQL:
      begin
        aQuery.SQL.Text :'show index from ' + cyDBX.BackQuotedStr(aTableName) + ' where Key_name ''PRIMARY''';
        Column_name := 'column_name';
      end;

    cdOracle: ;
  end;



  aQuery.Active := true;
  if not aQuery.Eof then
    Result := aQuery.FieldByName(Column_name).AsString;

  aQuery.Active := false;
  aQuery.Free;
end;



Comme vous pouvez le voir, je ne gère que MySQL et MS SQL.
Ce que je voudrai est, dans le cas oú vous pouvez tester , me donner le code pour la autres base de données.

Merci,
Mauricio


Composants Cindy pour Delphi
=257958 Faites une donation.

6 réponses

Messages postés
1284
Date d'inscription
mardi 28 octobre 2003
Statut
Contributeur
Dernière intervention
3 juillet 2015
13
Salut Mauricio !

Pas vu Firebird dans ta liste... Je te mets la requête quand même (avec le paramètre P_TableName pour la table à cibler) :

Select t1.RDB$FIELD_NAME as column_name
From RDB$INDEX_SEGMENTS t1
Inner Join RDB$INDICES t2
On t1.RDB$INDEX_NAME = t2.RDB$INDEX_NAME
Inner join RDB$RELATION_CONSTRAINTS t3
on t2.RDB$RELATION_NAME = t3.RDB$RELATION_NAME
Where t2.RDB$RELATION_NAME = :P_TableName
and t3.RDB$CONSTRAINT_TYPE = 'PRIMARY KEY'
ORDER BY t1.RDB$FIELD_POSITION

Je vois que tu mets aussi Datasnap. J'avais cru comprendre que ce n'était qu'un moyen de développer des applis Client/Serveur... C'est aussi un format de base de données ?
Messages postés
2106
Date d'inscription
mardi 10 décembre 2002
Statut
Modérateur
Dernière intervention
15 décembre 2014
5
Salut Simon,

en effet, il manque fireBird.
En fait, j' ai pris la liste des connexions possibles avec le compo TSQLConnection (DB Express).

Ne pouvant pas tester toutes les solutions, peux tu stp écrire la partie FireBird, la tester puis me l' envoyer?

Merci,

a+
Messages postés
1284
Date d'inscription
mardi 28 octobre 2003
Statut
Contributeur
Dernière intervention
3 juillet 2015
13
Oulààà !!! Mais heureusement que Firebird est dispo sur le TSQLConnection... Je teste ça, pas de souci (la requête était testée)
Par contre, je ne comprends pas bien le retour attendu...
 if not aQuery.Eof then
Result := aQuery.FieldByName(Column_name).AsString;

Si tu as une table avec deux champs dans une clé primaire, quel est le retour de la fonction ? Un seul champ dans la clé primaire ?
Messages postés
2106
Date d'inscription
mardi 10 décembre 2002
Statut
Modérateur
Dernière intervention
15 décembre 2014
5
En fait,

la fonction renvoie le nom de la clé primaire ...

a+

Messages postés
1284
Date d'inscription
mardi 28 octobre 2003
Statut
Contributeur
Dernière intervention
3 juillet 2015
13
Ok, je croyais que tu voulais les noms des champs de la clé... Dans ce cas, pour firebird :
cdFirebird :
begin
   aQuery.SQL.Add('Select t1.RDB$INDEX_NAME as column_name');
   aQuery.SQL.Add('From RDB$INDICES t1');
   aQuery.SQL.Add('Inner join RDB$RELATION_CONSTRAINTS t2');
   aQuery.SQL.Add('on (t1.RDB$RELATION_NAME = t2.RDB$RELATION_NAME AND t1.RDB$INDEX_NAME = t2.RDB$INDEX_NAME)');
   aQuery.SQL.Add('Where t1.RDB$RELATION_NAME = '+ cyDBX.BackQuotedStr(aTableName));
   aQuery.SQL.Add('and t2.RDB$CONSTRAINT_TYPE = ''PRIMARY KEY''');
end;


et pour "update" pour les champs de la clé primaire (la précédente fonctionne aussi, mais celle ci est plus propre...) :

Select t1.RDB$FIELD_NAME as column_name
From RDB$INDEX_SEGMENTS t1
Inner Join RDB$INDICES t2
On t1.RDB$INDEX_NAME = t2.RDB$INDEX_NAME
Inner join RDB$RELATION_CONSTRAINTS t3
on (t2.RDB$RELATION_NAME = t3.RDB$RELATION_NAME AND t2.RDB$INDEX_NAME = t3.RDB$INDEX_NAME)
Where t2.RDB$RELATION_NAME = :P_TableName
and t3.RDB$CONSTRAINT_TYPE = 'PRIMARY KEY'
ORDER BY t1.RDB$FIELD_POSITION



Pour Interbase, ça ne doit pas être très différent. Je ne l'ai malheureusement pas installé sur mon poste car ça ne cohabite pas terriblement bien avec Firebird...

Messages postés
2106
Date d'inscription
mardi 10 décembre 2002
Statut
Modérateur
Dernière intervention
15 décembre 2014
5
Merci Simonpelloquin
Messages postés
1284
Date d'inscription
mardi 28 octobre 2003
Statut
Contributeur
Dernière intervention
3 juillet 2015
13
Mais avec plaisir ! ;-)