Page 1 sur 2

Aide sur simplexml_load_string

Posté : 14 janv. 2011, 14:05
par mctarek
Bonjour. Je teste la fonction simplexml_load_string en utilisant simplement le code
en ligne sur http://fr.php.net/simplexml_load_string
Si le code me retourne bien un objet du flux RSS, ce qui est marqué en dessous de l'exemple,
à savoir: "À partir de là, vous pouvez utiliser $xml->body et tout autre élément"
ne me retourne rien (aucun résultat, aucun message), et idem si je fais $xml->title
Je suis sur PHP 5.2.17
Merci de votre avis.
Note: Cet exercice doit me permettre de comprendre un autre script élaboré pour
lire un flux RSS/AIML. Une autre histoire que j'exposerai plus tard.

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 14:12
par stealth35
fais un var_dump() sur le retour de simplexml_load_string

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 14:22
par mctarek
var_dump donne :

Code : Tout sélectionner

object(SimpleXMLElement)[1] public 'title' => string 'Forty What?' (length=11) public 'from' => string 'Joe' (length=3) public 'to' => string 'Jane' (length=4) public 'body' => string ' I know that's the answer -- but what's the question? ' (length=57)
et print_r (comme dans l'exemple) donne :

Code : Tout sélectionner

SimpleXMLElement Object ( [title] => Forty What? [from] => Joe [to] => Jane [body] => I know that's the answer -- but what's the question? )
J'ai rajouté
echo 'extraction du body'.'<br />';
$xml->body;

echo 'extraction du title'.'<br />';
$xml->title;
J'ai uniquement les messages echo, mais pas l'information de l'objet.

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 14:25
par stealth35
normal faut faire echo $xml->body;

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 14:49
par mctarek
Voilà qui est clair et fonctionnel !

Je vais pouvoir rebondir sur le vif du sujet sur un script intéressant et présent sur le site http://ssm2017.free.fr/index.php/Techni ... abots.html

Pour l'utiliser, il faut activer php_curl [extension=php_curl.dll] avec bug connu sur php 5.2.14,
connaître l'usage de sa fonction sur http://fr.php.net/manual/fr/function.curl-exec.php
connaître simplexml_load_string()
et enfin avoir un bot en ligne pour converser (flux RSS). Ce qui est mon cas.

voici le code adapté à mon bot
<?php
// definition des variables
$uri = "http://www.pandorabots.com/pandora/talk-xml";
$botid = 'bb9d8db85e36d4b9'; // ce bot s'appelle ssm2017 et il me sert de test ( ne vous attendez pas à ce qu'il vous parle de shakespeare )
$input = 'salut';
$custid = '';
 
// construction de la chaine à poster
$post = "botid=$botid&input=$input&custid=$custid";
 
// ouverture d'un "buffer" ( mettre les donnees en cache )
ob_start();
 
// definition des options de curl
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $uri); // uri où aller
// curl_setopt($ch, CURLOPT_HEADER, 0); // ajout
curl_setopt($ch, CURLOPT_TIMEOUT, 9); // arret au bout de 9 secondes si aucune reponse
curl_setopt($ch, CURLOPT_POST, TRUE); // oui monsieur, on envoie des donnees en POST
curl_setopt($ch, CURLOPT_POSTFIELDS, $post); // les donnees à envoyer
curl_setopt($ch, CURLOPT_POSTFIELDSIZE, strlen($post)); // la quantite de donnees à envoyer ( optionnel )
 
// execution de curl
curl_exec($ch);
 
// recuperation du contenu du cache
$string = ob_get_contents();
 
// affichage du message d'erreur si il y en a un
if (curl_errno($ch)) {
   echo "Error: " . curl_error($ch);
   return; // on se casse, on a plus rien à faire ici, ca deconne :)
}
 
// arret de curl
curl_close($ch);
 
// vidage du cache
ob_end_clean();
 
// convertion du resultat en objet xml
$xml = simplexml_load_string($string);
 
// utilisation d'une requete "xpath" pour "pointer" l'element "that"
$result = $xml->xpath('/result/that');
 
// balayage des reponses
while(list( , $node) = each($result)) {
  // affichage du/des resultat(s)
    echo 'that = ',$node,"\n";
}

?>
Le script me donne le message d'erreur : Warning: simplexml_load_string() [function.simplexml-load-string]: Entity: line 2: parser error : Extra content at the end of the document in F:\Program Files\EasyPHP5.2.10\www\bot.php on line 42

Le bot est fonctionnel sur pandorabots, et l'auteur dit obtenir un bon résultat avec mon bot. I am lost !

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 15:01
par stealth35
normalement pas besoin de cURL pour faire ca (et le buffer sert a rien aussi, y'a une option curl pour mettre tout dans une variable...)
$url = 'http://www.pandorabots.com/pandora/talk-xml';

$query = array('botid' => 'c515e91c1e36b68b',
               'input' => 'salut',
               'custid' => '');

$context = stream_context_create(array('http' => array(
                                'method' => 'POST', 
                                'header' => 'Content-type: application/x-www-form-urlencoded',
                                'content' => http_build_query($query))));

libxml_set_streams_context($context);

$xml = simplexml_load_file($url);

var_dump($xml);

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 20:04
par mctarek
whaou... J'étais balloté dans un grand navire avec de nouvelles fonctions, je me retrouve cette fois étourdi avec de nouvelles :-)
Une chose est sûre. Je vois une Terre en vue. Merci mon capitaine.
Ton var_dump($xml) donne un (objet-tableau) avec 2 éléments public (input et that).
C'est suffisant pour voir son entrée, et lire la réponse du Bot.
Mais un 3è élément est indispensable pour pouvoir être reconnu par le Bot, et donc maintenir le fil de la conversation : custid.
Il est généré dès le premier input de l'utilisateur.
Lorsque custid est fixé en value dans : <input type="hidden" name="custid" value=""/> alors le bot maintient la conversation.
(ex: mon nom est Paul, Bonjour Paul, Quel est mon nom, C'est Paul). A défaut : Quel est mon nom, je ne connais pas ton nom.
Je dois donc parvenir à extraire custid de l'objet-tableau puis le fixer en constante dans le value.
Le problème est que même une boucle foreach (tableau ou objet) ne permet point de la récupérer.
Mon code (partiel) + formulaire html pour entrée message est le suivant :
<html>
<head>
<title>Bot mctarek</title>
</head>

<body>
<form method="POST" action="<?php echo $_SERVER['PHP_SELF']; ?>">
<input type="hidden" name="botid" value="bb9d8db85e36d4b9"/>
<input type="hidden" name="custid" value=""/>
<input name="input" type="text" value=""/>
<input name="submit" type="submit"/>
</form>
</body>
</html>

[php]
<?php

// var_dump($_POST);
// exit;


$url = 'http://www.pandorabots.com/pandora/talk-xml';

$query = array('botid' => 'bb9d8db85e36d4b9',
               'input' => @$_POST['input'],
               'custid' => '');

$context = stream_context_create(array('http' => array(
                                'method' => 'POST',
                                'header' => 'Content-type: application/x-www-form-urlencoded',
                                'content' => http_build_query($query)))
								);

libxml_set_streams_context($context);

$xml = simplexml_load_file($url);

var_dump($xml);
echo '<br />';

foreach($xml as $cle=>$valeur)
{
echo $cle.'>'.$valeur.'<br />'; // affiche uniquement input et that - comment récupérer custid?
}

// echo $xml->input;
// echo $xml->that;

?>
[/PHP]

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 20:17
par moogli
yop,

hum a priori faut faire : echo $xml->attributes()->custid;

@+

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 21:03
par mctarek
Mission accomplie !
Je tiens à tous vous remercier car j'ai eu droit à une belle leçon de technicité PHP aujourd'hui.
Mon Bot AIML fonctionne localement et conserve le fil de la discussion.
Je dois travailler sur le retour des caractères (ex: Quel âge as tu?) alors que tout est Ok
sur pandorabots. A voir chez free.fr aussi. Si vous avez un dernier avis, je suis preneur. A défaut, no problem.
Bonne soirée.
mctarek

Re: Aide sur simplexml_load_string

Posté : 14 janv. 2011, 21:19
par stealth35
vérifie que tout est en utf-8
faq-tutoriels/encodage-utf-t245062.html

:wink:

Re: Aide sur simplexml_load_string

Posté : 15 janv. 2011, 08:34
par mctarek
Voilà donc la touche finale d'une équipe formidable!
Tout est opérationnel avec les bons caractères.

En étudiant le code, on a l'impression que tout vient
du

Code : Tout sélectionner

$xml = simplexml_load_file($url);
et que $query et $context sont inutiles. Il y a bien un lien
implicite entre

Code : Tout sélectionner

libxml_set_streams_context($context);
et

Code : Tout sélectionner

simplexml_load_file($url);
J'en ai encore le vertige !

Mon forum sur AIML: http://mctarek2.free.fr/phorum/list.php?8

Re: Aide sur simplexml_load_string

Posté : 15 janv. 2011, 16:12
par stealth35
libxml_set_streams_context t'ouvre un context sur la prochaine ouverture d'un XML, c'est dans se contexte qu'on a mis les paramètres de POST :wink:
si tu le met pas ca va ouvrir l'url sans y mettre de parametres

Re: Aide sur simplexml_load_string

Posté : 15 janv. 2011, 17:01
par mctarek
Merci. Mon problème étant à 100% résolu, je me demande pourquoi ne pas avoir continué avec CURL
comme dans le premier script. En fait, j'essaie de comprendre la portée pratique de Curl comme je viens
de comprendre la portée pratique de simplexml.
mctarek

Re: Aide sur simplexml_load_string

Posté : 15 janv. 2011, 17:28
par stealth35
Merci. Mon problème étant à 100% résolu, je me demande pourquoi ne pas avoir continué avec CURL
comme dans le premier script. En fait, j'essaie de comprendre la portée pratique de Curl comme je viens
de comprendre la portée pratique de simplexml.
mctarek
cURL est utilisé par ignorance des contextes de stream. C'est utilise pour certain cas mais ici non, d'ailleurs si tu regardes bien cURL ne fais que mettre le contenu de la page dans une variable qui est ensuite lu par simpleXML, alors qu'en stream on lit directement l'URL.

si tu veux la version cURL c'est pas si diffèrent ca donne ca :
$url = "http://www.pandorabots.com/pandora/talk-xml";

$query = array('botid' => 'c515e91c1e36b68b',
               'input' => 'salut',
               'custid' => '');
 
$ch = curl_init();
curl_setopt_array($ch, array(CURLOPT_URL            => $url,
                             CURLOPT_RETURNTRANSFER => true,
                             CURLOPT_POST           => true,
                             CURLOPT_POSTFIELDS     => http_build_query($query)));
 
$string = curl_exec($ch);
curl_close($ch);

$xml = simplexml_load_string($string);

var_dump($xml);
:wink:

Re: Aide sur simplexml_load_string

Posté : 15 janv. 2011, 20:43
par mctarek
whaou. Tu n'es pas Ganesha pour rien stealth35 !
Le deuxième exemple est parfaitement fonctionnel
comme le précédent. J'ai matière à travail pour plusieurs jours.
Avec mes 3 mois d'expérience sur PHP, je suis fortement encouragé à continuer dans
ce sens, tant ce langage répond à mes attentes.
Avec ta permission, je souhaite reproduire les 2 exemples
sur mon forum traîtant d'AIML/Pandorabots, tout en citant ce forum...bien sûr.
mctarek
Bot: bb9d8db85e36d4b9