Contrôle de présence d'une balise dans un flux XML


Mountain Magazin
WRInaute impliqué
WRInaute impliqué
 
Messages: 598
Inscription: 1 Oct 2004

Contrôle de présence d'une balise dans un flux XML

Message le Ven Oct 23, 2009 23:25

Salut,

J'ai un souci qui me prend la tête depuis plusieurs jours.

dans le cadre d'un projet, je vais permettre à tous de charger un flux XML à travers un formulaire. Pas de souci, je contrôle si l'URL est accessible, s'il s'agit bien d'un flux... mais comme tout le monde risque de soumettre un peu tout et n'importe quoi, je dois aussi m'assurer que la structure du flux est bonne avec la présence des balises title, link et description

Mon souci, impossible de contrôler si mes trois balises sont bien présentes. Voici mon code, qui pourra peut être en aider certains :
Code: Tout sélectionner
//-- Nombre maximum de lignes qui s'affichent sur votre site
$max_lignes = 1;

$adresse_flux = $_POST['urlrss']; //-- Adresse complète du flux RSS.

//-- Nom des Balises à afficher dans le résumé du flux ( voir (1) )
$balises = array('title', 'link', 'description');


function readFeedCurl ( $url, $objets, $nb_items ) {

   $msg_error = 'Erreur';

   $curl = curl_init();
   curl_setopt($curl, CURLOPT_URL, $url);
   curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
   $data = curl_exec ($curl);
   curl_close ($curl);

   if ( !empty ( $data ) ) {

      $pos = strpos ( $data, '<?xml version="1.0" encoding="utf-8"?>' );

      if ( $pos === false ) {

           echo utf8_encode ( $msg_error );

      }

      else {

         @$xml = new simpleXMLElement ( $data );

         $i = 0;
         $resultat = array();

         //-- On boucle pour récupérer les différents <item>
         foreach ( $xml -> channel -> item as $item ) {

            //-- On boucle pour automatiser les récupération des balises en fonction du tableau
            foreach ( $objets as $objet ) {

               $resultat[$i][$objet] = $item->$objet;

               if ( $resultat[$i][$objet] ) { return true; }
                  else {
                     echo utf8_encode ( $msg_error );
                     break;
                  }

            }

            $i++;

            if ( $i > $nb_items ) { break; }

         }

         if ( empty ( $resultat[0] ) ) { echo utf8_encode ( $msg_error ); }

      }

   }

   else {

      echo utf8_encode ( $msg_error );

   }

}


C'est au niveau de ces lignes que je ne sais pas comment vérifier si la balise existe ou non :
Code: Tout sélectionner
début des soucis      if ( $resultat[$i][$objet] ) { return true; }
                  else {
                     echo utf8_encode ( $msg_error );
                     break;
Fin des soucis            }

Pour le reste, tout est ok. Je veux pas que tout parte en sucette si au lien d'utiliser les balises standard, un flux utilise des balises maison du type "titre", "lien" et "texte", ce qui rendrait le parsing problématique.

Je précise qu'il s'agit bien entendu de flux distants qui ne sont pas les miens, sinon, je ne me poserait même pas la question de la conformité du balisage.

Si vous avez la soluce, merci.


nza2k
WRInaute impliqué
WRInaute impliqué
 
Messages: 771
Inscription: 16 Jan 2004

Re: Contrôle de présence d'une balise dans un flux XML

Message le Sam Oct 24, 2009 15:37

Je ne suis pas expert en flux xml, mais peut-être peux-tu contourner le pbm de la façon suivante :

Dans ton formulaire, tu dis explicitement que, par défaut, tu interroges telles et telles balises. Si ces balises sont absentes du flux, tu invites les utilisateurs à saisir les balises correspondantes qu'ils utilisent dans leurs flux. Ensuite, tu adaptes automatiquement le script qui parse ce flux.


Mountain Magazin
WRInaute impliqué
WRInaute impliqué
 
Messages: 598
Inscription: 1 Oct 2004

Re: Contrôle de présence d'une balise dans un flux XML

Message le Sam Oct 24, 2009 16:26

Salut,

Je te remercie de ta réponse. L'idée est pas mauvaise, mais comme souvent, ça complexifie les inscriptions et les utilisateurs risquent de renseigner n'importe quoi.

Un principe auquel je tiens : ne jamais faire confiance à la saisie utilisateur (pas l'utilisateur, sa saisie hein !).

D'autre part, je pense qu'un certain nombres d'utilisateurs de flux, notamment avec les CMS et autres projets open source, je savent pas comment s'articule leurs flux.

A la limite, il faut mieux juste contrôler que l'URL est valide et répond, et vérifier ensuite manuellement la validité du flux. Mais c'est une perte de temps dans la mesure où l'on peut le faire automatiquement. Une vérif manuelle du flux n'apporte aucune plus value, mieux vaut consacrer ce temps à du travail rédactionnel par exemple.

Merci quand même d'avoir pris le temps de répondre. Si quelqu'un a une soluce, j'ai toujours pas trouvé.


Mountain Magazin
WRInaute impliqué
WRInaute impliqué
 
Messages: 598
Inscription: 1 Oct 2004

Re: Contrôle de présence d'une balise dans un flux XML

Message le Lun Oct 26, 2009 15:39

Personne n'a eu le problème alors ? :cry:

Je suis quand même pas le seul à vouloir m'assurer du format des balises qui constituent un document XML ?

calligan
Nouveau WRInaute
Nouveau WRInaute
 
Messages: 9
Inscription: 16 Sep 2009

Re: Contrôle de présence d'une balise dans un flux XML

Message le Mar Oct 27, 2009 5:51

Je vois pas pourquoi tu te prend le curl :lol: : ( et aussi tu utilise curl), je pense que tu doit tout simplement parser ton xml avec du dom voila un exemple

Code: Tout sélectionner
$dom = new DOMDocument();
                        if (!$dom->load($gurl)) {
                            die('Impossible de charger le fichier XML');
                        }
                       
                        // root node product
                        $itemList = $dom->getElementsByTagName('product');
                        foreach ($itemList as $item) {
                           
                            // prend la section name
                            $titre = $item->getElementsByTagName('name');
                            // si le noeud existe
                            if ($titre->length > 0) {
                                $pTitre= $titre->item(0)->nodeValue;
                            } else {
                             // la tu met ce que tu veux
                             }
                       
                        }


sinon pour d'autre détails c'est par la

http://php.net/manual/en/domdocument.getelementsbytagname.php


Mountain Magazin
WRInaute impliqué
WRInaute impliqué
 
Messages: 598
Inscription: 1 Oct 2004

Re: Contrôle de présence d'une balise dans un flux XML

Message le Mar Oct 27, 2009 13:37

Salut,

Merci de ta réponse, je n'avais pas pensé à passer par l'arbre Dom, impeccable, bouclé en deux minutes. Je ne voyais pas l'évidence. Pour ceux que ça intéresse, voici la fonction complète :

Cette fonction permet de tester le format et la disponibilité d'un flux XML qui serait soumis par exemple via un formulaire sur un annuaire ou autre site. Si vous avez décider de parser uniquement des flux qui comportent les balises standard (ou autres balises, selon votre choix), voici comment vérifier que le flux soumis respecte vos contraintes.

Code: Tout sélectionner
   //-- Zone de paramétrage------->

   $adresse_flux = http://www.example.com/flux.xml; //-- Adresse complète du flux RSS.
   $balises = array ( 'title', 'link', 'description' ); //-- Nom des Balises à parser )

   $msg_error = '<li>Votre message d'erreur</li>';

   if ( !readFeedDom ( $adresse_flux, $balises ) ) {
      echo utf8_encode ( $msg_error );
   }

function readFeedDom ( $url, $objets ) {

   $dom = new DOMDocument();

   if ( @!$dom -> load ( $url ) ) {
      return false;
   }
                       
   // root node product
   $itemList = $dom->getElementsByTagName('item');

   foreach ( $itemList as $item ) {
                           
      foreach ( $objets as $objet ) { //-- On boucle pour automatiser les récupération des balises en fonction du tableau

         $resultat[$objet] = $item -> getElementsByTagName ( $objet );

         if ( $resultat[$objet] -> length > 0 ) {}
            else {
               return false;
               break;
            }

      }

      return true;

   }

}

Vous pouvez adapter la fonction pour que au lieu d'afficher un message comme quoi le flux est conforme, lire directement le flux ou donner un ordre d'insertion en base de données.

A vous de voir. Et merci à calligan pour cette piste que j'avais complètement négligé :wink:


Si vous avez aimé cette discussion, partagez-la sur vos réseaux sociaux préférés :

Lectures recommandées sur ce thème :



Qui est en ligne

Utilisateurs parcourant ce forum: Aucun utilisateur enregistré et 1 invité