Recevez les mises à jour gratuites du blog par Email : »» Garanti sans spam indésirable ««

Rotation d’une bannière publicitaire au contenu dynamique en AJAX

de Mimie le 7 janvier 2010

Rubrique : Programmation

Introduction

Les visiteurs de votre site peuvent s’attarder sur une page, si votre bannière publicitaire n’affiche qu’un contenu (aléatoire ou ciblé) uniquement à chaque chargement de page, ces visiteurs ne verront qu’une seule publicité pendant un temps plus ou moins long.

Pourquoi plutôt ne pas faire en sorte que la bannière fasse une rotation sur elle-même toutes les xx secondes afin d’afficher différents contenus même si l’utilisateur ne rafraichît pas la page ?

C’est le but de cet article, les sources sont mises à disposition en fin de page.

Présentation

Les bannières publicitaires sont généralement constituées d’un texte, d’une image ou d’une animation flash (comme Google AdSense), les faire faire par des professionnels reste très onéreux.

Voici un moyen simple qui permettra de réaliser votre bannière en AJAX en affichant aléatoirement (non ciblé) un contenu publicitaire différent toutes les xx secondes sans avoir à recharger la page, les types de contenus autorisés sont :

  1. HTML : texte, image, formulaire, swf … (autant dire tout)
  2. JAVASCRIPT : fichier ou code simple

Qu’on se comprenne bien cela ne va pas faire à votre place vos images (animées ou non) ou vos animations flash mais cela va vous permettre de fabriquer vous-même votre bannière en paramétrant simplement le contenu graphique ou texte à afficher dans celle-ci : le mécanisme est en place, à vous de le paramétrer !

Explications

  • La façon de récupérer les contenus à afficher dans la bannière est faite de manière asynchrone en utilisant AJAX avec la bibliothèque Prototype.
// récupère une publicité à afficher
function getAd() {
	var url = ctx + "/banner.do?action=getRandomAd&date=" + new Date().getTime();
	// make a HTTP request to the specified URL
    new Ajax.Request(url, {
        method:'get',
        asynchronous:true,
        onSuccess: function(xhr, json) {
        	if (json.error) {
        		$("BANNER_ADS").innerHTML = json.error;
        	} else {
        		// affichage de l'HTML
        		$("BANNER_ADS").innerHTML = json.content;
        		// lancement des éventuels javascripts
        		var scripts = $("BANNER_ADS").getElementsByTagName('script');
        		for (var i=0, j=scripts.length; i<j; i++) {
        			// javascript utilisant un fichier externe
        			if (scripts[i].src) {
        				include_dom_js_file(scripts[i].src);
        			} else {
        				eval_js_script(scripts[i].text);
        			}
        		}
        	}
        }
    });
}
// au chargement de la page
window.onload = function() {
	getAd();
	setInterval("getAd()", 5000); // toutes les 5 secondes
}
  • Les contenus HTML récupérés sont placés dans une div et les contenus JavaScript sont évalués
<body>
	<!-- emplacement de la bannière -->
	<div id="BANNER_ADS"></div>
</body>

et

// exécution à la volée du fichier javascript donné
function include_dom_js_file(script_filename) {
    var html_doc = document.getElementsByTagName('head').item(0);
    var js = document.createElement('script');
    js.setAttribute('type', 'text/javascript');
    js.setAttribute('src', script_filename);
    html_doc.appendChild(js);
    return false;
}
// exécution à la volée d'un code javascript donné
function eval_js_script(script_code) {
	// javascript code must not contain "<!--" and "//-->" to eval
	script_code = script_code.replace("<!--", "");
	script_code = script_code.replace("//-->", "");
	eval(script_code);
}
  • La communication vers le serveur est fait avec Struts (framework de présentation) et les données renvoyées à la page appelante sont au format JSON, plus léger que le format XML et pas besoin de parseur, en utilisant la bibliothèque Json-lib. (voir mon précédent article)
public class BannerAction extends DispatchAction {
	private BannerService bannerService = BannerServiceImpl.getInstance();
	// action Struts : récupération côté serveur de la requête AJAX
	public ActionForward getRandomAd(ActionMapping mapping, ActionForm actionForm, HttpServletRequest request, HttpServletResponse response)
			throws Exception {
		try {
			// appel métier
			AdBean ad = bannerService.getRandomAd();
			// données à retourner
			Map<String, String> hm = new HashMap<String, String>();
			hm.put("type", ad.getType());
			hm.put("content", ad.getContent());
			// chaque clé de notre map devient une clé dans l'objet JSON
			JSONObject jsonObject = JSONObject.fromObject(hm);
			// façon d'envoyer l'objet JSON pour que Prototype puisse le récupérer
			response.setHeader("X-JSON", jsonObject.toString());
		} catch (Exception e) {
			Map<String, String> hm = new HashMap<String, String>();
			hm.put("error", e.getMessage());
			JSONObject jsonObject = JSONObject.fromObject(hm);
			response.setHeader("X-JSON", jsonObject.toString());
		}
		return null;
	}
}
  • Le paramétrage des contenus publicitaires et la façon de les récupérer est faite côté Java. Notre exemple stocke en dur dans une liste les différents contenus, il est préférable de les stocker en base et d’avoir à les récupérer selon des critères (ou pas), en tout cas c’est un cas simple pour montrer le principe :
	public AdBean getRandomAd() throws Exception {
		// liste des pubs
		List<AdBean> adsList = this.getAds();
		int lower = 0;
		int higher = adsList.size();
		// nombre aléatoire entre lower (inclus) et higher (exclus)
		int random = (int) (Math.random() * (higher - lower)) + lower;
		return adsList.get(random);
	}
	/**
	 * retourne la liste des publicités en dur (les récupérer d'ailleurs : fichier, base, etc. hors de ce contexte d'exemple)
	 *
	 * @return
	 */
	private List<AdBean> getAds() {
		// SELECT * FROM ADS WHERE ...
		List<AdBean> adsList = new ArrayList<AdBean>();
		// html simple
		adsList.add(new AdBean("<em>ban</em>ner 1"));
		adsList.add(new AdBean("banner <strong>2.0.</strong>"));
		adsList.add(new AdBean("<h1>big banner</h1>"));
		// image
		adsList.add(new AdBean("<img src=\"http://desgeeksetdeslettres.com/blog/wp-content/plugins/sociable/images/facebook.png\" />"));
		// flash
		adsList.add(new AdBean(
				"<object type=\"application/x-shockwave-flash\" data=\"http://mathsp.tuxfamily.org/IMG/swf/escargot_pleinepage.swf\" width=\"604\" height=\"600\">" +
					"<param name=\"movie\" value=\"http://mathsp.tuxfamily.org/IMG/swf/escargot_pleinepage.swf\" />" +
					"<param name=\"wmode\" value=\"transparent\" />" + "<p>Image ou texte alternatif</p>" +
				"</object>"));
		// javascript
		adsList.add(new AdBean(
				"<script type='text/javascript'>adParameter = 'oui';</script>" +
				"<script type='text/javascript' src='http://localhost:8080/BannerRotation/scripts/alert.js'></script>"));
		adsList.add(new AdBean(
				"<script type='text/javascript'>toDisplay = \"<table border='1'><tr><td>case1</td><td>case2</td></tr></table>\";</script>" +
				"<script type='text/javascript' src='http://localhost:8080/BannerRotation/scripts/insert.js'></script>"));
		// google ads
		adsList.add(new AdBean(
				"<p style='text-align: center;'>" +
					"<script type='text/javascript'><!--" +
						"google_ad_client = 'pub-xxxxxxxxxxxxxxxx';" +
						"google_ad_slot = 'yyyyyyyyyy';" +
						"google_ad_width = 120;" +
						"google_ad_height = 600;" +
					"//--></script>" +
					"<script type='text/javascript' src='http://pagead2.googlesyndication.com/pagead/show_ads.js'>" +
					"</script>"+
				"</p>"));
		return adsList;
	}

Conclusion

Pour ceux qui en ont assez de leur bannière utilisant les iframes, cette solution sexy utilisant AJAX devrait vous plaire. De plus pouvoir inclure n’importe quel code HTML et du JavaScript est un plus pour remplacer vos publicités souvent mono-contenus, à vous de juger :-)

Sources disponibles ici (Eclipse Galileo, JDK 1.6, Tomcat 6.0)

Cet article a été écrit par :

– qui a déjà rédigé 123 posts sur Des Geeks et des lettres.

Passionné d'informatique et développeur JavaEE de métier, je me consacre principalement à écrire des billets sur les sujets du Web et de la programmation Web. Ce blog est un espace qui me permet de partager mes découvertes avec vous et me sert accessoirement de pense bête !

Contacter l'auteur

Jetez aussi un oeil sur :

{ 7 commentaires… à vous de vous exprimer ! }

1 Greg janvier 7, 2010 à 22 h 31 min

Ca m’a l’air super sympa comme idée :) Merci pour le code.

Répondre

2 achille52 janvier 8, 2010 à 9 h 45 min

J’essairai le jour ou j’utiliserais un hebergement personnel :D On peut y intégrer Google Adsense ?

Répondre

3 Mimie janvier 8, 2010 à 11 h 41 min

Bonjour achille52, il n’est pas possible avec ce code d’intégrer Google Adsense …
Je suis en train d’améliorer le code pour que cela fonctionne, c’est en bonne voie, je publie le résultat ce soir.
Merci pour ton commentaire tu m’as fait évolué mon code :-)

Répondre

4 Mimie janvier 8, 2010 à 23 h 44 min

Voilà nouvelles sources disponibles et modification légère de l’article. Cette fois-ci le tout est simplifié et Google Ads fonctionne :-)

Répondre

5 PC novembre 8, 2011 à 22 h 16 min

Ca ne marche pas et ca ne peut pas marcher.

Pour une raison très simple: la plupart des codes javascript utilisés par les régies pour afficher des bannières contiennent des instructions « document.write ».

Or, l’utilisation d’un « document.write », après la fin du chargement d’une page, efface automatiquement toute la page …

Si vous en doutez, essayer ce simple code dans une page:

window.onload=function(){document.write(‘coucou’);};

Donc, sur le papier c’est très beau, mais en pratique c’est, hélas, inutilisable avec la plupart des régies pub …

Répondre

6 Mimie novembre 8, 2011 à 22 h 38 min

@PC : il n’y a pas que du javascript pour faire ses publicités, d’ailleurs au début du billet je parle d’images, de texte, de flash, etc. Pour le javascript c’est en effet assez limité, à moins que ce soit votre propre code et non celui d’une régie.
Il faut voir en ce billet un exercice et non une méthode absolue et générique adaptée pour tous.

Répondre

7 PC novembre 9, 2011 à 13 h 17 min

Ah ?
99% des régies pubs utilisent un tag d’appel en javascript … et ensuite, 90% des pubs s’affichent avec des « document.write » et même, pire, avec des successions de
document.write( ») vu que les régies écoulent des inventaires provenant d’autres régies …
Tu crois vraiment que les pubs c’est encore du HTML/image, du genre </ ? LOL

Répondre

Laissez un Commentaire

Article précédent:

Article suivant: