Сначала написал вариант для Drupal 6, но в силу актуальности семерки, предлагаю вариант кода для 7й версии.
Описание вы найдете в прошлой статье, здесь обновлена только работа с базой данных. Привожу код класса и пример его вызова.
Код класса:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 |
/* класс, который займется рутиной */ class xmlsitemap_builder { var $domain; var $recordsPerFile = 1000; var $outputDir = ''; var $types = array('page'); var $files = array(); //конструктор function xmlsitemap_builder() { $this->domain = 'http://' . $_SERVER['HTTP_HOST']; $this->outputDir = variable_get('file_public_path', ''); if ($this->outputDir === '') $this->outputDir = 'sitemaps'; else $this->outputDir .= '/sitemaps'; } //генерация карты сайта function rebuild() { if (!file_exists($_SERVER['DOCUMENT_ROOT'] . '/' . $this->outputDir)) mkdir($_SERVER['DOCUMENT_ROOT'] . '/' . $this->outputDir); //получим список нод для xml карты $res = $this->getNodeList(); //главная страница сразу в списке $items = array(' <url> <loc>' . $this->domain . '</loc> <changefreq>daily</changefreq> <priority>1</priority> </url>'); //перебираем список while ($r = $res->fetchObject()) { $items[] = ' <url> <loc>' . $this->domain . '/' . ($r->dst ? $r->dst : 'node/' . $r->nid) . '</loc> <changefreq>weekly</changefreq> <lastmod>' . date('c', $r->changed). '</lastmod> <priority>0.5</priority> </url>'; //пишем XML файл if (count($items) >= $this->recordsPerFile) $this->__buildfile($items); } //пишем остатки if (count($items)) $this->__buildfile($items); //пишем реестр if (!empty($this->files)) $this->__buildreestr(); } private function getNodeList() { //мы "подшиваем" к публикациям их алиасы, //чтобы выбрать всю информацию за один запрос return db_query("SELECT UA.alias as dst, node.nid, node.changed FROM node LEFT JOIN url_alias UA ON UA.source = CONCAT('node/', node.nid) AND node.language = UA.language WHERE node.status <> 0 AND node.type IN ('" . implode("','", $this->types) . "')"); } //создание файла-списка private function __buildfile(&$items) { $N = count($this->files); $filepath = $_SERVER['DOCUMENT_ROOT'] . '/' . $this->outputDir . '/sitemap-' . $N . '.xml'; $handle = fopen($filepath, "w"); fwrite($handle, '<?xml version="1.0" encoding="UTF-8"?> <urlset xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:image="http://www.google.com/schemas/sitemap-image/1.1" xsi:schemaLocation="http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd" xmlns="http://www.sitemaps.org/schemas/sitemap/0.9"> ' . implode('', $items). ' </urlset> '); fclose($handle); //очищаем список $items = array(); //запишем url файла $this->files[] = $this->domain . '/' . $this->outputDir . '/sitemap-' . $N . '.xml'; } //создание файла-реестра private function __buildreestr() { $reestr = array(); foreach ($this->files as $fileurl) { $reestr[] = ' <sitemap> <loc>' . $fileurl . '</loc> <lastmod>' . date('c') . '</lastmod> </sitemap>'; } $filepath = $_SERVER['DOCUMENT_ROOT'] . '/sitemap.xml'; $handle = fopen($filepath, "w"); fwrite($handle, '<?xml version="1.0" encoding="UTF-8"?> <sitemapindex xmlns="http://www.sitemaps.org/schemas/sitemap/0.9"> ' . implode("\n", $reestr). ' </sitemapindex> '); fclose($handle); } } |
Пример работы:
1 2 3 4 5 6 7 8 |
//создали объект $builder = new xmlsitemap_builder(); //задали типы нод $builder->types = array('story', 'page'); //сменили кол-во урлов в одном файле $builder->recordsPerFile = 2000; //запустили создание XML карты сайта $builder->rebuild(); |
Остались вопросы — пишите в комментарии.