Zend FR

Consultez la FAQ sur le ZF avant de poster une question

Vous n'êtes pas identifié.

#1 14-10-2008 20:35:06

Fly705
Nouveau membre
Date d'inscription: 14-10-2008
Messages: 2

requete avec un IN

bonjour,

j'aimerais savoir comment peut on faire une requete avec un IN imbriqué?
car dans la doc je n'ai pas vu d'exemple...

par exemple, j'ai ceci en sql:

Code:

select v.nom, v.description
from ville v, pays p, ville_in_pays vp
where pays like '$pays'
and v.id_ville=vp.id_ville
and vp.id_pays=p.id_pays
and v.id_ville IN (select recompense.id_ville from recompense)

Merci d'avance de votre aide

Hors ligne

 

#2 14-10-2008 20:57:11

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

Salut,

Avant de t'aider, j'aimerais juste savoir où se situe réellement ton problème.

Tu ne sais pas comment créer une requête à l'aide de Zend_Db ou tu ne sais pas comment créer une sous-requête dans ton "IN()" ?

Remarques : au lieu d'utiliser des conditions comme celle-ci "v.id_ville=vp.id_ville and vp.id_pays=p.id_pays", utilises des jointures wink

Dernière modification par acharrex (14-10-2008 21:02:19)

Hors ligne

 

#3 14-10-2008 21:14:15

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

M'enfin, voici déjà une solution :

Code:

$select = $this->_db->select()
            ->from("ville", array("nom", "description"))
            ->join("ville_in_pays", "ville_in_pays.id_ville = ville.id_ville", array())
            ->join("pays", "pays.id_pays = ville_in_pays.id_pays", array())
            ->where("ville.id_ville IN (".new Zend_Db_Expr($this->_db->select()->from("recompense", array("id_ville"))).")")
            ->where("pays.pays_name LIKE '{$pays}'")
            ->query();
    
echo '<pre>';
print_r($select->fetchAll());
echo '</pre>';

Dernière modification par acharrex (14-10-2008 21:15:48)

Hors ligne

 

#4 15-10-2008 10:16:11

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

acharrex a écrit:

M'enfin, voici déjà une solution :

Code:

$select = $this->_db->select()
            ->from("ville", array("nom", "description"))
            ->join("ville_in_pays", "ville_in_pays.id_ville = ville.id_ville", array())
            ->join("pays", "pays.id_pays = ville_in_pays.id_pays", array())
            ->where("ville.id_ville IN (".new Zend_Db_Expr($this->_db->select()->from("recompense", array("id_ville"))).")")
            ->where("pays.pays_name LIKE '{$pays}'")
            ->query();
    
echo '<pre>';
print_r($select->fetchAll());
echo '</pre>';

j'ai essayé ce code là,
avec $this->_db->getAdapter()->select()
il me renvoie

Catchable fatal error: Object of class AnalyserController could not be converted to string in controller.php

ey si je met avec $this->_db->select()
il renvoie:

Exception : Zend_Db_Statement_Exception Message : SQLSTATE[42000]: Syntax error or access violation: 1065 Query was empty

Si quelqu'un pourrait me dire pourquoi ma requête ne fonctionne pas, ça maiderait bcp


Merci d'avance!

Hors ligne

 

#5 15-10-2008 10:53:02

Delprog
Administrateur
Date d'inscription: 29-09-2008
Messages: 670

Re: requete avec un IN

Salut,

Soit tu utilises _db, soit tu utilises getAdapter(), mais pas les deux puisque getAdapter() sert à récupérer l'objet 'db' par défaut.

Donc c'est logique que la première syntaxe ne fonctionne pas.

Ensuite pour l'autre message d'erreur, est-ce que tu peux nous coller le code de ton select() en entier ?


A+ benjamin.


http://www.anonymation.com/ - anonymation - Studio de création.
http://code.anonymation.com/ - anonymation - blog - développement et architecture web

Hors ligne

 

#6 15-10-2008 11:49:20

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

j'ai fait un autre test avec une requete
et j'ai le probleme chaque fois que j'essaye de nommer une table par exemple quand je fait:

Code:

->from(array('v' => $this->ville), array('v.id_ville', 'v.nom_ville'))
->where('v.id_ville= ?', $this->identifiant)

là il me met:

Exception : Zend_Db_Statement_Exception Message : SQLSTATE[42000]: Syntax error or access violation: 1065 Query was empty

par contre quand je met

Code:

->from($this->ville, array('id_ville', 'nom_ville')))
->where('id_ville= ?', $this->identifiant)

ça fonctionne...  :s

Quelqu'un sait-il pourquoi?

car quand je vais faire une jointure, je devrai nommer mes tables car certaines auront les même champs

merci d'avance


edit: ajout de la parenthèse manquante

Dernière modification par Fly706 (15-10-2008 12:03:13)

Hors ligne

 

#7 15-10-2008 11:52:23

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

C'est plutôt :

Code:

->from(array('v' => $this->ville), array('v.id_ville', 'v.nom_ville'))
->where('v.id_ville= ?', $this->identifiant)

Hors ligne

 

#8 15-10-2008 12:02:12

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

oui j'ai oublié une parenthèse :s

mais le problème reste le même... sad

Hors ligne

 

#9 15-10-2008 12:13:52

Delprog
Administrateur
Date d'inscription: 29-09-2008
Messages: 670

Re: requete avec un IN

Qu'est-ce qu'est censé te renvoyer

Code:

$this->ville

?


http://www.anonymation.com/ - anonymation - Studio de création.
http://code.anonymation.com/ - anonymation - blog - développement et architecture web

Hors ligne

 

#10 15-10-2008 12:33:05

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

Voici le code du modèle que tu devrais utiliser :

Code:

class Ville extends Zend_Db_Table
{

    protected $_name = 'ville';
    protected $_primary = 'id_ville';
    //...

Et là-dedans tu mets une fonction dans laquelle tu fais ta requête :

Code:

$select = $this->_db->select()
            ->from(array("v" => $this->_name), array("nom", "description"))
            ->where("v.{$this->_primary} = ?", $this->identifiant)
            ->query();

Hors ligne

 

#11 15-10-2008 12:35:00

Delprog
Administrateur
Date d'inscription: 29-09-2008
Messages: 670

Re: requete avec un IN

Voilà smile

D'où ma question, ce '$this->ville' ne me plaisait pas...


http://www.anonymation.com/ - anonymation - Studio de création.
http://code.anonymation.com/ - anonymation - blog - développement et architecture web

Hors ligne

 

#12 15-10-2008 13:13:23

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

mon modèle ville, je l'avais déjà.

dans mon controlleur, j'ai:

Code:

public function init()
{
        parent::init();
        $request = $this->getRequest();
        
        try 
        {
                $this->ville= new Ville(array('db' => 'db'));
        }
        catch (Zend_Exception $e) 
        {
                throw($e);
        }
}

puis j'ai ma fonction...

et tjs le problème de:

Exception : Zend_Db_Statement_Exception Message : SQLSTATE[42000]: Syntax error or access violation: 1065 Query was empty

:s

Dernière modification par Fly706 (15-10-2008 13:13:35)

Hors ligne

 

#13 15-10-2008 13:18:08

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

OK, tu peux juste poster le code de ton contrôleur et ton modèle ?

Hors ligne

 

#14 15-10-2008 13:45:08

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

mon modele, j'ai ceci:

Code:

<?php    
    class Ville extends Zend_Db_Table_Abstract
    {
        protected $_name = 'projet_ville';                      
    }

?>

mon controlleur:

Code:

<?php
class Controller extends AbstractController
{    
    public function init()
   {
        parent::init();
        $request = $this->getRequest();
        
        try 
        {
                $this->ville= new Ville(array('db' => 'db'));
        }
        catch (Zend_Exception $e) 
        {
                throw($e);
        }
   }

private function _getVille($donnee)
{
    $select = $this->ville->select()
   ->from(array('v' => $this->ville), array('v.id_ville', 'v.nom_ville'))
   ->where('v.id_ville= ?', $donnee)

   return $this->ville->fetchAll($select)->toArray();
}

public function IndexAction()
{
            $request = $this->getRequest();

            $this->identifiant= $request->getParam('identifiant');    
            
            $this->view->UneVille = $this->_getVille($this->identifiant);
            
            $this->render();
}
}

quand je fais ceci, il me renvoie l'exception

et quand je fais ceci:

Code:

private function _getVille($donnee)
{
    $select = $this->ville->select()
   ->from($this->ville, array('id_ville', 'nom_ville'))
   ->where('id_ville= ?', $donnee)

   return $this->ville->fetchAll($select)->toArray();
}

ça fonctionne...


Mais pour faire des jointures, j'aurai besoin de faire de nommer mes tables par des initials car des champs seront commun à plusieurs tables

merci d'avance si qqun peut m'eclairer...

Hors ligne

 

#15 15-10-2008 14:00:33

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

Oui, ok, là je vois où est ton problème.

Il faut juste que tu y mettes un peu plus d'ordre, et que tu ne trompes pas entre ton "$this->ville" instance de ton modèle ville, et du "$this->ville" contenant le nom de ta table.

Voici ce que je te propose pour ton contrôleur :

Code:

<?php
class Controller extends AbstractController
{    
    public function init()
   {
        parent::init();
        $request = $this->getRequest();
        
        try 
        {
                $this->ville= new Ville();
        }
        catch (Zend_Exception $e) 
        {
                throw($e);
        }
   }


public function IndexAction()
{
            $request = $this->getRequest();

            $this->identifiant= $request->getParam('identifiant');    
            
            $this->view->UneVille = $this->ville->getVille($this->identifiant);
            
            $this->render();
}
}

Puis pour ton modèle :

Code:

<?php    

    class Ville extends Zend_Db_Table_Abstract
    {
    
        protected $_name = 'projet_ville';         
        protected $_primary = 'id_ville';
        
        public function getVille($donnee)
        {
            $select = $this->_db->select()
                ->from(array('v' => $this->_name), array("v.{$this->_primary}", "v.nom_ville"))
                ->where("v.{$this->_primary} = ?", $donnee)

           return $select->fetchAll();
        }
        
        
    }

Et tu peux sans problème remplacer cette requête par celle que je t'ai donné dans mon deuxième post.

Voilà, normalement, tout devrait jouer wink

Dernière modification par acharrex (15-10-2008 14:01:38)

Hors ligne

 

#16 15-10-2008 14:23:44

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

ce n'est pas possible de garder ma fonction dans le controlleur?

Hors ligne

 

#17 15-10-2008 14:27:22

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

Si si, mais les fonctions autres que les actions se mettent dans le modèle. Enfin, en tout cas par convention...

Et pour que dans ta fonction "getVille" tu puisses utiliser "$this->_db->select()", il faut que ta classe étende Zend_Db_Table.

Donc en mettant "getVille" dans ton modèle, tu es doublement gagnant wink

Hors ligne

 

#18 15-10-2008 14:31:29

Delprog
Administrateur
Date d'inscription: 29-09-2008
Messages: 670

Re: requete avec un IN

Tu n'as aucun intérêt à placer cette méthode dans ton bootstrap, sinon tu ne réponds plus aux conventions du MVC.

Il faut placer les méthodes de tes modèles dans tes classes de modèles, sinon ça devient desuite très difficile à maintenir.

Un controller ne doit avoir un rôle que de Controller et un modèle de Modèle avec toutes ses méthodes qui le définissent et permettent l'accès à ses propres données.


A+ benjamin.


Edit : acharrex a été plus rapide smile

Dernière modification par Delprog (15-10-2008 14:32:50)


http://www.anonymation.com/ - anonymation - Studio de création.
http://code.anonymation.com/ - anonymation - blog - développement et architecture web

Hors ligne

 

#19 15-10-2008 14:32:20

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

et pour ta requete:

Code:

$select = $this->_db->select()
            ->from("ville", array("nom", "description"))
            ->join("ville_in_pays", "ville_in_pays.id_ville = ville.id_ville", array())
            ->join("pays", "pays.id_pays = ville_in_pays.id_pays", array())
            ->where("ville.id_ville IN (".new Zend_Db_Expr($this->_db->select()->from("recompense", array("id_ville"))).")")
            ->where("pays.pays_name LIKE '{$pays}'")
            ->query();

je la place dans le modele de ville?
car comme j'instancie les classes pays et ville_in_pays dans le "constructeur" de mon controleur, il ne les connaitra pas encore il me semble :s
il y a un truc qui m'échappe...


edit: j'ai essayé de faire comme décrit ci-dessus... il me met mnt:

Exception : Zend_Db_Select_Exception Message : Unrecognized method 'fetchAll()'

Dernière modification par Fly706 (15-10-2008 14:52:42)

Hors ligne

 

#20 15-10-2008 15:02:38

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

La classe de ton modèle doit étendre "Zend_Db_Table".

Hors ligne

 

#21 15-10-2008 15:06:52

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

acharrex a écrit:

La classe de ton modèle doit étendre "Zend_Db_Table".

oui comme dit plus haut.
j'ai bien mit : class Ville extends Zend_Db_Table  mais il connait pas fetchAll :s

c'est bien comme cela?


Sinon pour ta requete, je dois la placer dans quel modele?
(car moi je l'aurais mit dans le controleur... mais comme tu as dit, c'est plus clair en la mettant dans le modele)

Hors ligne

 

#22 15-10-2008 15:14:36

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

Tu dois le placer dans ton modèle "Ville", car ce que tu souhaites c'est sélectionner des villes...

Ton modèle doit être :

Code:

<?php    

    class Ville extends Zend_Db_Table
    {
    
        protected $_name = 'projet_ville';         
        protected $_primary = 'id_ville';
        
        public function getVille($donnee)
        {
            $select = $this->_db->select()
                        ->from("ville", array("nom", "description"))
                        ->join("ville_in_pays", "ville_in_pays.id_ville = ville.id_ville", array())
                        ->join("pays", "pays.id_pays = ville_in_pays.id_pays", array())
                        ->where("ville.id_ville IN (".new Zend_Db_Expr($this->_db->select()->from("recompense", array("id_ville"))).")")
                        ->where("pays.pays_name LIKE '{$pays}'")
                        ->query();
                
            echo '<pre>';
            print_r($select->fetchAll());
            echo '</pre>';
        }
        
        
    }

Hors ligne

 

#23 15-10-2008 15:41:40

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

ok ok merci pour le temps consacré ;-)

une petite chose, tu dis que je dois placer ta requete dans le modele ville car je selectionne des villes...

mais si dans ma selection apres jointure, je prend le nom du pays par exemple.
je laisse tjs la fonction dans le modele ville?  il reconnaitra direct le champs nom de la table pays?

Hors ligne

 

#24 15-10-2008 16:22:23

acharrex
Membre
Lieu: Suisse
Date d'inscription: 27-04-2008
Messages: 135

Re: requete avec un IN

Salut,

Si tu fais une jointure de ce type :

Code:

->join("pays", "pays.id_pays = ville_in_pays.id_pays", array("nom"))

Il prendra automatiquement le champ "nom" de la table "pays".

Sinon, il est vrai que ta requête se basent sur plusieurs tables différentes (ville, pays, ville_in_pays, competence). Pour savoir dans quel modèle la placer (pour structurer ton programme, car en fait tu pourrais la mettre n'importe où), il faut que tu saches quel contrôleur va se charger de son appel.

Par exemple, si je veux afficher la liste des membres de mon site et y indiquer le nombre de messages écrits dans le forum, la ville dans laquelle ils habitent etc., je vais créer une requête sélectionnant tous les membres puis faisant une jointure sur la table des villes et sur celles des messages du forum.

Dans dans ce cas, ma requête sera placée dans une fonction du modèle "Liste des membres". Car mon but est de sélectionner les membres puis des informations complémentaires.

Sinon, il faut bien que tu dises que tu n'as pas besoin de créer un modèle étendant Zend_Db_Table pour chacune de tes tables. Avec le "$this->_db->select()->...", tu peux sélectionner autant de champs que tu veux dans autant de tables que tu souhaites.

Voilà, j'espère que c'est assez clair wink

Dernière modification par acharrex (15-10-2008 16:24:22)

Hors ligne

 

#25 15-10-2008 16:28:15

Fly706
Membre
Date d'inscription: 15-10-2008
Messages: 20

Re: requete avec un IN

oui merci bcp wink

Hors ligne

 

Pied de page des forums

Propulsé par PunBB
© Copyright 2002–2005 Rickard Andersson
Traduction par punbb.fr

Graphisme réalisé par l'agence Rodolphe Eveilleau
Développement par Kitpages