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

VB.NET Discussion :

Affecter une requête à un DataGridView [Débutant]


Sujet :

VB.NET

  1. #1
    Membre actif
    Inscrit en
    Juillet 2013
    Messages
    777
    Détails du profil
    Informations forums :
    Inscription : Juillet 2013
    Messages : 777
    Points : 275
    Points
    275
    Par défaut Affecter une requête à un DataGridView
    Bonjour,

    J'ai créé une bdD dans un nouveau projet VS2010 Express avec la méthode "Ajouter un élément/Base de Données".

    Ma bdD s'appelle Cave.sdf.
    J'y ai créé 4 tables et ai organisé les relations entre ces tables.

    Après pas mal de difficulté, je crois avoir trouvé une solution pour créer en dur une requête. Pour cela, j'ai été dans le CaveDataSet.xsd créé en même temps que la bdd Cave.sdf et en faisant un clic droit, j'ai fait "ajouter une requête" que j'ai appelée SommeQuantitéAchetée et dont la SQL est formée à partir de la table "Vins Achetés" et est égal à "SELECT Référence, SUM([Quantité achetée]) AS [SommeDeQuantité achetée] FROM [Vins achetés] GROUP BY Référence"
    Cette requête SommeQuantitéAchetée apparaît dans QueriesTableAdapter
    Il m'a semblé voir que, de cette manière, la requête est appelable comme n'importe quelle fonction.
    1ère question : est-ce la bonne méthode ?

    Ensuite, je n'ai pas trouvé comment faire en sorte que la datasource de mon DataGridView soit cette requête.

    2ème question : Quelqu'un peut-il m'expliquer comment faire, de préférence à l'aide de l'assistant VS2010 ? Parce que la méthode code me pose un autre pb : je n'ai pas trouvé la syntaxe du string à utiliser en paramètre de SqlConnection. Ce sera la 3ème question optionnelle

    Nota : j'ai préféré créer ma BdD avec la méthode indiquée plus haut, plutôt que celle du tuto de P. LASSERRE qui utilise SQL Serveur car cette dernière méthode semble plus adaptée à un logiciel distribué à de multiples utilisateurs qui interrogent une base de données commune sur un serveur. Or mon logiciel consiste à gérer une base de donnée par licence, celle, unique, de chaque utilisateur. Il s'agit en effet d'un logiciel de gestion de cave pour ceux qui n'auraient pas deviné . Donc chaque utilisateur de l'application est amené à remplir sa propre base de données qui sera sa cave.

    Merci d'avance.

  2. #2
    Membre du Club Avatar de anasschiguer
    Homme Profil pro
    Étudiant
    Inscrit en
    Juillet 2013
    Messages
    35
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Canada

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Finance

    Informations forums :
    Inscription : Juillet 2013
    Messages : 35
    Points : 62
    Points
    62
    Par défaut
    Bonjour, tu viens de découvrir les dataSets et c'est vraiment intéressant je t'asssure, alors pour la première question est-ce la bonne fonction je te dirai oui car c'est une méthode qu'on peut utiliser si on veux créer une requete, tu simplement t'assurer que ta requete est la bonne
    tu vas dans le formulaire qui contient ta DataGridView (DGV) et tu insère le code suivant (bien suur à l'execution assure toi que tu as bien une base remplie de données si tu veux voir des résultats lors du test ):
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    ' assure toi que : VinAchetesTableAdapter est bien le nom de ton table adapter que tu viens de créer
    Dim TAVinsAchetes as CaveTableAdapters.QueriesTableAdapter
    DGV.dataSource=TAVinsAchetes.SommeQuantiteAchetee()
    je te conseille cette méthode car il n'y a pas de codes pour faire la connection et tout ca tu doit juste t'assurer que ta base de données est dans le dossier bin -> debug, tu dois juste t'assurer qu'elle ne permet pas d'injections sql ( je n'ai pas cherché mais je crois qu'elle l'est évite)
    Et finalement quand je l'utilise lors de la déploiement, je la protège par un mot de passe et je crypte le ficher .config, par sécurité, mais si tu ne te soucis pas trop de la sécurité pour l'instant tant mieux
    bon courage

  3. #3
    Membre actif
    Inscrit en
    Juillet 2013
    Messages
    777
    Détails du profil
    Informations forums :
    Inscription : Juillet 2013
    Messages : 777
    Points : 275
    Points
    275
    Par défaut
    Merci tout d'abord pour ta réponse.

    Alors je bloque sur cette ligne :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Dim TAVinsAchetes as CaveTableAdapters.QueriesTableAdapter
    En effet, Dans les objets présents de ma boîte à outil pour le DGV, j'ai les choix suivants :
    CaveDataSet
    QueriesTableAdapter (celui qui, je suppose, contient ma requête)
    TableAdapterManager
    Vins_achetésTableAdapter
    VinsTableAdapter

    Je suppose que quand tu écris
    assure toi que : VinAchetesTableAdapter est bien le nom de ton table adapter que tu viens de créer
    tu veux dire qu'il faut rajouter l'outil "Vins_AchetésTableAdapter" dans le formulaire, ce qui se traduit par l'apparition d'une icône du même nom en bas de Form1.
    Mais CaveTableAdapter n'existe pas.

    En tâtonnant, j'ai réussi à faire accepter cette déclaration :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Dim TAVinsAchetes As CaveDataSetTableAdapters.QueriesTableAdapter
    (Au passage, ne faut-il pas mettre un "As New" ?)

    Alors, il accepte la ligne suivante.

    ce qui donne au total le code suivant :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
        Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
            Dim TAVinsAchetes As New CaveDataSetTableAdapters.QueriesTableAdapter
            DG_DataGrid.DataSource = TAVinsAchetes.SommeQuantiteAchetee
     
        End Sub
    Mais quand je lance l'appli le form s'ouvre... désespérément vide.
    cave.sdf est bien dans le répertoire Débug (je n'ai rien fait, il y était déjà)

    Après, je n'ai pas compris
    tu dois juste t'assurer qu'elle ne permet pas d'injections sql
    . Comment fait-on pour s'en assurer ? Le problème vient-il de là ?

  4. #4
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Décembre 2012
    Messages
    330
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Vaucluse (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2012
    Messages : 330
    Points : 774
    Points
    774
    Par défaut
    Bonjour,

    L'objet DataAdapter est un objet permettant de mettre en relation une DataTable d'un Dataset et une table d'une base de données.
    Il contient des méthodes telles que Fill(...) qui permet de remplir une DataTable, Update(...) qui met à jour les données dans le sens DataTable >>> Table de BD.
    Ces méthodes sont basées sur des requêtes (Select ... pour la méthode Fill(),...)

    Il est possible par code de modifier les requêtes.

    Cependant, dans votre cas, vous voulez remplir une DataTable avec un schéma différent d'une de vos tables dans votre BD.
    Je pense qu'il vous faudrait créer un nouvel objet DataTable et un nouvel Objet DataAdapter avec les requêtes qui vont bien dans votre DataSet.

    Après, je n'ai pas compris
    Citation:
    tu dois juste t'assurer qu'elle ne permet pas d'injections sql
    Comment fait-on pour s'en assurer ? Le problème vient-il de là ?
    En utilisant les requêtes paramétrées.

  5. #5
    Membre actif
    Inscrit en
    Juillet 2013
    Messages
    777
    Détails du profil
    Informations forums :
    Inscription : Juillet 2013
    Messages : 777
    Points : 275
    Points
    275
    Par défaut
    Ouh là, c'est un peu trop général pour moi. Je ne suis qu'un débutant

    Comment affecter ma requête "SommeQuantiteAchetee" à un dataset ?
    Je sais le faire (enfin je crois...) avec une SQL mais là, j'essaye de transformer mes requêtes en fonction pour pouvoir les réutiliser plus loin.

    J'ai réussi à enregistrer cette requête dans QueriesTableAdapter, et c'est tout.

    Je ne l'ai pas dit mais mon ma requête SommeQuantiteAchetee a vocation à être elle-même réutilisée dans d'autres requêtes. C'est pourquoi j'essaye de donner un nom à chacune de mes requête intermédiaires.

    La réponse de anasschiguer me laissait imaginer que j'étais près du but.

  6. #6
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Décembre 2012
    Messages
    330
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Vaucluse (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2012
    Messages : 330
    Points : 774
    Points
    774
    Par défaut
    Bonjour,

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    Dim TAVinsAchetes As New CaveDataSetTableAdapters.QueriesTableAdapter 'Créé un nouveau TableAdapter
    DG_DataGrid.DataSource = TAVinsAchetes.SommeQuantiteAchetee 'Assigne la DataTable SommeQuantitéAchetée comme DataSource du DGV
    Ça c'est bon. Par contre si la table n'a jamais été remplie, par l'appel de TAVinsAchetés.Fill(...) ou TAVinsAchetés.GetData(), le DGV va rester vide.

    Regardez ce lien, il vous donnera un apperçu de comment procéder.

  7. #7
    Membre actif
    Inscrit en
    Juillet 2013
    Messages
    777
    Détails du profil
    Informations forums :
    Inscription : Juillet 2013
    Messages : 777
    Points : 275
    Points
    275
    Par défaut
    Merci pour votre réponse.

    Citation Envoyé par Rainui Voir le message

    Ça c'est bon. Par contre si la table n'a jamais été remplie, par l'appel de TAVinsAchetés.Fill(...) ou TAVinsAchetés.GetData(), le DGV va rester vide.
    Il y a un truc qui m'échappe : j'ai pourtant bien rempli mes tables avec des données . Quand j'effectue un aperçu de ma requête, elle renvoie bien un tableau contenant des données ce qui me permet de contrôler que la SQL est conforme à mes attentes.

    Alors pourquoi mon DGV reste vide quand même ? Faut-il écrire qqch comme
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
     TAVinsAchetes.Fill(CaveDataSet, SommeQuantitéAchetee) 'Je suppose que cette syntaxe est fausse car SommeQuantiteAchetee n'est pas un string
    Mais alors, il faudrait corriger la dernière instruction ce qui donnerait :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
     DG_DataGrid.DataSource = CaveDataSet.Tables(0)
    ???

  8. #8
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Décembre 2012
    Messages
    330
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Vaucluse (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2012
    Messages : 330
    Points : 774
    Points
    774
    Par défaut
    Il ne faut pas confondre une Table dans une base de données et une DataTable d'un DataSet.
    Une Table de base de données est un emplacement dans une base de données où sont stockées les données.
    Une DataTable est un emplacement en mémoire qui suit le schéma d'une Table de base de données.
    Un DataSet est un objet en mémoire qui est le reflet de votre base de données.
    Tel quel, il n'y a pas de liaison entre votre base de données et le DataSet. C'est à dire que dans l'état, les DataTables du DataSet ne contiennent aucunes données. Elles répondent seulement au schéma de la base de données.

    Pour faire la liaison entre le DataSet et la base de données, il existe un objet appelé DataAdapter.
    Celui-ci contient notament la propriété .Commands dans laquelle on trouve:
    .SelectCommand
    .DeleteCommand
    .InsertCommand
    .UpdateCommand
    Lors que l'on demande au DataAdapter d'exécuter la méthode .Fill(...), il va exécuter la SelectCommand sur la table en base de donnée et transférer le résultat de la requête dans la DataTable. A partir de ce moment là, les données sont manipulables dans la DataTable.
    Lorsque l'on utilise le concepteur pour créer le DataSet, ce qui est dommage, c'est que l'on ne voit pas tout ce qui est créé.(On peut le voir dans un fichier caché)

  9. #9
    Membre actif
    Inscrit en
    Juillet 2013
    Messages
    777
    Détails du profil
    Informations forums :
    Inscription : Juillet 2013
    Messages : 777
    Points : 275
    Points
    275
    Par défaut
    Ben je comprends la théorie mais je nage dans les types.

    Reprenons ce que tu me disais

    Citation Envoyé par Rainui Voir le message
    Ça c'est bon. Par contre si la table n'a jamais été remplie, par l'appel de TAVinsAchetés.Fill(...) ou TAVinsAchetés.GetData(), le DGV va rester vide.
    Or la méthode Fill et GetData ne s'applique pas à l'objet TAVinsAchetés tel que défini.
    TAVinsAchetés est du type TableAdapter, OK.
    Fill et GetData s'appliquent à un objet DataAdapter

    Quel est le lien entre DataAdapter et TableAdapter ?
    Quel est le DataAdapter propre à ma BdD ?
    Rappelons que le but est de pouvoir utiliser mes objets prédéfinis par l'Assistant sans avoir à tout redéfinir depuis la méthode sqlconnection (d'autant que s'agissant de la chaine de connexion, les propriétés m'indiquent "Data Source=|DataDirectory|\Cave.sdf" et que ça ne marche pas mieux même en faisant un test d'affichage d'une simple table en suivant le tuto)

    Bref, je ne vois toujours pas le chainon manquant entre mes 2 lignes de code que tu as approuvées et la ligne qui spécifie
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    DG_DataGrid.Datasource =...

  10. #10
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Décembre 2012
    Messages
    330
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Vaucluse (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2012
    Messages : 330
    Points : 774
    Points
    774
    Par défaut
    Quel est le lien entre DataAdapter et TableAdapter ?
    L'ojet TableAdapter hérite de DataAdapter.
    Ils ont les mêmes méthodes. Pour vous en assurer : DataAdpter
    Quel est le DataAdapter propre à ma BdD ?
    Si vous avez créé votre DataSet avec le concepteur, il y en a un par DataTable.
    Rappelons que le but est de pouvoir utiliser mes objets prédéfinis par l'Assistant sans avoir à tout redéfinir depuis la méthode sqlconnection
    Dans le concepteur du DataSet, vous ajoutez un TableAdapter, quand vous arrivez à la fenêtre "Entrez une instruction SQL", cliquez sur "Générateur de requête, créez votre requête "SELECT Référence, SUM([Quantité achetée]) AS [SommeDeQuantité achetée] FROM [Vins achetés] GROUP BY Référence".
    Puis cliquez sur OK, puis suivant. Là, théoriquement la dernière case à cocher devrait être grisée du fait de la fonction Sum() dans la requête. Cliquez sur suivant puis terminer.
    Il ne restera plus qu'à utiliser le TableAdapter fraichement créé pour remplir la DataTable associée.

  11. #11
    Membre actif
    Inscrit en
    Juillet 2013
    Messages
    777
    Détails du profil
    Informations forums :
    Inscription : Juillet 2013
    Messages : 777
    Points : 275
    Points
    275
    Par défaut
    YESSSS !! Ca marche !

    Il a fallu toutefois que je renomme la Tabledata ainsi créée (par défaut, elle s'appelle Vins achetés1) en "SommeQuantiteAchetee"





    Je cherchais à rajouter cette requête dans le VinsAchetésTableAdapter mais je n'ai pas réussi.
    Mais finalement, je me dis que puisque l'idée est de pouvoir appeler la requête simplement dans la suite du code (et notamment l'imbriquer dans d'autres requêtes), c'est sans doute mieux comme ça, non ?

    En tout cas voilà le code complet (pour ultimes observations de ta part le cas échéant, et pour d'autres lecteurs qui voudraient la solution)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
        Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
            Dim MonDS As New CaveDataSet
            Dim TAVinsAchetes As New CaveDataSetTableAdapters.SommeQuantiteAcheteeTableAdapter
     
            TAVinsAchetes.Fill(MonDS.SommeQuantiteAchetee)
     
            DG_DataGrid.DataSource = MonDS.SommeQuantiteAchetee
     
        End Sub
    Cela dit, maintenant que j'ai créé cette nouvelle datatable dans mon CaveDataSet, j'ai voulu voir par curiosité si, au lieu de taper le code ci-dessus, on ne pouvait pas plus simplement utiliser l'assistant du Form.

    Voici les sources disponibles pour le DGV :



    Quand je sélectionne SommeQuantiteAchetee, miracle, ça marche aussi, sans taper un seul code. Enfin, voici le code retourné par cette manip :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
            'TODO: cette ligne de code charge les données dans la table 'CaveDataSet1.SommeQuantiteAchetee'. Vous pouvez la déplacer ou la supprimer selon vos besoins.
            Me.SommeQuantiteAcheteeTableAdapter.Fill(Me.CaveDataSet1.SommeQuantiteAchetee)
     
        End Sub
    Au-delà de la simplicité accrue de la 2ème méthode, faut-il privilégier l'une ou l'autre des 2 méthodes ?

    En tout cas merci pour ton aide. D'autant que ça commence à rentrer dans ma petite tête.

  12. #12
    Membre éclairé
    Homme Profil pro
    Technicien maintenance
    Inscrit en
    Décembre 2012
    Messages
    330
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Vaucluse (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Technicien maintenance
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2012
    Messages : 330
    Points : 774
    Points
    774
    Par défaut
    Les deux méthodes sont bonnes. La seule différence c'est que les objets requis sont instanciés à des moments différents.
    Dans la première méthode, c'est vous qui instanciez les objet dont vous avez besoin sur l’événement Load du formulaire.
    Dans la deuxième, les objets sont instanciés dans la procédure InitializeComponent qui est exécuté dans la méthode .New() du formulaire.
    Content d'avoir pu vous aider

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. affecter une requête SQL à un tableau
    Par gastoncs dans le forum VB.NET
    Réponses: 2
    Dernier message: 22/07/2012, 10h18
  2. Réponses: 2
    Dernier message: 10/05/2012, 12h26
  3. Affecter une requête à une table
    Par DrWilly dans le forum WinDev
    Réponses: 5
    Dernier message: 30/01/2007, 09h52
  4. [Access 2003/VBA]Affecter une requète à un raport dans Access ?
    Par cotmar dans le forum Requêtes et SQL.
    Réponses: 27
    Dernier message: 19/06/2006, 12h21
  5. Affecter résultat SQL d'une requête à une variable
    Par bozolozo dans le forum Requêtes et SQL.
    Réponses: 2
    Dernier message: 02/01/2005, 17h37

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