Google Adsense и XHTML
Как заставить Adsense работать на XHTML-страницах
Не секрет, что Adsense для вставки рекламы использует <iframe>. Не секрет, что для вставки этого <iframe> используется самый простой метод — document.write(). Какими же проблемами это грозит? Частично отвечая на вопрос, почему это не работает для XHTML-документов?
Сразу оговорюсь, что не работает это не для всех документов, а только для тех, которые, как и полагается XHTML-документам, выдаются с Content-Type: application/xhtml+xml.
Итак, для "настоящих XHTML-документов" возникает две проблемы:
Основной является первая проблема. Тем не менее, даже если заменить document.write другой конструкцией (document.createElement()/document.createElementNS() + node.appendChild() или аналогичной), то в результате получим невалидный XHTML-код (который может не отображаться в валидирующих браузерах — я слышал, что это свойственно Konqueror).
Как же с этим бороться? Как уже было сказано, в современных версиях XHTML элемента <iframe> нет. Но есть другой, не менее известный элемент — <object>. Теоретически можно сохранить скрипт Google AdSense локально, изменить его, научив использовать document.createElement()/document.createElementNS() и <object> вместо <iframe>. Вот только имеет ли это смысл?
Идём дальше. Как уже было сказано выше, источник проблем здесь — специфический Content-Type (или, если смотреть глубже, кривые руки разработчиков Google — кому какой вариант нравится больше). То есть если страница будет выдаваться как, например, text/html, то AdSense будет работать. А если это соединить с <object>, то получим готовое решение.
Выглядеть это будет так: на странице, на которой должны быть объявления, вместо кода Google Adsense помещаем следующий код:
Сама же страница adsense.html будет выглядеть следующим образом:
<html>
<head>
<title>Google Adsense - Disable Me in Adblock :-)</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<style type="text/css">
html, body { margin: 0; padding: 0; border: 0; }
</style>
</head>
<body>
<script type="text/javascript">//<!--
google_ad_client = "pub-5756520316076607";
google_ad_slot = "5162144530";
google_ad_width = 468;
google_ad_height = 60;
//-->
</script>
<script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>
</body>
</html>
Разумеется, следует использовать свои параметры AdSense.
Если сервер настроен выдавать статические .html-страницы с Content-Type: application/xhtml+xml (или любым другим, кроме text/html), то это, разумеется, надо поправить (как именно — зависит от сервера). Например, для Apache это может выглядеть следующим образом (предполагается, что эти строки будут добавлены в файл .htaccess, находящийся в том же каталоге, что и adsense.html):
ForceType text/html
</Files>
Update: мне всё же интересно, будут ли объявления в этом случае контекстно-зависимыми? Ведь по большому счету, referer'ом скрипта http://pagead2.googlesyndication.com/pagead/show_ads.js будет страница adsense.html, а не та, на которой эта реклама должна отображаться… И проверить из-за проблем с аккаунтом не могу
Update: Stu Nicholls нашел еще одну скрытую ошибку: дело в том, что при нажатии на ссылку в рекламном блоке, Internet Explorer откроет её не в главном окне (как это должно быть), а внутри тэга <object>.
Stu Nicholls предлагает следующее решение проблемы: использовать условные комментарии для того, чтобы не использовать <object> в IE (в любом случае, IE пока не понимает application/xhtml+xml, так что использование небольшого хака для IE не будет критичным). Я немного изменил предложенный код так, чтобы IE вообще не видел тэг <object> (нечто подобное было сделано в статье "Кросс-браузерное одноуровневое вертикальное меню без JavaScript")
<object data="adsense.html" type="text/html"></object>
<!--<![endif]-->
<!--[if lte IE 8]>
<script type="text/javascript">
google_ad_client = "pub-5756520316076607";
google_ad_slot = "5162144530";
google_ad_width = 468;
google_ad_height = 60;
</script>
<script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>
<![endif]-->

