为自定义模型生成站点地图


12

我已经开发了一个定制模块,该模块列出了网站上的一系列人员。每个人都有自己的URL(一个定制的Magento控制器,它对Person模型进行基本的CRUD),我需要将这些公共URL馈入Google Sitemap XML文件中。

如果可以的话,我想使用Magento自己的站点地图生成程序和cron。

Mage_Sitemap_Model_Observer已经拉在所有的网站地图记录sitemaps表,并一个接一个电话他们的generateXml()方法。

$collection = Mage::getModel('sitemap/sitemap')->getCollection();
/* @var $collection Mage_Sitemap_Model_Mysql4_Sitemap_Collection */
foreach ($collection as $sitemap) {
    /* @var $sitemap Mage_Sitemap_Model_Sitemap */

    try {
        $sitemap->generateXml();
    }
    catch (Exception $e) {
        $errors[] = $e->getMessage();
    }
}

我认为我需要在sitemaps表中添加新的Sitemap,然后将其调用以为我的自定义模型记录生成我的(单独的)XML文件。但是,我不知道如何告诉Magento使用我的扩展My_Module_Model_Sitemap而不是just Mage_Sitemap_Model_Sitemap,后者将只给我一个XML文件,列出所有与主站点地图相同的类别,产品和CMS页面。

sitemaps表有一个sitemap_type列,但据我所知,在Magento代码库中从未引用过该列。

如何覆盖覆盖Mage_Sitemap_Model_Sitemap自有generateXml()方法的同时使用Magento的内置站点地图引擎?还是我必须为自己的目的构建替代站点地图系统?


您想扩展Mage_Sitemap_Model_Sitemap类并覆盖generateXml()吗?你尝试了什么?
FlorinelChis

尝试过,但是Magento只是使用,Mage_Sitemap_Model_Sitemap并给了我另一个包含产品,类别和CMS页面的站点地图-它不使用我的扩展版本。我不确定如何告诉它怎么做。
亚伦·波洛克

可能需要重写整个Mage_Sitemap_Model_Sitemap站点,并在类别和产品调用下添加我自己的模型。将会随着进度更新。
亚伦·波洛克

Answers:


6

我最终使用的步骤如下,到目前为止的评论和答案使我朝着正确的方向开始。

首先,我在“ sitemap”表中添加了一行。由于我们已经建立了多存储,并且因为我想保持模块存储不可知,所以我没有将这个INSERT硬编码到MySQL迁移中,而是手动在存储上运行它:

INSERT INTO sitemap (sitemap_type, sitemap_filename, sitemap_path, store_id)
    VALUES ('people', 'people.xml', '/sitemap/', 2);

然后,我Mage_Sitemap_Model_Sitemap在自己模块的config.xml文件的global / models部分中重写了模型:

<global>
    <models>
        <sitemap>
            <rewrite>
                <sitemap>Mymod_People_Model_Sitemap</sitemap>
            </rewrite>
        </sitemap>
    </models>
</global>

这会覆盖Mage_Sitemap_Model_Sitemap使用我的自定义模型对网站范围内的所有调用,但是我不想在那里复制和粘贴太多代码。根据Petar Dzhambazov的建议,除非条件sitemap_type为“ people”,否则我使用了一个条件来服从父类。

class Mymod_People_Model_Sitemap extends Mage_Sitemap_Model_Sitemap
{
    const PAGE_REFRESH_FREQUENCY = 'weekly';
    const PAGE_PRIORITY = '1.0';

    public function generateXml()
    {
        if ($this->getSitemapType() != 'people') {
            return parent::generateXml();
        }

        $io = new Varien_Io_File();
        $io->setAllowCreateFolders(true);
        $io->open(array('path' => $this->getPath()));

        if ($io->fileExists($this->getSitemapFilename()) && !$io->isWriteable($this->getSitemapFilename())) {
            Mage::throwException(Mage::helper('sitemap')->__('File "%s" cannot be saved. Please, make sure the directory "%s" is writeable by web server.', $this->getSitemapFilename(), $this->getPath()));
        }

        $io->streamOpen($this->getSitemapFilename());

        $io->streamWrite('<?xml version="1.0" encoding="UTF-8"?>' . "\n");
        $io->streamWrite('<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">');

        $storeId = $this->getStoreId();
        $date    = Mage::getSingleton('core/date')->gmtDate('Y-m-d');
        $baseUrl = Mage::app()->getStore($storeId)->getBaseUrl(Mage_Core_Model_Store::URL_TYPE_LINK);

        /**
         * Generate people sitemap
         */
        $changefreq = Mymod_People_Model_Sitemap::PAGE_REFRESH_FREQUENCY;
        $priority   = Mymod_People_Model_Sitemap::PAGE_PRIORITY;
        $collection = Mage::getModel('people/person')->getCollection();
        foreach ($collection as $item) {
            $xml = sprintf('<url><loc>%s</loc><lastmod>%s</lastmod><changefreq>%s</changefreq><priority>%.1f</priority></url>',
                htmlspecialchars($item->getUrl()),
                $date,
                $changefreq,
                $priority
            );
            $io->streamWrite($xml);
        }
        unset($collection);

        $io->streamWrite('</urlset>');
        $io->streamClose();

        $this->setSitemapTime(Mage::getSingleton('core/date')->gmtDate('Y-m-d H:i:s'));
        $this->save();

        return $this;
    }
}

有没有更好的方法,可以避免从父类复制和粘贴太多内容?


1

您可以扩展Mage_Sitemap_Model_Sitemap并在其中检查sitemap_type它是否是您的类型,生成xml或生成父xml。或者,您可以为集合load_after事件添加观察者,并将站点地图模型添加到集合中。


0

有没有更好的方法,可以避免从父类复制和粘贴太多内容?

如果您的Magento> = 1.9.0.0,并且不关心使用产品或目录的优先级/更改频率设置,则可以在 sitemap_products_generating_before

public function addPagesToSitemap(Varien_Event_Observer $observer)
{
    $collection = $observer->getCollection();
    $myPages = # your data: array('url_1', 'url_2')
    foreach ($myPages as $url) {
        $item = new Varien_Data_Object;
        $item->setUrl($url);
        $collection->addItem($item);
    }
}

如果您想在站点地图页面上完成其他行为,请阅读Sitemap.xml改回首页和/或调度一个更通用的事件

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.