Récupérer un élément particulier d'une page HTML
orfait
Membre
Bonjour,
je suis depuis quelques temps en train de chercher à récupérer le contenu de la balise <title> d'une page web. J'ai trouvé un exemple fourni par Apple qui parvient à faire un listing des balises mais le code est très obscur... (DOMTreeView).
Donc si quelqu'un a une réponse, un exemple, une voie de recherche, je suis preneur.
Si je trouve, je mettrai ma réponse ici.
Merci !
EDIT : précision très importante : je souhaite faire ceci sans utiliser de WebView et j'ai vu sur les list apple : "WebKit does not support loading viewless data sources.". Je pense que ma question a plus de sens avec ce détail.
je suis depuis quelques temps en train de chercher à récupérer le contenu de la balise <title> d'une page web. J'ai trouvé un exemple fourni par Apple qui parvient à faire un listing des balises mais le code est très obscur... (DOMTreeView).
Donc si quelqu'un a une réponse, un exemple, une voie de recherche, je suis preneur.
Si je trouve, je mettrai ma réponse ici.
Merci !
EDIT : précision très importante : je souhaite faire ceci sans utiliser de WebView et j'ai vu sur les list apple : "WebKit does not support loading viewless data sources.". Je pense que ma question a plus de sens avec ce détail.
Connectez-vous ou Inscrivez-vous pour répondre.
Réponses
Si ton document est compliqué, voir le tuto sur XML.
sinon le faire à la main par manip de chaà®ne ne devrait pas être compliqué à partir du source de la page HTML.
désolé, j'avais pas lu, ma réponse est à côté.
mais en même comme tu parles d'un exemple fourni par Apple réalisant une arborescence à partir de la page Web, il y a un peu contradiction ...
Ton lien m'a beaucoup intéressé mais je crois que ce n'est pas adapté... enfin, je lis car il n'y a pas qu'une seule page
En revanche, je crois que je n'ai pas le choix que d'utiliser un WebView (masqué) si je veux rester avec le webkit.
Tu as toujours le choix.
Mais, en passant par le webkit, tu fais faire une bonne partie du travail par ce framework (récupérer le contenu de la balise <TITLE> du doc html n'est pas toujours suffisant : imagine que ce titre soit mis par javascript...).
Effectivement, un petit webview non affiché est suffisant.
Par exemple, tu peux mettre ce webview dans un nib tout seul.
Ensuite, tu charges le nib (et donc instancie le webview), puis tu utilises le webview pour charger la page et puis lire son titre. Enfin tu peux décharger le nib.
Voici un exemple (l'outlet du webview se nome wb).
Il faut charger la page :
Ensuite, il faut utiliser une méthode delegate qui se déclenche quand la page a fini d'être chargée :
(il faut connecter le delegate FrameLoadDelegate à l'objet contrôleur).
.
Bah le plus simple (mais p-ê pas le plus propre) c'est de faire une regex... C'est ce que je fais, pas besoin de resortire tout l'apareil XML compliquer...
Voici une page html :
[tt]
<html>
<head>
<script language="javascript">var unTitre='joli titre';</script>
<style>
body { background-color: yellow; }
</style>
</head>
<body onload="javascript:document.title=unTitre">
bla bla
</body>
</html>
[/tt]
Tu fais comment avec ton regex pour récupérer le titre ?
.
Bah en même temps XML est simple, sauf si le titre est masqué dans le doc comme le montre l'exemple de Bru :
#import <Cocoa/Cocoa.h>
int main(int argc, char * argv[] ){
NSAutoreleasePool * pool=[NSAutoreleasePool new];
NSError * error;
// création du document
NSString * xmlString=[NSString stringWithUTF8String:
"<html> \
<head>\
<script language='javascript'>var unTitre='joli titre';</script> \
<style> \
body { background-color: yellow; }\
</style>\
</head>\
<body onload=\"javascript:document.title=unTitre\">\
bla bla\
</body>\
</html> "];
NSXMLDocument * xmlDoc;
xmlDoc=[[NSXMLDocument alloc] initWithXMLString:xmlString
options:NSXMLNodePreserveWhitespace|NSXMLNodePreserveCDATA
error:&error];
// lecture de ce que l'on veut : par exemple le style
NSArray * nodes;
nodes=[[xmlDoc rootElement] nodesForXPath:@//style/text() error:&error];
if(error){
NSLog(@%@",error);
}else{
printf("%s\n",[[nodes description] UTF8String]);
}
[xmlDoc release];
[pool release];
return 0;
}
/<html>.*<body onload="javascript:document.title=(.*)">.*/ $1
Biiiip, vous avez perdu... Recommencez encore une fois !
(le regex va ramener le mot unTitre, qui est une variable javascript contenant elle même la valeur "joli titre").
.
D'une part ça ne marche pas tout à fait parce que ça récupère "unTitre" qui est le nom d'une variable javascript et non pas une string litérale (d'ailleurs je soupçonne fort Bru d'avoir fait exprès de mettre ça comme page HTML en prévision que tu ferais l'erreur ^^)
D'autre part parce que le but est de récupérer le titre de la page dans tous les cas imaginables. Par dans le cas particulier où il est dans <title> uniquement, et s'il est fixé en javascript il peut l'être de plein de manières différentes (le onload pouvant appeler une fonction javascript par exemple init(), et c'est dans le init() qu'en plein milieu on a un [tt]document.title = xxx[/tt], où xxx peut être une variable, un string litteral, ou même un appel de fonction, et que sait-je encore.
bref tu ne pourras jamais prévoir tous les cas.
Et puis la question n'est pas tant de savoir si ça n'est que 10 ou 15% des pages qui font ça ou pas, mais de prévoir tous les cas, non ?
Et donc de préférer une solution qui donne le vrai titre en autant de lignes qu'une autre solution ne fonctionnant pas à tous les coups.
D'autant que Cocoa ne permet pas de faire des RegEx de base (bon ok un peu avec les NSPredicate, soyons honnêtes, mais bon), donc il faut pour bien faire rajouter un framework les gérant.
Mais je cherchais une solution très "simpliste" et sans devoir charger un "affichage" de page. Ceci dit, ma question serait plutôt de savoir si les ressources utilisées pour un webview masqué sont aussi "importantes" qu'avec un webview affiché.
En fait, je me disais : "il doit sûrement exister un moyen pour éviter d'avoir à "intepréter" le code HTML en vue d'un affichage... je ne veux avoir le contrôle que sur le code... inutile d'afficher."
Voilà , je pense que la méthode indiquée par Bru est la bonne et je vais m'y tenir. J'espère que mon remue-ménage n'a pas dérangé... je ne pensais provoquer tant de réponses !
Bon si le unTitre est setté à un endroit qui pourrait être n'importe ou, c'est vrai que c'est pas possible, mais c'est un cas rarisime... la plupart du temps, le titre est setté dans le HTML en utilisant <title> dans quel cas une regex suffit (/.*<head>.*<title>(.*)<.title>.*<.head>.*/) (c'est pas propre, mais ça fonctionne)
Ce que je veux dire, c'est que dans la majorité des cas 99% du temps, il est inutile de faire 50 lignes de code XML quand une regex (3 lignes de code) suffit.
Je suis sur que vous connaisez KISS?