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

PyQt Python Discussion :

[QtSql]Problème avec setQuery


Sujet :

PyQt Python

  1. #1
    Candidat au Club
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2013
    Messages
    6
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Juin 2013
    Messages : 6
    Points : 4
    Points
    4
    Par défaut [QtSql]Problème avec setQuery
    Bonjour,

    Je suis en train de me familiariser avec PyQt (Python 3 avec PyQt5). Pour les besoins de ma future application qui consistera à comparer des données fixes avec d'autres données extraites d'une BDD, je m'entraîne en faisant un programme simple:
    J'aimerais me connecter à une BDD, faire une requête simple et l'afficher dans une fenêtre basique.

    Pour l'instant, ça plante avec le code erreur suivant: Process finished with exit code -1073741819 (0xC0000005)

    La connexion semble correcte. En cherchant à isoler le problème, il semblerait qu'il provienne de la ligne suivante: model.setQuery("SELECT AVION FROM POOL_AVION WHERE NUMERO= 5",db)

    Voici mon code:
    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
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
     
    from PyQt5.QtCore import *
    from PyQt5.QtGui import QColor
    from PyQt5.QtWidgets import *
    from PyQt5.QtSql import *
     
     
    def createConnection(db):
     
        db.setHostName("x.x.x.x")
        db.setPort(3306)
        db.setDatabaseName("DATABASE_NAME")
        db.setUserName("USER")
        db.setPassword("PASSWD")
        print("Etape 0")
     
        if not db.open():
            QMessageBox.critical(None, "Cannot open database",
                                 str(db.lastError()),
                                 QMessageBox.Cancel)
            return False
     
        print("1")
        return True
     
    def initializeModel(model, db):
        print("2")
        model.setQuery("SELECT AVION FROM POOL_AVION WHERE NUMERO=5",db)
        print("3")
        model.setHeaderData(0, Qt.Horizontal, "AVION")
    offset = 0
    views = []
     
     
    def createView(title, model):
        global offset, views
     
        view = QTableView()
        views.append(view)
        view.setModel(model)
        view.setWindowTitle(title)
        view.move(100 + offset, 100 + offset)
        offset += 20
        view.show()
     
    if __name__ == '__main__':
     
        import sys
     
        app = QApplication(sys.argv)
        db = QSqlDatabase.addDatabase("QMYSQL")
     
        if not createConnection(db):
            sys.exit("Bloque à l'étape 1")
     
        plainModel = QSqlQueryModel()
     
        initializeModel(plainModel, db)
     
        createView("Plain Query Model", plainModel)
     
        sys.exit(app.exec_())
    J'obtiens le résultat suivant:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    "C:\Program Files\Python35\python.exe" C:/Users/test/PycharmProjects/untitled/TESTcoMYSQL.py
    Etape 0
    1
    2
     
    Process finished with exit code -1073741819 (0xC0000005)
    J'ai également bien testé ma requête SQL, elle fonctionne correctement lorsque je l'exécute sur le serveur.


    Merci pour votre aide

  2. #2
    Expert éminent
    Avatar de tyrtamos
    Homme Profil pro
    Retraité
    Inscrit en
    Décembre 2007
    Messages
    4 462
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2007
    Messages : 4 462
    Points : 9 249
    Points
    9 249
    Billets dans le blog
    6
    Par défaut
    Bonjour,

    Attention pour ce qui suit: je travaille sur une base sqlite, et non mysql. Je connais donc bien le pilote python sqlite3, mais pas du tout celui pour mysql.


    Comme j'utilise assez fréquemment l'extraction sur requête SQL et l'affichage du résultat sur un QTableView, j'ai fini par adopter la méthode suivante:

    - Je fais une extraction avec SELECT, mais je crée une table temporaire avec le résultat ("CREATE TABLE xxx AS xxx"). Et je fais ça avec le pilote Python (module sqlite3) et non celui de Qt!

    - j'affiche ensuite la table temporaire obtenue dans un QTableView en utilisant le pilote de Qt.

    Bien sûr, la base de données n'est jamais ouverte en même temps avec les 2 pilotes!

    J'ai donc une classe d'affichage qui ressemble à ça:

    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
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    #############################################################################
    class VueTable(QtWidgets.QDialog):
        """visualisation d'une table d'une base de données ouverte
        """
     
        #========================================================================
        def __init__(self, cnx, nomtable, parent=None):
            super().__init__(parent)
     
            self.cnx = cnx # connexion à la base de données
            self.nomtable = nomtable # nom de la table à afficher
     
            self.model = QtSql.QSqlRelationalTableModel(self, self.cnx)
            self.model.setTable(self.nomtable)
            self.model.setEditStrategy(QtSql.QSqlTableModel.OnFieldChange)#OnManualSubmit)
            self.model.select()
     
            self.vuetable = QtWidgets.QTableView()
            self.vuetable.setModel(self.model)
            self.vuetable.setItemDelegate(QtSql.QSqlRelationalDelegate(self.vuetable))
            self.vuetable.setSortingEnabled(True)
     
            position = QtWidgets.QVBoxLayout()
            position.addWidget(self.vuetable)
            self.setLayout(position)
     
            self.setWindowTitle("Table: " + self.nomtable)
            self.vuetable.resizeColumnsToContents()
    Et en fait, je gère entièrement la base de données avec le pilote Python (création de tables, ajout d'enregistrement, etc...). Je le préfère nettement à celui de Qt, et il me permet en plus de créer et d'utiliser dans les scripts SQL des fonctions écrites en Python! De ce fait je n'utilise le pilote Qt que pour visualiser les extractions et si nécessaire de modifier des champs si la table affichée est une table de base et non une table temporaire issue d'une extraction.

    On peut en contrepartie faire des choses étonnantes avec un QTableView et la machinerie Qt. Par exemple faire des recherches et des filtrages complexes en utilisant un QSortFilterProxyModel qui s'interpose entre le modèle et le QTableView. Ou peut aussi utiliser un delegate pour afficher certaines colonnes avec des widgets spécifiques non prévus par Qt. On peut aussi enregistrer une table telle qu'elle est affichée (donc avec tri et filtrage) dans un fichier csv pour pouvoir être repris par un tableur (Excel ou autre). Etc...
    Un expert est une personne qui a fait toutes les erreurs qui peuvent être faites, dans un domaine étroit... (Niels Bohr)
    Mes recettes python: http://www.jpvweb.com

  3. #3
    Candidat au Club
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2013
    Messages
    6
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Juin 2013
    Messages : 6
    Points : 4
    Points
    4
    Par défaut
    Bonjour et merci pour ta réponse,

    Ta réponse m'a permis de m'orienter et le problème vient bien des drivers Mysql. Il semblerait que le driver est un problème de compatibilité avec pyqt.
    Tout fonctionne avec Qt c++ mais pas en pyqt. J'ai également changé les connecteurs sur le site de Mysql sans que cela ne règle de problème...

  4. #4
    Expert éminent
    Avatar de tyrtamos
    Homme Profil pro
    Retraité
    Inscrit en
    Décembre 2007
    Messages
    4 462
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2007
    Messages : 4 462
    Points : 9 249
    Points
    9 249
    Billets dans le blog
    6
    Par défaut
    Bonjour,

    Peut-être n'ai-je pas été assez clair dans mon propos. Le pilote que tu utilises ("QMYSQL") est celui qui vient avec PyQt/Qt. Quand tu exécutes une requête SQL avec PyQt, c'est lui qui est concerné.

    Mais Python peut utiliser aussi pour gérer la base de données un pilote mysql qui n'a rien à voir avec PyQt. Par exemple celui-là (il y en a d'autres): https://pypi.python.org/pypi/PyMySQL.

    Avec sqlite, on peut agir sur la même base de données avec l'un ou l'autre des pilotes. Je ne sais pas si c'est la même chose avec mysql, mais si oui, c'est une possibilité pour toi de sortir de ton problème: installe pymysql, gère ta base avec lui et quand tu veux afficher une table, et seulement dans ce cas, utilise le pilote PyQt!
    .
    Sinon, il m'est déjà arrivé d'utiliser PyQt et son pilote pour gérer ma base, et si je regarde ton code, je n'utilise jamais "model.setQuery": je crée un nouveau query = QtSql.QSqlQuery(cnx), j'exécute la requête "req" avec ok = query.exec_(req), et je libère les ressources (indispensable) avec query.finish(). Si tu le souhaites, je peux te construire un exemple plus complet, y compris avec transaction (il faudrait alors me laisser un peu de temps car je suis pris pour le week-end).
    Un expert est une personne qui a fait toutes les erreurs qui peuvent être faites, dans un domaine étroit... (Niels Bohr)
    Mes recettes python: http://www.jpvweb.com

  5. #5
    Candidat au Club
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2013
    Messages
    6
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Juin 2013
    Messages : 6
    Points : 4
    Points
    4
    Par défaut
    Ok je comprends mieux. Ca marche avec ta technique. En utilisant pymysql, je peux effectivement gérer mes enregistrements en BDD et les afficher avec qt. Je suis quand même pas super familier avec l'environnement, et pour l'instant je me contente d'afficher le résultat de ma requête dans un simple Label.

    Pourrais-tu me montrer un exemple complet en utilisant cette façon de faire?



    Encore merci pour ton aide,

  6. #6
    Expert éminent
    Avatar de tyrtamos
    Homme Profil pro
    Retraité
    Inscrit en
    Décembre 2007
    Messages
    4 462
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2007
    Messages : 4 462
    Points : 9 249
    Points
    9 249
    Billets dans le blog
    6
    Par défaut
    Bonjour,

    Voilà un petit code de démo qui va te montrer de manière interactive comment on peut faire.

    J'ai choisi pour cet exemple d'utiliser uniquement QtSql, et non le module Python sqlite3. On peut traiter ce dernier cas si ça t'intéresse.

    J'ai utilisé le SGBDR sqlite (avec le pilote de Qt), parce que je n'ai que ça pour l'instant. Il faudra donc modifier les fonctions d'ouverture et de fermeture pour adapter à MySql. Il faudra aussi changer le nom de la base de données.

    Pour l'exemple, j'ai une table "contacts" avec 3 champs texte: nom, prenom et telephone.

    Quand on lance le programme, il vient une fenêtre avec un QTextEdit et un QPushButton.

    Dans le QTextEdit, on peut écrire des requêtes SQL quelconques, avec ces particularités:

    - une requête commençant par "SELECT" pourra être multiligne, mais unique. La requête donnera ses résultats dans une table temporaire appelée 'tempo', et déclenchera l'affichage de cette table dans un QTableView.

    Exemple de requête d'extraction:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    select *
    from contacts;
    - pour les autres requêtes, il peut y en avoir plusieurs et même multilignes, mais chacune doit se terminer par ';'. L'intérêt d'avoir plusieurs requêtes est qu'elles seront traitées dans une "transaction". Cela veut dire que l'échec d'une seule de ces requêtes entrainera l'annulation de toutes les requêtes de cette transaction. Cela permet de ne pas laisser la base de données dans un état "intermédiaire" inacceptable.

    Exemple de 3 requêtes qui s'exécuteront dans une même transaction:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    insert into contacts values ('Toto', 'Albert', '00.00.00.00.91');
    insert into contacts 
    values ('Tata', 'Jean', '00.00.00.00.92');
    insert into contacts values ('Titi', 'Alain', '00.00.00.00.93');
    L'exécution de ces requêtes se fait en cliquant sur le bouton. Des messages pourront signaler si c'est ok ou pas.

    A part ça, il faut éplucher le code qui est assez largement commenté, pour bien comprendre ce que ça fait.

    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
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
    156
    157
    158
    159
    160
    161
    162
    163
    164
    165
    166
    167
    168
    169
    170
    171
    172
    173
    174
    175
    176
    177
    178
    179
    180
    181
    182
    183
    184
    185
    186
    187
    188
    189
    190
    191
    192
    193
    194
    195
    196
    197
    198
    199
    200
    201
    202
    203
    204
    205
    206
    207
    208
    209
    210
    211
    212
    213
    214
    215
    #!/usr/bin/python
    # -*- coding: utf-8 -*-
     
    import sys
    import os
     
    from PyQt5 import (QtWidgets, QtGui, QtCore, QtSql)
     
    #############################################################################
    def ouvrebaseqt(basesql):
        """ouvre la base sqlite3 'basesql' sous PyQt et renvoie la connexion
           si échec, retourne None
        """
        db = QtSql.QSqlDatabase.addDatabase("QSQLITE")
        db.setDatabaseName(basesql)
        if not db.open():
            db = None # Erreur d'ouverture de la base de données basesql
        return db # retourne la connexion (=None si échec)
     
    #############################################################################
    def fermebaseqt(db):
        """Ferme la base ouverte avec la connexion db 
        """
        db.close()
        db.removeDatabase(db.databaseName())
     
    #############################################################################
    class VueTable(QtWidgets.QDialog):
        """visualisation d'une table d'une base de données ouverte
        """
     
        # nouveau signal pour indiquer la fin d'affichage à l'appelant
        finvuetable = QtCore.pyqtSignal(int)
     
        #========================================================================
        def __init__(self, db, nomtable, indexfin=0, parent=None):
            super().__init__(parent)
            self.resize(600, 400)
     
            self.db = db # connexion à la base de données
            self.nomtable = nomtable # nom de la table à afficher
            self.indexfin = indexfin
     
            self.model = QtSql.QSqlRelationalTableModel(self, self.db)
            self.model.setTable(self.nomtable)
            self.model.setEditStrategy(QtSql.QSqlTableModel.OnFieldChange)#OnManualSubmit)
            self.model.select()
     
            self.vuetable = QtWidgets.QTableView()
            self.vuetable.setModel(self.model)
            self.vuetable.setItemDelegate(QtSql.QSqlRelationalDelegate(self.vuetable))
            self.vuetable.setSortingEnabled(True)
     
            # Changer la police de caractère
            font = QtGui.QFont()
            font.setFamily("DejaVu Sans Mono")
            font.setPointSize(10)
            self.vuetable.setFont(font)
     
            position = QtWidgets.QVBoxLayout()
            position.addWidget(self.vuetable)
            self.setLayout(position)
     
            self.setWindowTitle("Table: " + self.nomtable)
            self.vuetable.resizeColumnsToContents()
     
        #========================================================================
        def closeEvent(self, event):
            """fermeture de la fenêtre
            """
            # envoi du signal de fermeture à l'appelant
            self.finvuetable.emit(self.indexfin)
            # et acceptation de la fermeture
            event.accept()
     
    #############################################################################
    class Fenetre(QtWidgets.QWidget):
     
        #========================================================================
        def __init__(self, db, parent=None):
            super().__init__(parent)
            self.resize(800, 600)
     
            self.db = db # variable de connexion ouverte de la base
     
            self.textEdit = QtWidgets.QTextEdit(self)
     
            # Changer la police de caractère
            font = QtGui.QFont()
            font.setFamily("DejaVu Sans Mono")
            font.setPointSize(10)
            self.textEdit.setFont(font)
     
            self.bouton = QtWidgets.QPushButton("Exécuter", self)
            self.bouton.clicked.connect(self.execsql)
     
            posit = QtWidgets.QGridLayout()
            posit.addWidget(self.textEdit, 0, 0)
            posit.addWidget(self.bouton, 1, 0)
            self.setLayout(posit)
     
        #========================================================================
        @QtCore.pyqtSlot()
        def execsql(self):
            """exécution de la requête introduite dans le QLineEdit
            """
     
            # lecture de la requête SQL
            req = self.textEdit.toPlainText().strip()
     
            # chercher s'il y a plusieurs requêtes
            lignes = [ligne.strip() for ligne in req.splitlines() if ligne.strip()!=""]
            reqs = [""]
            for ligne in lignes:
                if reqs[-1]!="":
                   reqs[-1] += " " 
                reqs[-1] += ligne
                if ligne.endswith(';'):
                    reqs.append("")
            # suppression des éventuelles requêtes vides:
            reqs = [req for req in reqs if req!=""] 
            if reqs==[]:
                return # aucune requête: on ne fait rien
     
            # création d'un query sur la base ouverte
            query = QtSql.QSqlQuery(self.db)
     
            #--------------------------------------------------------------------
            if reqs[0].upper().startswith("SELECT"):
                # => extraction: on va créer une table 'tempo' pour affichage
     
                req = reqs[0] # seule la 1ère requête d'extraction sera exécutée
     
                # suppression de la table temporaire si elle existe déjà
                req0 = "DROP TABLE IF EXISTS tempo"
                ok = query.exec_(req0)
                if not ok:
                    QtWidgets.QMessageBox.warning(self, 
                        "Suppression table temporaire", 
                        " ====> Echec <==== ")
                    return
     
                # exécution de l'extraction et création de la table temporaire
                req = "CREATE TABLE tempo AS " + req
                ok = query.exec_(req)
                if not ok:
                    QtWidgets.QMessageBox.warning(self, 
                        "Exécution extraction", 
                        " ====> Echec <==== ")
                    return
     
                # affichage de la table temporaire
                self.vuetable = VueTable(self.db, "tempo")
                # la fermeture de la fenêtre entrainera l'exécution de self.infofinvuetable
                self.vuetable.finvuetable.connect(self.infofinvuetable)
                self.vuetable.show()
     
            #--------------------------------------------------------------------
            else:
                # exécution de requete(s) SQL
     
                # activation du mode transaction
                self.db.transaction() 
     
                # exécution de toutes les requêtes de la transaction
                for req in reqs:
                    if not query.exec_(req):
                        self.db.rollback() # <= échec de la requête
                        break # qui entrainera l'annulation de toutes les requêtes
     
                if not self.db.commit():
                    # on est ici si l'une des requêtes a échoué
                    QtWidgets.QMessageBox.warning(self, 
                        "Exécution requête(s)", 
                        " ====> Echec <==== ")
                    return
     
                # message de fin avec réussite
                QtWidgets.QMessageBox.information(self, 
                    "Exécution requête(s)", 
                    " ====> Réussite  <====")
     
        #========================================================================
        @QtCore.pyqtSlot(int)
        def infofinvuetable(self, indfin):
            """exécuté à chaque fermeture de la fenêtre VueTable
            """
            # simmple affichage en console
            print("Affichage terminé pour la fenêtre ", indfin)
     
        #========================================================================
        def closeEvent(self, event):
            """exécuté à la fermeture de la présente fenêtre
            """
            fermebaseqt(self.db) # fermeture de la base
            event.accept() # et acceptation de la fermeture de la fenêtre
     
    #############################################################################
    if __name__ == "__main__":
        app = QtWidgets.QApplication(sys.argv)
     
        # ouverture de la base à utiliser
        basesql = "basesql.db3"
        db = ouvrebaseqt(basesql)
        if db==None:
            QtWidgets.QMessageBox.critical(None, 
                    "Ouverture de la base", 
                    " ====> Echec <==== ")
            app.quit()
            sys.exit()
     
        fenetre = Fenetre(db)
        fenetre.setAttribute(QtCore.Qt.WA_DeleteOnClose)
        fenetre.show()
        sys.exit(app.exec_())
    Un expert est une personne qui a fait toutes les erreurs qui peuvent être faites, dans un domaine étroit... (Niels Bohr)
    Mes recettes python: http://www.jpvweb.com

  7. #7
    Candidat au Club
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2013
    Messages
    6
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Juin 2013
    Messages : 6
    Points : 4
    Points
    4
    Par défaut
    Super, je vais éplucher tout ça!

    Merci beaucoup pour tout le temps que tu m'as accordé

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

Discussions similaires

  1. VC++ Direct3D8, problème avec LPD3DXFONT et LPD3DTEXTURE8
    Par Magus (Dave) dans le forum DirectX
    Réponses: 3
    Dernier message: 03/08/2002, 11h10
  2. Problème avec [b]struct[/b]
    Par Bouziane Abderraouf dans le forum CORBA
    Réponses: 2
    Dernier message: 17/07/2002, 10h25
  3. Problème avec le type 'Corba::Any_out'
    Par Steven dans le forum CORBA
    Réponses: 2
    Dernier message: 14/07/2002, 18h48
  4. Problème avec la mémoire virtuelle
    Par Anonymous dans le forum CORBA
    Réponses: 13
    Dernier message: 16/04/2002, 16h10

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