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

QxOrm Discussion :

Génération de classe modèle-vue avec les services autogénérés


Sujet :

QxOrm

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Homme Profil pro
    Etudiant EPITECH 5e année
    Inscrit en
    Octobre 2014
    Messages
    28
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Etudiant EPITECH 5e année

    Informations forums :
    Inscription : Octobre 2014
    Messages : 28
    Par défaut Génération de classe modèle-vue avec les services autogénérés
    Bonjour,

    Je reviens une nouvelle fois ici pour découvrir un nouvel aspect de QxOrm et QxEntityEditor : les model/view. La petite particularité ici est que je désirerai les faire fonctionner avec les services. Y a t il une option cachée quelque part dans QxEntityEditor pour utiliser non pas la base de données directement, mais les services ?

    Pourrais tu m'indiquer un début de piste pour réaliser cela ?

  2. #2
    Membre Expert

    Profil pro
    Inscrit en
    Avril 2010
    Messages
    482
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 482
    Par défaut


    Le module QxModelView attaque directement la base de données avec la classe qx::QxModel<T>.

    Il est tout à fait possible de créer une nouvelle classe héritant de qx::QxModel<T>, et qui utilise les services au lieu d'attaquer directement la base de données.
    Je vois bien une classe avec 2 paramètres template :
    - T : la classe persistante enregistrée dans le contexte QxOrm ;
    - S : la classe de services associée à la classe persistante.

    Dans cette nouvelle classe, on va surcharger toutes les méthodes préfixeés par qx (qui attaquent par défaut la BDD), pour leur dire d'utiliser les services.
    Si on nomme cette nouvelle classe ModelService, ça pourrait donner quelque chose comme ça :

    ModelService.h :
    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
    template <class T, class S>
    class ModelService : public qx::QxModel<T>
    {
     
    public:
     
       ModelService(QObject * parent = 0) : qx::QxModel<T>(parent) { ; }
       ModelService(qx::IxModel * other, QObject * parent) : qx::QxModel<T>(other, parent) { ; }
       virtual ~ModelService() { ; }
     
       virtual QSqlError qxFetchAll(const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL)
       {
          Q_UNUSED(pDatabase);
          clear();
     
          typedef typename qx::QxModel<T>::type_collection type_collection_tmp;
          boost::shared_ptr<type_collection_tmp> tmp;
          tmp.reset(new type_collection_tmp());
     
          S services;
          m_lastError = services.fetchAll(tmp, m_lstColumns, relation);
     
          beginInsertRows(QModelIndex(), 0, (tmp->count() - 1));
          m_model = (* tmp);
          endInsertRows();
          return m_lastError;
       }
     
       /*
          Faire la même chose pour les méthodes suivantes (il faut regarder l'implémentation dans qx::QxModel<T>, et modifier cette implémentation pour utiliser les services) :
          ---------------------------------------------------------------------------------------------------------------------------------------------------------------
          virtual long qxCount(const qx::QxSqlQuery & query = qx::QxSqlQuery(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxCount(long & lCount, const qx::QxSqlQuery & query = qx::QxSqlQuery(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxFetchById(const QVariant & id, const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxFetchByQuery(const qx::QxSqlQuery & query, const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxInsert(const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxUpdate(const qx::QxSqlQuery & query = qx::QxSqlQuery(), const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxSave(const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxSaveRow(int row, const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxDeleteById(const QVariant & id, QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxDeleteAll(QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxDeleteByQuery(const qx::QxSqlQuery & query, QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxDestroyById(const QVariant & id, QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxDestroyAll(QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxDestroyByQuery(const qx::QxSqlQuery & query, QSqlDatabase * pDatabase = NULL);
          virtual QSqlError qxExecuteQuery(qx::QxSqlQuery & query, QSqlDatabase * pDatabase = NULL);
          virtual qx_bool qxExist(const QVariant & id, QSqlDatabase * pDatabase = NULL);
          virtual qx::QxInvalidValueX qxValidate(const QStringList & groups = QStringList());
       */
     
    };
    Voilà, à présent il faut utiliser cette nouvelle classe ModelService<T, S> au lieu de qx::QxModel<T>, comme ceci par exemple (voir la FAQ pour plus de détails) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    // Create a model and fetch all data from database
    qx::IxModel * pModel = new ModelService<author, services::author_services>();
    pModel->qxFetchAll();
     
    // Associate the model to a QTableView and display it
    QTableView tableView;
    tableView.setModel(pModel);
    tableView.show();
    Remarque : toutes les méthodes que tu as surchargé sont accessibles en QML (avec le suffixe "_" sur chaque méthode).

    Autre remarque : Si tu veux aller plus loin et utiliser QxEntityEditor (pour gérer la notion de relations 1-n, n-1, n-n, 1-1), on peut automatiser l'utilisation de cette nouvelle classe, un peu comme on a fait dans le sujet sur les services : http://www.developpez.net/forums/d14...s-autogeneres/

    Aller dans le menu "Tools >> Export to C++ model/view project (settings)".
    Dans la section "C++ model/view template files", sélectionner l'option "Custom" (au lieu de "Default").
    On va juste copier-coller ce qu'il y a dans "Default", en remplaçant qx::QxModel<T> par ModelService<T, S>.
    Ce qui donne ceci :

    Header (.h) :
    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
    @@COMMENT_FILE_CREATED_BY@@
     
    #ifndef @@INCLUDE_MACRO_GUARD@@
    #define @@INCLUDE_MACRO_GUARD@@
     
    #ifdef _QX_NO_PRECOMPILED_HEADER
    #ifndef Q_MOC_RUN
    #include "../include/@@PROJECT_NAME@@_precompiled_header.model_view.gen.h" // Need to include precompiled header for the generated moc file
    #endif // Q_MOC_RUN
    #endif // _QX_NO_PRECOMPILED_HEADER
     
    @@LIST_INCLUDE_DEPENDENCIES@@
     
    @@NAMESPACE_BEGIN@@
     
    typedef ModelService<@@FULL_CLASS_NAME@@, services::@@FULL_CLASS_NAME@@_services> @@CLASS_NAME@@_model_base_class;
    class @@CLASS_MACRO_EXPORT@@ @@CLASS_NAME@@_model : public @@CLASS_NAME@@_model_base_class
    {
     
       Q_OBJECT
     
    public:
     
       @@CLASS_NAME@@_model(QObject * parent = 0);
       @@CLASS_NAME@@_model(qx::IxModel * other, QObject * parent);
       virtual ~@@CLASS_NAME@@_model();
     
    @@LIST_RELATIONS_Q_INVOKABLE@@
    @@COMMENT_LIST_PROPERTIES_EXPOSED_BY_MODEL@@
     
    };
     
    @@NAMESPACE_END@@
     
    #endif // @@INCLUDE_MACRO_GUARD@@
    Source (.cpp) :
    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
    @@COMMENT_FILE_CREATED_BY@@
     
    #include "../include/@@PROJECT_NAME@@_precompiled_header.model_view.gen.h"
     
    @@LIST_INCLUDE_DEPENDENCIES_CPP@@
     
    #include <QxMemLeak.h>
     
    @@NAMESPACE_BEGIN@@
     
    @@CLASS_NAME@@_model::@@CLASS_NAME@@_model(QObject * parent /* = 0 */) : @@CLASS_NAME@@_model_base_class(parent) { ; }
     
    @@CLASS_NAME@@_model::@@CLASS_NAME@@_model(qx::IxModel * other, QObject * parent) : @@CLASS_NAME@@_model_base_class(other, parent) { ; }
     
    @@CLASS_NAME@@_model::~@@CLASS_NAME@@_model() { ; }
     
    @@IMPLEMENT_LIST_RELATIONS_Q_INVOKABLE@@
     
    @@NAMESPACE_END@@
    Le site de la bibliothèque QxOrm : bibliothèque C++ de gestion de données (Mapping Objet Relationnel ou ORM) basée sur les frameworks Qt et boost.
    QxEntityEditor : éditeur graphique pour la bibliothèque QxOrm (application multi-plateforme pour gérer graphiquement le modèle d'entités).

    Tutoriel : installer un environnement de développement avec QxOrm sous Windows.
    Tutoriel qxBlog : gestion de blogs en C++/Qt.
    Tutoriel qxClientServer : création d'un serveur d'applications en C++/Qt.

  3. #3
    Membre averti
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Octobre 2014
    Messages
    31
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Octobre 2014
    Messages : 31
    Par défaut
    Bonjour,

    Merci beaucoup pour votre réponse, cela m'a beaucoup aidé dans l'avancement de notre projet avec tortuga. Mise a part quelques includes qui manqué dans les fichiers générés, cette solution répond en tout point à notre problématique. Concernant les autres fonctions comme update, je reviendrai vers vous.

  4. #4
    Membre Expert

    Profil pro
    Inscrit en
    Avril 2010
    Messages
    482
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 482
    Par défaut
    cette solution répond en tout point à notre problématique
    Le site de la bibliothèque QxOrm : bibliothèque C++ de gestion de données (Mapping Objet Relationnel ou ORM) basée sur les frameworks Qt et boost.
    QxEntityEditor : éditeur graphique pour la bibliothèque QxOrm (application multi-plateforme pour gérer graphiquement le modèle d'entités).

    Tutoriel : installer un environnement de développement avec QxOrm sous Windows.
    Tutoriel qxBlog : gestion de blogs en C++/Qt.
    Tutoriel qxClientServer : création d'un serveur d'applications en C++/Qt.

  5. #5
    Membre averti
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Octobre 2014
    Messages
    31
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Octobre 2014
    Messages : 31
    Par défaut
    Bonsoir,

    hier soir, j'avais un problème compilation au niveau de la variable tmp dans la fonction ModelClass::qxFetchAll. Pour corriger cette erreur, j'ai changé le type de la variable en boost::shared_ptr<qx::QxModel<T>::type_collection>. Est ce correct ? si oui, comment je fais pour faire la fonction ModelClass::qxInsert ? si non, pouvais m'aider a y voir plus clair ?

    merci encore.

  6. #6
    Membre Expert

    Profil pro
    Inscrit en
    Avril 2010
    Messages
    482
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 482
    Par défaut
    Est ce correct ?
    Oui tu as raison, il y avait un problème de type (je n'avais pas essayé de compiler ).
    Pour respecter la norme C++ à 100% (et avoir du code compilable avec GCC par exemple), il faut même ajouter le mot-clé typename.
    Au final, la méthode qxFetchAll doit s'écrire comme ceci :
    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
    virtual QSqlError qxFetchAll(const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL)
    {
       Q_UNUSED(pDatabase);
       clear();
     
       typedef typename qx::QxModel<T>::type_collection type_collection_tmp;
       boost::shared_ptr<type_collection_tmp> tmp;
       tmp.reset(new type_collection_tmp());
     
       S services;
       m_lastError = services.fetchAll(tmp, m_lstColumns, relation);
     
       beginInsertRows(QModelIndex(), 0, (tmp->count() - 1));
       m_model = (* tmp);
       endInsertRows();
       return m_lastError;
    }
    comment je fais pour faire la fonction ModelClass::qxInsert ?
    C'est exactement le même principe que pour qxFetchAll : regarde l'implémentation de la méthode de la classe de base dans le fichier QxModel.h du package QxOrm (qui attaque directement la BDD), puis modifie cette implémentation dans ta classe dérivée pour utiliser les services.

    Voici ce qu'on a dans le fichier QxModel.h (package QxOrm) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    virtual QSqlError qxInsert(const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL)
    {
       if (relation.count() == 0) { m_lastError = qx::dao::insert(m_model, database(pDatabase)); }
       else { m_lastError = qx::dao::insert_with_relation(relation, m_model, database(pDatabase)); }
       return m_lastError;
    }
    Dans ta classe dérivée, tu peux remplacer/surcharger par ceci :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    virtual QSqlError qxInsert(const QStringList & relation = QStringList(), QSqlDatabase * pDatabase = NULL)
    {
       Q_UNUSED(pDatabase);
       typedef typename qx::QxModel<T>::type_collection type_collection_tmp;
       boost::shared_ptr<type_collection_tmp> tmp;
       tmp.reset(new type_collection_tmp());
       (* tmp) = m_model;
     
       S services;
       m_lastError = services.insert(tmp, relation);
       return m_lastError;
    }
    Le site de la bibliothèque QxOrm : bibliothèque C++ de gestion de données (Mapping Objet Relationnel ou ORM) basée sur les frameworks Qt et boost.
    QxEntityEditor : éditeur graphique pour la bibliothèque QxOrm (application multi-plateforme pour gérer graphiquement le modèle d'entités).

    Tutoriel : installer un environnement de développement avec QxOrm sous Windows.
    Tutoriel qxBlog : gestion de blogs en C++/Qt.
    Tutoriel qxClientServer : création d'un serveur d'applications en C++/Qt.

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

Discussions similaires

  1. Réponses: 13
    Dernier message: 21/12/2014, 22h42
  2. Implémenter le design pattern Observer avec les services web
    Par Klemsy78 dans le forum Services Web
    Réponses: 1
    Dernier message: 12/02/2008, 16h51
  3. Réponses: 10
    Dernier message: 08/01/2008, 21h03
  4. Problèmes avec les Services Intenet windows(IIS)
    Par mikawell3000 dans le forum C#
    Réponses: 1
    Dernier message: 26/07/2007, 11h55
  5. Problèmes avec les services NT/Windows 2000
    Par newfsch dans le forum API, COM et SDKs
    Réponses: 3
    Dernier message: 02/03/2006, 16h49

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