Précédent   Forum du club des développeurs et IT Pro > Autres langages > XML/XSL et SOAP > XQUERY/SGBD
XQUERY/SGBD Le langage XQUERY et tout ce qui a trait aux relations XML et bases de données : BDD XML native, intégration/extraction de XML, XML dans BDD relationnelle... Avant de poster -> FAQ XML, Sources XML
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse
 
Outils de la discussion
Publicité
'
Vieux 04/05/2012, 17h53   #1
jbidou88
Membre actif
 
Avatar de jbidou88
 
Inscription : avril 2006
Messages : 493
Détails du profil
Informations forums :
Inscription : avril 2006
Messages : 493
Points : 190
Points : 190
Par défaut Problème requête avec récupération de variables via post

Bonjour,

Je souhaite faire une recherche sur des annonces, j'ai donc un formulaire avec quelques critères de recherche :

Code :
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
<div id="content">
	           <form method="post" action="recherche.xql">
            		<p>
            		  <label>Marque :</label>
            		  <select name="make" id="make">
            		      <option value="">Tous...</option>
            		          {
                                    let $annonces := collection("annonces/Simple")
                                    for $make in distinct-values($annonces/ns:Ad/ns:Make)
                                    return <option value="{data($make)}">{data($make)}</option>
                                } 
                        </select>
                    </p>
                    <p>
                    <label>Modèle :</label>
                    <input type="text" name="model" id="model" />
                    </p>
                    <p>
                    <label>Prix :</label>
                    <select name="prixMin" id="prixMin">
                        <option value="">Tous...</option>
                        <option value="0">0 CHF</option>
                        <option value="1000">1000 CHF</option>
                        <option value="2000">2000 CHF</option>
                        <option value="5000">5000 CHF</option>
                        <option value="10000">10000 CHF</option>
                        <option value="20000">20000 CHF</option>
                        <option value="30000">30000 CHF</option>
                        <option value="40000">40000 CHF</option>
                        <option value="50000">50000 CHF</option>
                        <option value="100000">100000 CHF</option>
                        <option value="200000">200000 CHF</option>
                        <option value="300000">300000 CHF</option>
                    </select>
                    à
                    <select name="prixMax" id="prixMax">
                        <option value="">Tous...</option>
                        <option value="0">0 CHF</option>
                        <option value="1000">1000 CHF</option>
                        <option value="2000">2000 CHF</option>
                        <option value="5000">5000 CHF</option>
                        <option value="10000">10000 CHF</option>
                        <option value="20000">20000 CHF</option>
                        <option value="30000">30000 CHF</option>
                        <option value="40000">40000 CHF</option>
                        <option value="50000">50000 CHF</option>
                        <option value="100000">100000 CHF</option>
                        <option value="200000">200000 CHF</option>
                        <option value="300000">300000 CHF</option>
                    </select>
                    </p>
                    <p>
            		  <label>Carburant :</label>
            		  <select name="carburant" id="carburant">
            		      <option value="">Tous...</option>
            		          {
                                    let $annonces := collection("/db/annonces/Simple")
									for $carb in distinct-values($annonces/ns:Ad/ns:GeneralData/ns:Motorization)
									order by $carb 
									return <option value="{data($carb)}">{data($carb)}</option>
                                } 
                        </select>
                    </p>
                     <p>
            		  <label>Statut :</label>
            		  <select name="statut" id="statut">
            		      <option value="">Tous...</option>
            		          {
                                    let $annonces := collection("/db/annonces/Simple")
									for $status in distinct-values($annonces/ns:Ad/ns:GeneralData/ns:Status)
									order by $status 
									return <option value="{data($status)}">{data($status)}</option>
                                } 
                        </select>
                    </p>
                    <p>
                    	<input type="submit" value="Rechercher" />
                    </p>
                </form>
            </div>
Ensuite je souhaite afficher les annonces qui correspondent à mes critères de recherche :

Code :
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
xquery version "1.0" encoding "utf-8";
 
declare default element namespace "http://www.w3.org/1999/xhtml";
declare namespace ns = "http://ns.clic.ch/cours/XML/AdVehicleSimple";
declare option exist:serialize "method=xhtml media-type=text/html omit-xml-declaration=yes encoding=utf-8 indent=yes doctype-public=-//W3C//DTD&#160;XHTML&#160;1.0&#160;Strict//EN doctype-system=http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd";
declare variable $make := (request:get-parameter('make', ''));
declare variable $model := (request:get-parameter('model', ''));
declare variable $prixMin := (request:get-parameter('prixMin', ''));
declare variable $prixMax := (request:get-parameter('prixMax', ''));
declare variable $carburant := (request:get-parameter('carburant', ''));
declare variable $statut := (request:get-parameter('statut', ''));
 
<html>
	<head>
		<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 
		<title>Index</title>
 
		<link rel="stylesheet" type="text/css" href="css/stylesheet.css" media="screen" />
 
		<script type="text/javascript" src="js/fonctions.js"></script>
	</head>
	<body>
	   <div id="main">
	       <div id="header">
	           <h1>Annonce(s)</h1>
	       </div>
	       <div id="content">
	       		<p>{request:get-parameter('make', '')}</p>
	       		<p>{request:get-parameter('model', '')}</p>
	       		<p>{request:get-parameter('prixMin', '')}</p>
	       		<p>{request:get-parameter('prixMax', '')}</p>
	       		<p>{request:get-parameter('carburant', '')}</p>
	       		<p>{request:get-parameter('statut', '')}</p>
 
            </div>
            <div class="annonce">
					let $annonces := collection("annonces/Simple")
					let $where := concat("1=1",
					if($make != "") then concat("and $ad/ns:Make =", $make) else (),
					if($model != "") then concat("and $ad/ns:Model =", $model) else (),
					if($prixMin != "") then concat("and $ad/ns:GeneralData/ns:Amount >", $prixMin) else (),
					if($prixMax != "") then concat("and $ad/ns:GeneralData/ns:Amount <", $prixMax) else (),
					if($carburant != "") then concat("and $ad/ns:GeneralData/ns:Motorization =", $carburant) else (),
					if($statut != "") then concat("and $ad/ns:Status =", $statut) else ())
					for $ad in $annonces/ns:Ad
					where ($where)
					return
					(<img src="{data($ad/ns:Image)}" alt="{data($ad/ns:Make)}"/>,
					<p>{data($ad/ns:Make)}</p>,
					<p>{data($ad/ns:Model)}</p>,
					<p>{data($ad/ns:GeneralData/ns:Status)}</p>,
					<p>{data($ad/ns:GeneralData/ns:Cm3)} cm3</p>,
					<p>{data($ad/ns:GeneralData/ns:Transmission)}</p>,
					<p>{data($ad/ns:GeneralData/ns:Motorization)}</p>,
					<p>{data($ad/ns:GeneralData/ns:Km)} KM</p>,
					<p>{data($ad/ns:GeneralData/ns:Amount)} CHF</p>)
			</div>
Le problème est le suivant, j'ai une parse error mais impossible de trouver où :

Code :
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
Error found
 
err:XPST0003: Parse error: element name containing whitespace: unexpected token: , $prixMax) else (),
if($carburant != ") then concat( at line: 43 column: 107
 
Java Stack Trace:
Class Name	Method Name	File Name	Line
org.exist.xquery.parser.XQueryParser	elementConstructor	XQueryParser.java	8607
org.exist.xquery.parser.XQueryParser	elementContent	XQueryParser.java	10052
org.exist.xquery.parser.XQueryParser	mixedElementContent	XQueryParser.java	9665
org.exist.xquery.parser.XQueryParser	elementWithAttributes	XQueryParser.java	9520
org.exist.xquery.parser.XQueryParser	elementConstructor	XQueryParser.java	8589
org.exist.xquery.parser.XQueryParser	elementContent	XQueryParser.java	10052
org.exist.xquery.parser.XQueryParser	mixedElementContent	XQueryParser.java	9665
org.exist.xquery.parser.XQueryParser	elementWithAttributes	XQueryParser.java	9520
org.exist.xquery.parser.XQueryParser	elementConstructor	XQueryParser.java	8589
org.exist.xquery.parser.XQueryParser	elementContent	XQueryParser.java	10052
org.exist.xquery.parser.XQueryParser	mixedElementContent	XQueryParser.java	9665
org.exist.xquery.parser.XQueryParser	elementWithoutAttributes	XQueryParser.java	9612
org.exist.xquery.parser.XQueryParser	elementConstructor	XQueryParser.java	8594
org.exist.xquery.parser.XQueryParser	elementContent	XQueryParser.java	10052
org.exist.xquery.parser.XQueryParser	mixedElementContent	XQueryParser.java	9665
org.exist.xquery.parser.XQueryParser	elementWithoutAttributes	XQueryParser.java	9612
org.exist.xquery.parser.XQueryParser	elementConstructor	XQueryParser.java	8594
org.exist.xquery.parser.XQueryParser	directConstructor	XQueryParser.java	7302
org.exist.xquery.parser.XQueryParser	primaryExpr	XQueryParser.java	7001
org.exist.xquery.parser.XQueryParser	filterStep	XQueryParser.java	6147
Avez-vous une idée de ce qui peut être faux ?

Merci beaucoup pour votre aide
jbidou88 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 04/05/2012, 20h15   #2
Ziki_s
Invité(e)
 
Messages : n/a
Détails du profil
Informations forums :
Messages : n/a
Points : 0
Je ne sais pas exactement où est ton erreur, mais tu devrais déjà mettre tes variables $make et $model entre des apostrophes, comme ceci:

Code :
1
2
3
 
if($make != "") then concat("and $ad/ns:Make = '", $make, "'") else (),
if($model != "") then concat("and $ad/ns:Model = '", $model, "'") else (),
  Envoyer un message privé Réponse avec citation 00
Vieux 04/05/2012, 20h58   #3
jbidou88
Membre actif
 
Avatar de jbidou88
 
Inscription : avril 2006
Messages : 493
Détails du profil
Informations forums :
Inscription : avril 2006
Messages : 493
Points : 190
Points : 190
Merci pour votre conseil, j'ai fait ça pour toutes les chaînes de texte. Mais toujours la même erreur.
jbidou88 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 05/05/2012, 19h32   #4
tsuji
Membre chevronné
 
Inscription : octobre 2011
Messages : 412
Détails du profil
Informations forums :
Inscription : octobre 2011
Messages : 412
Points : 675
Points : 675
Je vois la construction de div effectivement souffre d'erreur multiple.

[1] La syntaxe de div ne respecte pas bien la syntaxe de constructeur d'élément au sens de xquery. Il manque de bretelles englobantes, n'est-ce pas?

[2] Je vois un peu ce que vous voulez faire pour $where. Même si la façon de faire "where ($where)" est faisable - ce qui n'est exactement pas - il est erroné à maints endroits, comme par exemple manquant un espace devant 'and', comme par exemple qu'il n'est pas correct d'utiliser else() parce que ça peut conduire à une structure comme concat(x,,y,) - ce qui est une erreur.

[3] La construction "where ($where)" n'est pas valable. La raison est simple: "where a=b" n'est pas la même que "where 'a=b'". Dans le cas-ci, même une certaine extension comme saxon:evaluate() ne peut pas le sauver pour des raisons de difficulté très technique. Bref, l'approche me semble tout à fait méconçue.

Voici ce que je souhaite de réécrire de ce bloque pour garder au moins quelque chance de succès.
Code :
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
    <div class="annonce">
    {
        let $annonces := collection("annonces/Simple")
        for $ad in $annonces/ns:Ad
        where (
            (if($make != "") then $ad/ns:Make = $make else fn:true())
            and
            (if($model != "") then $ad/ns:Model = $model else fn:true())
            and
            (if($prixMin != "") then $ad/ns:GeneralData/ns:Amount > $prixMin) else fn:true())
            and
            (if($prixMax != "") then $ad/ns:GeneralData/ns:Amount < $prixMax else fn:true())
            and
            (if($carburant != "") then $ad/ns:GeneralData/ns:Motorization = $carburant else fn:true())
            and
            (if($statut != "") then $ad/ns:Status = $statut else fn:true())
        )
        return (
            <img src="{data($ad/ns:Image)}" alt="{data($ad/ns:Make)}"/>,
            <p>{data($ad/ns:Make)}</p>,
            <p>{data($ad/ns:Model)}</p>,
            <p>{data($ad/ns:GeneralData/ns:Status)}</p>,
            <p>{data($ad/ns:GeneralData/ns:Cm3)} cm3</p>,
            <p>{data($ad/ns:GeneralData/ns:Transmission)}</p>,
            <p>{data($ad/ns:GeneralData/ns:Motorization)}</p>,
            <p>{data($ad/ns:GeneralData/ns:Km)} KM</p>,
            <p>{data($ad/ns:GeneralData/ns:Amount)} CHF</p>
        )
    }
    </div>
Je ne peux évidemment pas la tester pour les cas concrets pour une raison évidente, et il se peut y avoir des typos aussi - mais, c'est le plan d'ensemble général que je serais écrit au premier temps avant tester.
tsuji est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 05/05/2012, 23h18   #5
jbidou88
Membre actif
 
Avatar de jbidou88
 
Inscription : avril 2006
Messages : 493
Détails du profil
Informations forums :
Inscription : avril 2006
Messages : 493
Points : 190
Points : 190
Merci beaucoup pour vos très bonnes explications, cela fonctionne !
jbidou88 est déconnecté   Envoyer un message privé Réponse avec citation 00
Réponse Cette discussion est résolue.
Outils de la discussion

Navigation rapide


Fuseau horaire GMT +2. Il est actuellement 14h05.


 
 
 
 
Partenaires

Hébergement Web