Je viens solliciter votre aide car après mainte recherche je reste bloqué.
Mon but ?
Créer un JTree en java qui reprendrai la structure de ma base de données.
Ensuite celui-ci me servira à ajouter des champs dans un JTextArea pour élaborer une requête SQL sur ma base Oracle.
Voila un screenshot de Eclipse Birt qui affiche parfaitement ce que je veux :
J’ai bien réussi à récupérer la liste des tables via l’objet “DatabaseMetaData” et la méthode “getTables” mais je ne vois pas comment récupérer
la liste des champs et les ajouter à mon JTree.
Et bien j’ai tester avec le code du lien et c’est long… très très long.
Du coup je cherche depuis hier une autre méthode et je pense avoir trouver.
Je vous montres le code histoire d’aider ceux qui en ont besoin. N’hésitez pas si vous voyez des soucis :jap:
[spoiler]
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
import oracle.jdbc.pool.OracleDataSource;
public class Test {
public static void main(String[] args) {
Connection connection = null;
String url = "mon_url";
String user = "user";
String pass = "pass";
try {
OracleDataSource ods = new OracleDataSource();
ods.setURL(url);
ods.setUser(user);
ods.setPassword(pass);
connection = ods.getConnection();
DatabaseMetaData dmd = connection.getMetaData(); // Recupération des informations de la BDD
String[] type = {"TABLE"}; // Je ne souhaite afficher que les TABLES
ResultSet rset = dmd.getTables(null, user, "%", type);
while(rset.next()) {
System.out.println(rset.getString("TABLE_NAME")); // Affichage du nom de la Table
/**
* Je fait une requête sur la Table et je ne récupère qu'une Ligne
* Le rownum remplace le mot clé LIMIT pour Oracle
*/
String query = "Select * from " + rset.getString("TABLE_NAME") + " where rownum < 2";
Statement stmt = connection.createStatement();
ResultSet rset2 = stmt.executeQuery(query);
while(rset2.next()) {
ResultSetMetaData rset3 = rset2.getMetaData(); // Récupération des informations de la requête
int nbCol = rset3.getColumnCount(); // Je compte le nombre de colonne
for (int i = 1; i <= nbCol; i++) {
String nomCol = rset3.getColumnName(i);
String typCol = "(" + rset3.getColumnTypeName(i) + ")";
System.out.println("\t" + nomCol + typCol);
}
}
stmt.close();
rset2.close();
}
rset.close();
connection.close();
} catch (SQLException sql) {
sql.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}
}
En attendant ça fonctionne et comme j’ai pas trouver d’exemple ni de bonne âme apte à m’aider je me suis débrouiller
Si tu as mieux, je suis prenneur :jap:
Ben en exécutant des requêtes comme si tu interrogeait directement ta base. Surtout que si je ne me trompe pas, il y a une table de description des tables dans Oracle. Ca doit faire un truc du genre :
SELECT column_name FROM user_tab_columns WHERE table_name=?;
sachant que tu a récupéré les noms de table. C’est ni portable ni objet, mais si tu a des problèmes de perfs, là tu saura a moins que c’est un problème de base.
Je ne vais pas représenter toute la théorie du découpage logiciel en couches, mais ta classe d’accès aux données (DAO) ne doit contenir qu’une interrogation de la base et un retour “abstrait”. Ce peut être une grappe d’objets décrivant ta structure du type :
MaBase-(1)—()-Tables-(1)—()-Colonnes
C’est au niveau de la présentation que tu va mapper cette grappe sur ton JTree.
L’intérêt est que tu aura comme ça une classe de présentation réutilisable indépendamment de la base de données (il faudra coder une Dao adaptée) et ta classe d’exploration de la base n’est plus uniquement liée à une présentation que tu pourra réutiliser dans d’autres contextes, ta méthode devenant “getDatabaseDescription()”
Je viens de tester de cette manière et niveau temps c’est kiff kiff. J’y avais penser, d’ailleurs le morceau de code est toujours sur un bout de papier à côté de moi, mais je pensai qu’utiliser la méthode “getMetaData” était plus “propre”. Cela dit, je ne connaissais pas la table “user_tab_columns”, merci :jap:
Je vois bien ce que tu veux dire en ce qui concerne le portage mais pour l’instant je vois mal comment dissocié : Interrogation de la base et Construction du JTree.
L’intérêt de mon projet étant, pour l’instant de disposer d’un outil simple de requêtage sur notre base de données (comme on le fait actuellement sur notre AS400)
Enfin, je vais me pencher sur tout ça, sachant que j’ai commencer le Java il y à 2 mois
Je n’ai jamais eu à faire de l’exploration de base en Java, donc j’admets ne pas m’être trop intéressé au sujet, mais comme je te l’ai dit : utiliser ta getMetaData est plus générique et donc tu pourrait réutiliser ce que tu a codé pour d’autres bases. Le problème dans la conception ici est de bien faire la part entre les bénéfices/déficites de la généricité ou de la spécialisation.
C’est une certaine difficulté… Ok vu la remarque suivante…
Arf… Donc 2 mois d’objet, je vais éviter de parler de patterns de conception, tout ça tout ça…
Bon, note ce que je t’ai dit, et repense y quand tu aura cerné un peu la conception Objet. Évidemment, n’hésite pas à reposer une question.
J’ai lu le tuto du Site du Zéro concernant les patterns (MVC, etc…), mais c’est encore assez complexe pour moi et comme " j’étudie " du boulot je n’ai pas forcément la concentration nécessaire pour comprendre ce concept.
Autant l’apprentissage du Java en lui même m’a paru simple, autant cette notion est d’un niveau assez supérieur.
Une fois que j’aurai fini mon projet, c’est à dire d’ici peu, j’essayerai de le mettre aux normes.
Oui oui, ce n’est plus boxer dans la même catégorie. Après, Java est simple à prendre en main, mais pas forcément facile à utiliser correctement (la question piège classique : tu est sûr d’avoir compris le principe des Interfaces, hein ). Si tu n’en a pas déclaré une seule dans ton projet, alors tu a compris la syntaxe de java, mais pas la conception objet. Ce n’est pas une critique mais un repère