Developpez.com - Développement Web
X

Choisissez d'abord la catégorieensuite la rubrique :


Technique du Partial Update ou "Comment mettre à jour dynamiquement une partie d'une page web"

Date de publication : 25/11/2005 , Date de mise à jour : 25/11/2005


I. Présentation
II. Fonctionnement
III. Exemple de page utilisant la technique du Partial Update
IV. Avantages de la technique du partial update
V. Comparatif avec / sans la technique du Partial Update
VI. Implémentation
VI. Utilisations diverses
VIII. Exemple d'utilisation
IX. Conclusion


I. Présentation

La technique du Partial Update permet, comme son nom l'indique de faire des mises à jour partielles d'une page web, le tout sans aucun scintillement de la page.

Il est ainsi possible d'afficher une page au fur et à mesure des besoins mais le partial update ne s'arrête pas là. Nous verrons quelques unes des autres possibilités qu'offre la technique.

Le gain de temps, mais également la diminution de la taille des informations transférées, à l'aide de cette technique peut être conséquent selon le nombre de mises à jour partielles. A l'inverse, certaines utilisations de la technique peuvent rendre l'affichage de la page plus lent et plus coûteux en taille d'informations transférées. Nous verrons dans quels cas il est opportun d'utiliser la technique du partial update et dans quels cas il est préférable de l'éviter.

Côté client, cette technique utilise du JavaScript pour effectuer les demandes et pour manipuler le DOM (Document Object Model) du fichier HTML. Côté serveur, il s'agit d'utiliser n'importe quel "language serveur".

Cette technique a été présentée par l'équipe de développement de XMLRAD lors de la conférence de décembre 2004.

Il existe d'autres techniques que celle présentée dans ce document. On peut principalement citer l'utilisation de XmlHttpRequest pour lequel vous trouverez certainement un article sur fr developpez.com dans un futur proche. Cependant les principes restent les mêmes, seules les techniques différent.


II. Fonctionnement

La technique du partial update utilise un ou plusieurs iframes cachés ainsi que du JavaScript.

Concrètement, une iframe, l'abréviation de " inline frame ", permet de charger un document HTML ou XHTML au sein même d'un autre document HTML comme on le ferait dans une frame classique. La seule différence entre les deux est que l'iframe ne peut pas être redimensionné par l'utilisateur contrairement à la frame.

Le rafraîchissement de la page que l'on souhaite éviter s'effectue en fait dans l'iframe. Vu que cet iframe est caché, le rafraîchissement est invisible pour l'utilisateur.

Le JavaScript est utilisé pour effectuer les différents appels de page et pour manipuler les éléments des pages HTML.

Le fonctionnement d'une mise à jour partielle est le suivant :

- Un événement quelconque (1) permet l'appel d'une fonction JavaScript (2)
- Chargement d'une page dans l'iframe caché (3). Cette page peut dès lors effectuer un traitement sur des informations passées par la méthode POST (formulaire classique) ou la méthode GET (passage d'arguments dans l'url). Ce traitement peut être, par exemple, l'ajout des informations dans une source de données quelconque ou encore un questionnement de cette même source de données (4) ou simplement un calcul
- Affichage de la page dans l'iframe (5). Cette page peut être vierge si aucun information ne doit être récupérée, ce qui est rarement le cas. Effectivement, même si il ne s'agit pas d'afficher des données proprement dites, la page contient généralement un appel à une fonction JavaScript, cette fonction permettant de signaler à l'utilisateur si l'action s'est bien effectuée ou non.
- Mise à jour de la page (6) à l'aide de fonctions JavaScript. Suivant l'utilité, le script de traitement peut se trouver soit dans la page soit dans l'iframe.


III. Exemple de page utilisant la technique du Partial Update

L'exemple présenté ici se contente de charger une page dans l'iframe à l'aide d'une fonction JavaScript appelée par un lien hypertexte. L'utilisation du JavaScript pour ce chargement n'est pas nécessaire, un simple lien aurait suffit mais le but de l'exemple était de montrer que d'autres opérations pouvaient au préalable être effectuées.

La deuxième étape se déclenche lorsque la page est chargée dans l'iframe. Celle-ci appelle une fonction, contenue dans la page courante, qui se charge de copier le contenu de l'iframe dans le div que nous avons créé dans cette page.
ExempleSimple.html
<html>
	<head>
		<script language="javascript">
		
		// General functions 
					
		function UpdateEtape1()
		{
			alert('chargement de la page') ;
		ChangeFrameLocation('FrameMiseAJour', 'ExempleSimpleContenu.html');
		}
					
		function UpdateEtape2()
		{
			if (obj = getObjectById('Contenu'))
		obj.innerHTML = window.frames["FrameMiseAJour"].document.body.innerHTML;
		}
		</script>
	</head>
	<body>
		<div id="Contenu">Contenu de départ</div><br/><br/>
		<a href="javascript:UpdateEtape1();">Mettre à jour le texte</a><br/><br/>
		<iframe name="FrameMiseAJour" id="FrameMiseAJour" width="200" height="100"/>
	</body>
</html>
La page contenant le texte à copier est relativement simple.
ExempleSimpleContenu.html
<html>
	<head>
	</head>
	<body onload="parent.UpdateEtape2();">
		Contenu mis à jour<br/><br/>
		<a href="javascript:alert('Ceci est un nouvel élément HTML, ce qui prouve que toute 
			la page ExempleSimpleContenu a bien été copiée...');">Un élément HTML</a>
	</body>
</html>
Ce qui donne comme résultats :

La page ci-dessus utilise l'événement onload pour copier les données. Cependant nous n'avons pas toujours la possibilité de modifier cet événement dans la page à copier. C'est pourquoi il est préférable d'utiliser l'événement onload de l'iframe.

Le résultat de cette modification est :
ExempleSimple.html
<html>
<head>
<script language="javascript">
//…
</script>
</head>
<body>
<div id="Contenu">Contenu de départ</div><br/><br/>
	<a href="javascript:UpdateEtape1();">Mettre à jour le texte</a><br/><br/>
	<iframe name="FrameMiseAJour" id="FrameMiseAJour" width="200" height="100" onload="UpdateEtape2();"/>
</body>
</html>
pour la page container et
ExempleSimpleContenu.html
<html>
	<head>
	</head>
	<body>
		Contenu mis à jour<br/><br/>
		<a href="javascript:alert('Ceci est un nouvel élément HTML, ce qui prouve que toute 
			la page ExempleSimpleContenu a bien été copiée...');">Un élément HTML</a>
	</body>
</html>
pour la page contenue.


IV. Avantages de la technique du partial update

Pas de flicking (clignotement)

La page n'est pas rechargée entièrement, c'est pourquoi les modifications sont effectuées de manière dynamique comme le ferait une application Windows classique. Ainsi, il n'y a aucun clignotement lors d'un éventuel rechargement de la page.

Construction incrémentale

Certaines actions peuvent prendre beaucoup de temps comme par exemple un calcul compliqué au travers d'une très grosse base de données ou le listing des fichiers d'un répertoire. Par ailleurs, il n'est pas toujours impératif d'afficher ces résultats directement voire même ne pas les afficher du tout.

Une attente trop longue pour obtenir le résultat d'une page web entraînera, dans la plupart des cas, la perte définitive du visiteur.

Gestion aisée des branches affichées dans le cadre d'un treeview

Pour savoir quelles sont les branches d'un treeview qui sont ouvertes, il existe toute une série de moyens, la plupart nécessitant le passage d'informations lors des différents retours serveurs. Dans le cas du partial update, il est possible de n'afficher une branche et d'en récupérer le contenu que lorsque le besoin s'en fait sentir. Pour en savoir plus, une petite lecture du point qui lui est consacré dans le paragraphe " Utilisations diverses " est la bienvenue.

Rapidité d'exécution

Le transit d'un minimum d'informations permet de diminuer le temps d'exécution. Effectivement, il n'est pas nécessaire de recharger des informations qui auraient déjà été chargées.

Diminution de nombre de caractères en transfert

En plus de l'avantage précédent, il est bon de noter que le fait de transférer moins d'informations permet de diminuer la consommation du quota des abonnements adsl.



V. Comparatif avec / sans la technique du Partial Update

Pour effectuer ce comparatif, nous allons utiliser une base de données Sql Server.

Trois tables, expressément constituées pour le test, seront utilisées. Il s'agit de :

- PU_Categories (IdGroup, GroupName, Description)
- PU_Rubrics (IdSGroup, IdGroup, GroupName, Description)
- PU_Messages (IdMessage, Item, IdSGroup)

Nombre Categories Rubriques / Catégorie Messages / Rubrique Nombre total de messages Avec Partial Update Sans Partial Update
5 6 8 240 0s14 0s02
5 12 8 480 0s14 0s05
10 12 8 960 0s14 0s11
10 12 16 1920 0s14 0s22
10 12 32 3840 0s14 0s43
10 24 32 7680 0s14 0s87
20 24 32 15360 0s14 1s75
Pour chacun des cas, nous supposerons que nous avons besoin d'afficher les messages de six rubriques.

L'exemple ci-dessus est basé sur des essais réels. Cependant les valeurs avec le partial update ont été arrondes vers le haut.

Nous voyons déjà qu'avec 2000 éléments, la technique du Partial Update est intéressante et permet un gain de temps. Cependant, le nombre de requêtes HTTP est plus important puisque, pour une requête pour afficher toutes les données sans la technique du javascript, il est nécessaire d'en effectuer 7 avec la technique. Ces 7 requêtes sont réparties de la manière suivante :

- 1 pour afficher la liste des rubriques (0s02)
- 1 par affichage des messages de la rubrique (0s016, arrondi à 0s02)


VI. Implémentation

En plus des fonctions décrites dans le chapitre précédent, la technique du Partial Update nécessite quelques fonctions supplémentaires. Ces fonctions ont pour but de récupérer la valeur d'un élément et de l'assigner à un autre.
Manipulate.js
// …

var idToChange;
var boolReload;
var lastName;
var lastDesc;


function setValue(FieldName, FieldValue) 
{
	if (E = getObjectById(FieldName))
		E.value = FieldValue;
}

function setInner(FieldName, FieldValue) 
{
	if (E = getObjectById(FieldName))
		E.innerHTML = FieldValue;		
}			

function getValue(FieldName) 
{
	var value = '';
	if (E = getObjectById(FieldName))
		value = E.value;
	return value;
}			


function copyNewValues()
{
	if (boolReload == true)
	{
		boolReload = false;
		setValue (idToChange, window.frames["PartialFrame"].document.body.innerHTML);	}

}	

function newId(objname)			
{
	idToChange = objname;
	boolReload = true;
}

VI. Utilisations diverses

Treeview dynamique

Dans le cas d'une application web de bureau à distance (qui liste les fichiers et les répertoires d'un ordinateur présent sur le réseau dans lequel le serveur se trouve par exemple), il peut être fort désavantageux de lister tous les fichiers de tous les répertoires en une seule fois.

Le partial update permet de lister les sous-répertoires et fichiers d'un répertoire à la demande. Ainsi, lors du premier affichage, seule la liste des disques est affichée. Lors d'un clic sur l'un de ces disques, on appelle une page dans l'iframe. Le serveur, lorsqu'il recevra la demande, va dès lors lister les éléments correspondants avant de les mettre en forme dans la page qui sera renvoyée au navigateur. Il ne reste plus dès lors qu'à copier le contenu de cette page au niveau du nœud du treeview.

On retrouve ce principe dans la page d'administration des catégories. Effectivement, la liste des rubriques n'apparaît que lors d'un clic. Cette liste est chargée à la demande car, la plupart du temps, on a besoin que de modifier, supprimer ou ajouter qu'une seule information.

Graphiques et Charts

Certains langages serveur permettent de créer des graphiques sous formes d'images. C'est le cas, par exemple, de .NET et php. Imaginons qu'on souhaite faire une simulation avec génération dynamique d'images, il est possible d'utiliser cette technique. C'est dans l'iframe que sera générée l'image, il ne reste plus qu'à la substituer à celle présente à l'heure actuelle.

DataGrids avancés

L'affichage des données dans un tableau de données est relativement simple à effectuer, quelque soit le langage utilisé pour le faire. Le Partial Update permet d'utiliser ce tableau de données afin d'effectuer des opérations telles que celles que l'on effectue avec des applications Windows fenêtrées, c'est à dire avec des modifications à la volée.

Pour effectuer ces modifications, il suffit, lors de la création du tableau de données, d'afficher un élément HTML span ayant comme contenu la valeur à afficher ainsi qu'un composant input de type text avec la même valeur.

La fonction de traitement appliquée à l'événement onclick de l'élément span permet de cacher cet élément et d'afficher l'élément input en modifiant le contenu de l'attribut style.

La fonction appliquée à l'événement onblur de l'élément input permet d'afficher l'élément span avec la valeur modifiée et de cacher l'élément input et surtout d'envoyer les informations au serveur pour effectuer la mise à jour de son côté. Une bonne pratique est de réafficher l'élément span grâce au javascript contenu dans la réponse du serveur, ce qui permet de vérifier de la réussite ou non de la fonction.

Aide contextuelle

Beaucoup d'applications Windows permet d'afficher des informations dans une bulle d'aide lors du survol d'une zone si le mode " aide " est activé, c'es à dire si on a appuyé sur le " ? ".

Il est possible de faire pareil grâce au Partial Update. Effectivement, lors du survol d'une zone, il est possible d'envoyer des informations au serveur et en retour d'afficher des bulles d'aide.

Recherche d'informations sur un mot clé

Le principe ici est d'utiliser l'événement onclick sur des éléments particuliers dont la valeur est dans un tag span. Lors du clic sur un de ces mots, une requête est envoyée au serveur avec comme paramètre le mot sur lequel un traitement doit être effectué.

Lorsque la réponse parvient au navigateur, elle est affichée à l'intérieur d'un élément div.

On peut y trouver diverses utilisations telles que des traductions, l'affichage des définitions, …

Drag and drop avec enregistrement des préférences

Ceci ne fonctionne uniquement sous Internet Explorer, les autres navigateurs n'ayant pas implémenté, à l'heure actuelle, les méthodes ondrag et apparentées.

Le principe est simple, il suffit de gérer le déplacement à l'aide des méthodes ondrag et ondrop. Dans la fonction correspondant à ondrop, il suffit de déplacer réellement l'élément concerné et d'envoyer sa position au serveur qui se charge de l'enregistrer.

Dialogue en direct

Celui-ci est détaillé dans un prochain article.

Recherche incrémentale

A chaque fois que l'on appuye sur une touche dans un élément de type input/text, l'événement onkeypress est lancé. Ainsi, si on y attache une fonction, il suffit dès lors d'envoyer au serveur les critères déjà encodés. En réponse, le serveur renvoie une liste de critères que l'utilisateur pourrait utiliser afin de lui faciliter la tâche.

Ce n'est pas exactement la technique utilisée par Google Suggest pour afficher les suggestions mais elle s'y apparente.

Vérification de formulaire en temps réel (contraintes de validité)

A chaque élément input, une fonction est associée à l'événement onblur. Cette fonction doit se charger d'envoyer les informations au serveur qui se chargera de valider les informations qui ont été encodées et qui ne peuvent subir de vérification à l'aide de javascript. On peut citer, par exemple, le fait de vérifier qu'un pseudonyme n'a pas encore été pris par quelqu'un d'autre.

Menus déroulants et menus contextuels

L'utilisation est identique au treeview dynamique si ce n'est qu'il s'agit de gérer l'événement onover.



VIII. Exemple d'utilisation

Vous trouverez un exemple d'utilisation de cette technique à l'adresse suivante: fr http://ditch.developpez.com/javascript/partialupdate/exemple/


IX. Conclusion

Comme on peut le voir, là où le développement web devait auparavant laisser place au développement fenêtré, nous pouvons désormais réaliser des applications web, avec tous ses avantages (gestion centralisée, pas d'installation nécessaire, accessible de partout, ...), qui s'apparentent de plus en plus à une utilisation similaire aux applications classiques. Comme dirait un humoriste belge, "le futur a de l'avenir".



Valid XHTML 1.1!Valid CSS!

Les sources présentées sur cette page sont libres de droits et vous pouvez les utiliser à votre convenance. Par contre, la page de présentation constitue une œuvre intellectuelle protégée par les droits d'auteur. Copyright © 2005 Danse Didier. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents, images, etc. sans l'autorisation expresse de l'auteur. Sinon vous encourez selon la loi jusqu'à trois ans de prison et jusqu'à 300 000 € de dommages et intérêts.

Responsable bénévole de la rubrique Développement Web : Xavier Lecomte -