IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

JDBC Java Discussion :

Centraliser les accès à la base de données


Sujet :

JDBC Java

  1. #1
    Rédacteur
    Avatar de romaintaz
    Homme Profil pro
    Java craftsman
    Inscrit en
    juillet 2005
    Messages
    3 790
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Java craftsman
    Secteur : Finance

    Informations forums :
    Inscription : juillet 2005
    Messages : 3 790
    Points : 7 702
    Points
    7 702
    Par défaut Centraliser les accès à la base de données
    Bonjour à tous,

    Je cherche le meilleur moyen de centraliser mes accès à une base de données. En gros, mon application possède un nombre important de classes (une vingtaine) qui font des requêtes directement à ma base de données.
    Je compte changer tout cela de façon à ce qu'il n'y ait plus qu'un seul point d'accès vers ma base de données.

    J'avais imaginé une solution, mais j'aimerais que vous me disiez si je suis sur la bonne voie, ou s'il y a de meilleures façons de faire (sans pour autant écrire quelque chose de trop complexe) :

    Je crée une classe DatabaseAccess, qui est un singleton. Son rôle est d'initialiser les accès à la base de données. Cette classe serait donc la seule à avoir accès au pool de connections. Une fois cette initialisation réalisée, elle crée un Thread dont la tâche principale est d'exécuter la requête SQL. Ainsi, je peux réaliser plusieurs requêtes en parallèle, sans problème.
    Du coup, si une classe désire faire une requête SQL, elle fait appel à mon singleton DatabaseAccess, qui se chargera de tout. Par exemple, j'imagine que je pourrais avoir quelque chose comme ça pour l'appel depuis cette classe :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
    try {
      String maRequete = "SELECT blabla...";
      ResultSet monResultSet = null;
      DatabaseAccess.getInstance().executeSelect(maRequete, monResultSet);
      while (monResultSet == null) {
        // Attente du resultat.
        Thread.sleep(100);
      }
      // Code de traitement du resultset.
      ...
    } catch (Exception e) {
      // Si erreur lors de l'execution.
      ...
    }
    C'est une idée comme ça, qui me parait à peu près propre et pas franchement complexe à coder. Qu'en pensez-vous ?

    Merci pour votre aide.
    Nous sommes tous semblables, alors acceptons nos différences !
    --------------------------------------------------------------
    Liens : Blog | Page DVP | Twitter
    Articles : Hudson | Sonar | Outils de builds Java Maven 3 | Play! 1 | TeamCity| CitConf 2009
    Critiques : Apache Maven

  2. #2
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : avril 2002
    Messages : 13 938
    Points : 23 015
    Points
    23 015
    Billets dans le blog
    1
    Par défaut Re: Centraliser les accès à la base de données
    Salut,


    Quelques remarques :


    • Si le traitement doit être effectué dans un Thread, pourquoi attendre que ce thread soit terminé pour continuer ? --> Tu n'as pas besoin de faire le traitement dans un Thread séparé...
    • La référence monResultSet que tu passes en paramètre à ta méthode ne sera jamais modifié dans la méthode appellante, et ta boucle d'attente sera infini...
    • Je ne vois pas le code pour la libération des ressources (close() sur Connection/Statement/Resultset). Est-ce un oubli ?
    • Tu traite toi-même ton ResultSet dans une boucle while(). Du coup en quoi est-ce différent d'une requête directe ? (il suffit de remplacer l'appel à executeSelect() par la création et l'exécution du Statement pour revenir au code précédent ou presque).




    Perso je te conseilles l'API DbUtils de Jakarta, et donc de jeter un coup d'oeil au tutoriel de Christophe Jollivet : Simplifiez vous JDBC avec Jakarta Commons DbUtils, où alors d'attendre Java 6.0 qui intègrera un système similaire grâce aux annotations...

    a++

  3. #3
    Membre confirmé
    Profil pro
    Inscrit en
    avril 2003
    Messages
    509
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : avril 2003
    Messages : 509
    Points : 568
    Points
    568
    Par défaut
    Salut,
    Effectivement centraliser l'acces a une base me semble etre une bonne idée ,
    Tu peux faire de ton DatabaseAccess une interface pour eviter un couplage trop fort.
    Ce qui me gene c'est la creation d'un thread pour executer la requete , en generale ce genre de traitement doit etre synchrone , d'ailleurs tu fais attendre le thread principale le temps que le thread s'execute , autant eviter les thread dans ces conditions !!
    Enfin c'est mon avis !!
    UML avec VIOLET

  4. #4
    Membre confirmé
    Profil pro
    Inscrit en
    avril 2003
    Messages
    509
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : avril 2003
    Messages : 509
    Points : 568
    Points
    568
    Par défaut Re: Centraliser les accès à la base de données
    Citation Envoyé par adiGuba
    Salut,


    Quelques remarques :


    • Si le traitement doit être effectué dans un Thread, pourquoi attendre que ce thread soit terminé pour continuer ? --> Tu n'as pas besoin de faire le traitement dans un Thread séparé...
    • La référence monResultSet que tu passes en paramètre à ta méthode ne sera jamais modifié dans la méthode appellante, et ta boucle d'attente sera infini...
    • Je ne vois pas le code pour la libération des ressources (close() sur Connection/Statement/Resultset). Est-ce un oubli ?
    • Tu traite toi-même ton ResultSet dans une boucle while(). Du coup en quoi est-ce différent d'une requête directe ? (il suffit de remplacer l'appel à executeSelect() par la création et l'exécution du Statement pour revenir au code précédent ou presque).




    Perso je te conseilles l'API DbUtils de Jakarta, et donc de jeter un coup d'oeil au tutoriel de Christophe Jollivet : Simplifiez vous JDBC avec Jakarta Commons DbUtils, où alors d'attendre Java 6.0 qui intègrera un système similaire grâce aux annotations...

    a++
    Ha bah oui , y a aussi tout ca !!
    Moi je parlais plus de conception sans trop regarder le code !!
    Par contre on est d'accord sur le thread !!

    Mais d'apres ce que j'ai compris sa conception est tout de meme meilleur que l'ancienne puisque il n'y auras plus qu'une seul classe gérant la connexion ou le pool de connexion ce qui semble plus facile a maintenir !!
    UML avec VIOLET

  5. #5
    Rédacteur
    Avatar de romaintaz
    Homme Profil pro
    Java craftsman
    Inscrit en
    juillet 2005
    Messages
    3 790
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Java craftsman
    Secteur : Finance

    Informations forums :
    Inscription : juillet 2005
    Messages : 3 790
    Points : 7 702
    Points
    7 702
    Par défaut Re: Centraliser les accès à la base de données
    Merci pour tes réponses adiGuba. Quelques précisions donc :

    1. Le traitement du résultat, je ne veux pas le faire dans un Thread. Le Thread n'aurait que pour rôle de récupérer le ResultSet (ou éventuellement de retourner un entier dans un cas d'un UPDATE, INSERT ou DELETE). Le traitement de ce ResultSet se ferait dans la classe qui appelle mon DatabaseAccess.

    2. Concernant le code de libération des ressources, je ne l'ai pas écrit volontairement, pour ne pas surcharger le code là. Mais bien entendu, je ne comptais pas l'oublier, hein

    3. En fait, je voudrais juste qu'aucune classe - sauf DatabaseAccess et le Thread - n'accède directement à la base de données. Ces classes n'auraient donc en charge que l'initialisation de la requête et le traitement des résultats retournés.

    Bon, je jette quand même un coup d'oeil sur DBUtils (que j'ai zappé trop rapidement hier en faisant mes recherches).

    Merci.

    Citation Envoyé par adiGuba
    Salut,


    Quelques remarques :


    • Si le traitement doit être effectué dans un Thread, pourquoi attendre que ce thread soit terminé pour continuer ? --> Tu n'as pas besoin de faire le traitement dans un Thread séparé...
    • La référence monResultSet que tu passes en paramètre à ta méthode ne sera jamais modifié dans la méthode appellante, et ta boucle d'attente sera infini...
    • Je ne vois pas le code pour la libération des ressources (close() sur Connection/Statement/Resultset). Est-ce un oubli ?
    • Tu traite toi-même ton ResultSet dans une boucle while(). Du coup en quoi est-ce différent d'une requête directe ? (il suffit de remplacer l'appel à executeSelect() par la création et l'exécution du Statement pour revenir au code précédent ou presque).




    Perso je te conseilles l'API DbUtils de Jakarta, et donc de jeter un coup d'oeil au tutoriel de Christophe Jollivet : Simplifiez vous JDBC avec Jakarta Commons DbUtils, où alors d'attendre Java 6.0 qui intègrera un système similaire grâce aux annotations...

    a++
    Nous sommes tous semblables, alors acceptons nos différences !
    --------------------------------------------------------------
    Liens : Blog | Page DVP | Twitter
    Articles : Hudson | Sonar | Outils de builds Java Maven 3 | Play! 1 | TeamCity| CitConf 2009
    Critiques : Apache Maven

  6. #6
    Rédacteur
    Avatar de romaintaz
    Homme Profil pro
    Java craftsman
    Inscrit en
    juillet 2005
    Messages
    3 790
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Java craftsman
    Secteur : Finance

    Informations forums :
    Inscription : juillet 2005
    Messages : 3 790
    Points : 7 702
    Points
    7 702
    Par défaut
    Citation Envoyé par FreshVic
    Salut,
    Effectivement centraliser l'acces a une base me semble etre une bonne idée ,
    Tu peux faire de ton DatabaseAccess une interface pour eviter un couplage trop fort.
    Ce qui me gene c'est la creation d'un thread pour executer la requete , en generale ce genre de traitement doit etre synchrone , d'ailleurs tu fais attendre le thread principale le temps que le thread s'execute , autant eviter les thread dans ces conditions !!
    Enfin c'est mon avis !!
    Juste pour information : Le code que j'ai écrit, c'est le code à écrire dans une classe quelconque de mon application, ce n'est pas le code de la classe DatabaseAccess.
    Dans mon exemple, ma classe qui a besoin d'un appel à la base de données réalise ces tâches :
    1. Elle appelle DatabaseAccess.getInstance().executeSelect(...), qui va initialiser la connection, puis créer un Thread pour exécuter la requête.
    2. Elle attend que monResultSet soit différent de null, ce qui signifie que le Thread a terminé l'exécution de la requête.
    Bon, j'admet que l'étape 2 n'est pas terrible, mais c'était surtout pour donner une idée de ce que je voulais faire.

    Donc seule la classe C attend un résultat, pas DatabaseAccess (qui est donc libre de démarrer une autre requête si besoin est).
    Nous sommes tous semblables, alors acceptons nos différences !
    --------------------------------------------------------------
    Liens : Blog | Page DVP | Twitter
    Articles : Hudson | Sonar | Outils de builds Java Maven 3 | Play! 1 | TeamCity| CitConf 2009
    Critiques : Apache Maven

  7. #7
    Membre confirmé
    Profil pro
    Inscrit en
    avril 2003
    Messages
    509
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : avril 2003
    Messages : 509
    Points : 568
    Points
    568
    Par défaut Re: Centraliser les accès à la base de données
    Citation Envoyé par romaintaz
    Merci pour tes réponses adiGuba. Quelques précisions donc :

    1. Le traitement du résultat, je ne veux pas le faire dans un Thread. Le Thread n'aurait que pour rôle de récupérer le ResultSet
    Mais pourquoi le faire dans un thread puisque de toute façon tu dois attendre le ResultSet en retour , les thread te permettent de paraleliser les tache et la en l'occurrence tu n'as jamais 2 taches en parallele puisque l'une attends le resultat de l'autre !
    UML avec VIOLET

  8. #8
    Rédacteur
    Avatar de romaintaz
    Homme Profil pro
    Java craftsman
    Inscrit en
    juillet 2005
    Messages
    3 790
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Java craftsman
    Secteur : Finance

    Informations forums :
    Inscription : juillet 2005
    Messages : 3 790
    Points : 7 702
    Points
    7 702
    Par défaut Re: Centraliser les accès à la base de données
    Citation Envoyé par FreshVic
    Mais pourquoi le faire dans un thread puisque de toute façon tu dois attendre le ResultSet en retour , les thread te permettent de paraleliser les tache et la en l'occurrence tu n'as jamais 2 taches en parallele puisque l'une attends le resultat de l'autre !
    Prennons le cas de figure suivant :

    La classe A et la classe B ont besoin d'accéder à la Base de Données.

    - La classe A appelle DatabaseAccess.getInstance().executeSelect(...).
    - Un Thread T1 est démarré par DatabaseAccess pour cette requête.
    - Ma classe A attend alors le résultat du Thread T1.
    Rien n'empêche que pendant ce temps, la classe B appelle à son tour DatabaseAccess.getInstance().executeSelect(...) pour une autre requête.
    Un Thread T2 sera alors démarré pour cette requête, tandis que A attendra encore le résultat de T1.
    Une fois T1 terminé, A aura les résultats de la requête, et pourra faire les traitements dessus...

    Seule la classe A est bloquée par T1, et rien d'autre (je fais la supposition bien entendu que les classes A et B peuvent être exécutées en parallèle et ne dépendent pas l'une de l'autre).

    Ou alors j'ai loupé quelque chose...
    Nous sommes tous semblables, alors acceptons nos différences !
    --------------------------------------------------------------
    Liens : Blog | Page DVP | Twitter
    Articles : Hudson | Sonar | Outils de builds Java Maven 3 | Play! 1 | TeamCity| CitConf 2009
    Critiques : Apache Maven

  9. #9
    Membre confirmé
    Profil pro
    Inscrit en
    avril 2003
    Messages
    509
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : avril 2003
    Messages : 509
    Points : 568
    Points
    568
    Par défaut Re: Centraliser les accès à la base de données
    Citation Envoyé par romaintaz
    Rien n'empêche que pendant ce temps, la classe B appelle à son tour DatabaseAccess.getInstance().executeSelect(...) pour une autre requête.
    Un Thread T2 sera alors démarré pour cette requête, tandis que A attendra encore le résultat de T1.
    Une fois T1 terminé, A aura les résultats de la requête, et pourra faire les traitements dessus...
    Si A et B sont deja dans 2 thread différent , ce que je pense etre le cas , puisque tu dis "pendant ce temps" tout le traitement que A demande au DataBaseAccess n'empecheras pas le thread executant B de faire appel à DatabaseAccess !

    Mais j'ai peut etre rien compris
    UML avec VIOLET

  10. #10
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : avril 2002
    Messages : 13 938
    Points : 23 015
    Points
    23 015
    Billets dans le blog
    1
    Par défaut
    Salut,

    Si les deux classes A et B accèdent en même temps à la méthode DatabaseAccess.getInstance().executeSelect(...), cela signifie obligatoirement qu'elle sont déjà exécuté dans deux Threads différents, il est donc inutile d'en créer deux supplémentaires. Le seul problème qui pourrait survenir, c'est que ta méthode executeSelect() modifies des champs de ta classe DatabaseAccess, et dans ce cas il faudrait simplement synchroniser ces portions de code...
    Que ton thread exécute la requête ou qu'il attende qu'un autre thread le fasse à sa place, cela revient au même (si pendant ce temps ton thread principal effectuait d'autre opération ce serait totalement différent). De plus pour attendre la fin d'un thread il vaut mieux utiliser la méthode join de ce dernier...


    Ensuite je voudrais savoir comment tu fermes ta connection ? A aucun endroit tu ne conserves une référence vers cette dernière (tout comme le Statement et le ResultSet d'ailleurs).

    a++

  11. #11
    Rédacteur
    Avatar de romaintaz
    Homme Profil pro
    Java craftsman
    Inscrit en
    juillet 2005
    Messages
    3 790
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Java craftsman
    Secteur : Finance

    Informations forums :
    Inscription : juillet 2005
    Messages : 3 790
    Points : 7 702
    Points
    7 702
    Par défaut
    Bon, initiallement, je voulais que toutes les opérations liées directement à la base de données se passent dans mon Thread d'exécution de requêtes, y compris la libération des ressources.
    Du coup, mon Thread donnerait à la classe d'appel (A ou B dans mon précédent exemple), un Object de type String[][] (par exemple), et non plus directement le ResultSet.
    Mais finalement, je pense que je vais m'orienter sur DBUtils, parce qu'il semble faire à peu près ce que je veux faire là.

    Merci pour votre aide.
    Nous sommes tous semblables, alors acceptons nos différences !
    --------------------------------------------------------------
    Liens : Blog | Page DVP | Twitter
    Articles : Hudson | Sonar | Outils de builds Java Maven 3 | Play! 1 | TeamCity| CitConf 2009
    Critiques : Apache Maven

Discussions similaires

  1. [C#] Accés à une base de données AS400
    Par Green Hornet dans le forum Accès aux données
    Réponses: 8
    Dernier message: 14/11/2011, 11h26
  2. Monitorer les accès en base de données MySQL
    Par kahya dans le forum MySQL
    Réponses: 1
    Dernier message: 22/11/2009, 21h42
  3. [phpMyAdmin] Comment tracker les accès à mes bases de données ?
    Par pdtor dans le forum EDI, CMS, Outils, Scripts et API
    Réponses: 1
    Dernier message: 27/12/2007, 23h02
  4. Accès aux bases de données via les objets de Borland (Bdpxx)
    Par agodinasandrien dans le forum Delphi .NET
    Réponses: 9
    Dernier message: 26/09/2005, 14h00
  5. Réponses: 2
    Dernier message: 01/10/2004, 15h13

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo