惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

D
Docker
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
C
Cisco Blogs
Scott Helme
Scott Helme
Know Your Adversary
Know Your Adversary
NISL@THU
NISL@THU
C
Cyber Attacks, Cyber Crime and Cyber Security
D
Darknet – Hacking Tools, Hacker News & Cyber Security
C
CXSECURITY Database RSS Feed - CXSecurity.com
S
Schneier on Security
I
Intezer
Spread Privacy
Spread Privacy
AWS News Blog
AWS News Blog
V
Vulnerabilities – Threatpost
Cloudbric
Cloudbric
V2EX - 技术
V2EX - 技术
Google Online Security Blog
Google Online Security Blog
L
Lohrmann on Cybersecurity
Recent Commits to openclaw:main
Recent Commits to openclaw:main
L
LINUX DO - 热门话题
S
Secure Thoughts
T
The Exploit Database - CXSecurity.com
博客园 - 【当耐特】
Recent Announcements
Recent Announcements
Security Archives - TechRepublic
Security Archives - TechRepublic
Stack Overflow Blog
Stack Overflow Blog
罗磊的独立博客
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
K
Kaspersky official blog
阮一峰的网络日志
阮一峰的网络日志
博客园_首页
Latest news
Latest news
B
Blog
F
Full Disclosure
大猫的无限游戏
大猫的无限游戏
博客园 - 叶小钗
L
LangChain Blog
GbyAI
GbyAI
Last Week in AI
Last Week in AI
S
Security Affairs
Apple Machine Learning Research
Apple Machine Learning Research
N
Netflix TechBlog - Medium
Security Latest
Security Latest
Vercel News
Vercel News
Y
Y Combinator Blog
G
GRAHAM CLULEY
S
Securelist
T
Troy Hunt's Blog
Hacker News - Newest:
Hacker News - Newest: "LLM"
雷峰网
雷峰网

Все публикации подряд на Хабре

Ловим музу за клавиатуру: как айтишнику стать автором Что умеет Midjourney в 2026? Мой немного грустный разбор этого шикарного инструмента Никто не любит писать тесты, но ИИ может исправить это IPv8 выглядит как мечта. Поэтому почти наверняка не взлетит Производители вернули в продажу материнки с DDR3. Что происходит? Управление агентом с телефона через Telegram теперь в KodaCode От координации к лидерству: как меняется роль руководителя разработки Я сделала родителям бизнес вместо пенсии: зарабатываем 70 тысяч, мама не даёт продать В три раза быстрее приемка товара и оптимизация трудозатрат на 73%: как «РСТ-Инвент» помог Gulliver Group ИИ-шечный мир победил? О влиянии искусственного интеллекта на игропром Кремль снижает давление на Телеграмм пока Европа строит интернет по паспорту Как CEO, CTO и CIO за 8 часов собрали ИИ-директора, который умеет держать позицию под давлением Как (не) потерять домен за выходные Вместо 8 разных VPS: как я организовал практику студентам на одном сервере Почему твой Open Source проект не замечают? R&D: искусство управления неопределенностью в разработке AI-дефляция: вакансий для разработчиков больше, а рост зарплат — худший за 15 лет Мы отдали управление роботами OpenClaw. Что из этого вышло Галактический ID: система идентификации для всех форм разумной жизни Шесть основ бизнес-анализа: начинаем с вопроса «Кто в игре?» Код-ревью, в котором дело не в коде Данные переехали. Команда — нет Системной подход к сдаче OSWE в 2025 Почему комната управления реактором покрашена в цвет морской пены 4 YAML-файла вместо PySpark: как аналитикам строить пайплайны без разработчиков LLM-агент для поиска свободных доменов: автоматизируем подбор Когда, зачем и как правильно начинать новую сессию в Claude Code? Как я заставил нейросеть писать макросы для FreeCAD Анатомия ИИ‑агента для подбора персонала. От тысячи резюме к топ‑10 за минуты Опыт разработчика как экономика внимания Автономность как точка невозврата: кто будет субъектом в цифровом будущем Обучение ИИ в «диких» условиях: как рутинные действия превращаются в датасеты Как измерить LLM для задач кибербеза: обзор открытых бенчмарков Где хранить код? Сравнение GitHub, GitLab и Bitbucket Математика объясняет, почему нормальное распределение встречается повсюду Почему ваш FinOps не работает: 12 тезисов от практиков Как подписать проектную документацию УКЭП с использованием бесплатных лицензий Pilot Адаптивное администрирование Sigla Vision Я грузил уран в бочки, а потом 20 лет строил ИТ в атомной отрасли Чем позвонить с Эвереста? История и обзор спутниковой связи. Часть 2 Как языковая модель помогает контролировать качество инструктажей по охране труда в металлургии Как не передать на desktop свой IP в РКН Анатомия SAP Privileges: как устроено управление правами в macOS MoneyDev: Сказка про три главных слова Обновлённый токенизатор видео K-VAE 2.0 от Сбера Как сделать диспетчеризацию дома на 1284 квартиры почти бесплатно Как мы разогнали железную дорогу Мы дали агентам рутину. Теперь надо решить — что делать с освободившимся временем Токсичный контент, промпт-хакинг и защита ИИ — всё о Guardrails для LLM Умный город начинается с точного взгляда: как «Фалькон Тех» меняет пространство к лучшему Навайбкодил приложение для анализа графов Почему Дюну так интересно читать? Упрощаем работу с рутиной или как стать Гендальфом Белым Деконструкция Go: CPU, RAM и что там происходит. Go Assembler база. Часть 1.1 Какие профессии исчезнут из-за ИИ, а какие появятся? И что с этим делать Как мы построили IT-отдел, где хочется расти: архитектурные встречи, прозрачные метрики и книжные подарки Rufler: Делаем из Claude Code автономный рой через один YAML-конфиг Sing-box и белый список приложений Как построить надёжный обмен сообщениями в микросервисах: лучшие практики для enterprise OpenAI строит MLM-пирамиду, а McKinsey и Accenture помогают ей в этом Дом, который не построил Фишер (Часть 2) «Сверхзвуковой математик» против «Вдумчивого логиста»: битва алгоритмов 3D-упаковки Мультимодальные модели – грубый и дорогой инструмент Разговоры ничего не стоят. Код тоже Проверки физических лиц: с кого начнет ФНС Топ-10 бесплатных нейросетей для создания видео в 2026 году Первые слои кода: как наши решения сегодня определяют архитектуру ИИ на десятилетия Разработка нового статического анализатора: PVS-Studio JavaScript Поиск уязвимостей ПО: базовый минимум или роскошный максимум Почему оценка персонала не работает как инструмент управления Как мы разработали ИИ-ассистента и сократили рутину продуктовой команды на 50% Как я ушел из найма, нажарил косточек и продал на маркетплейсах на 168 млн в год Когда 1С:ERP уже внедрена, а нормального производственного плана всё ещё нет Как я сделал Claude мультимодальным, подключив к нему Qwen Omni Как приглашение на вакансию мечты превращается в атаку Infrastructure as Code: философия и лучшие практики IaC Тестируем Yandex Code Assistant на задаче, в которой нужно хранить секреты nxs-universal-chart v3.0: новое поколение универсального Helm-чарта Callback Injection: Техника, которая отправила Microsoft Defender в глухой нокаут «Все идеи на стол»: митап как способ вывести проект из тупика Сегодня я узнал нечто новое о GPU благодаря багу в своей игре Как заставить LLM ̶ ̶г̶а̶л̶л̶ю̶ ̶ эволюционировать Карта событий как фундамент аналитики: практический кейс для E-commerce Что выбрать для AI: x86, ARM или RISC-V? Дайджест железа за март Роль соматических мутаций в развитии аутоиммунных заболеваний: путь к избирательной терапии Mythos от Anthropic — тревожный сигнал для всех, а не только для банков Guardrails для LLM на Java: как приручить промпт‑инъекции и токсичные ответы Green-VLA: как мы собрали VLA-модель для реального антропоморфного робота и не потеряли обобщение Финансовая гонка вооружений: почему умные люди добровольно в ней участвуют Эра ИИ-агентов наступила: выбираем лучшего цифрового сотрудника # Практический опыт внедрения WinCC Redundancy на производственном предприятии Сделал MVP за 3 дня, а потом неделю прикручивал оплату. Оно того стоило? Физика против Маска: почему Starship V3 может оказаться ещё одной катастрофой Нефть Венесуэлы: крупнейшие запасы в мире, но не крупнейшая нефтяная держава JPA 4. Переосмысление Hibernate Почему зеркальная фотокамера Nikon D5 десятилетней давности идеально подошла для миссии «Артемида-2» Проект «Уровень-Спутник» или как мы сделали платформу для гидрологов «Замедлиться, чтобы ускориться»: почему ИИ повышает цену ошибок в требованиях и архитектуре Как с нуля поднять трафик IT-компании на 1657% при бюджете 55 тыс. и выжить Pixel-perfect Downsampling — идеальная отрисовка 50 миллионов точек без потерь
Реализация RSS-генератора на «коленке» или наш ответ Чемберлену
ziptraser · 2026-06-24 · via Все публикации подряд на Хабре

Простой

5 мин

90

Всё началось с банальной задачи — я и моя напарница нейросеть Асси задумались над SEO-продвижением и адаптацией нашего сайта под современные реалии генеративного поиска (GEO / RAG) и краулеры языковых моделей (GPTBot, ClaudeBot, Perplexity). По старой привычке решили поглядеть, как эту задачу решают другие «взрослые дяди», открыли исходники популярных решений для синдикации в современных CMS… и, мягко говоря, офигели. То, что в корпоративном BigTech считается стандартом генерации банальной XML-ленты, на поверку оказалось кромешным инфраструктурным адом.

Анатомия корпоративного ада: Битрикс и остальные монстры.

Когда краулер стучится за RSS к типичному энтерпрайз-движку, на сервере начинается сущий кошмар, судите сами:

  1. Bitrix (Король тормозов): Это вообще отдельный котел для мазохистов. Чтобы отдать к примеру 15 новостей, Битрикс поднимает всё своё монструозное ядро, подключает prolog_before.php, инициализирует тысячи констант и лезет в базу через ORM, которая генерирует SQL-запросы длиной в километр. Если у вас «Композитный сайт» — готовьтесь к тому, что кэш будет инвалидироваться дольше, чем бот ждет ответа. Итог: сервак потеет, память жрётся, а краулер получает ответ через 500–800 мс. За это время можно было бы запустить ракету в космос.

  2. WordPress: Тут просыпается «прожорливое чудовище». WP_Query делает каскадные запросы к неоптимизированной базе, вытягивая метаданные и мусор. Потом это всё прогоняется через ад из сотен хуков и фильтров. Если стоят плагины типа Yoast — они перелопачивают строки в ОЗУ по кругу. Результат: 200–300 мс на ровном месте.

  3. Magento / Drupal: Тут вообще тушите свет. Чтобы выплюнуть тег , система оборачивает файл в десяток объектов, проверяет права доступа через три слоя абстракций и тратит прорву ресурсов на сериализацию.

    Unix-way или наш ответ Чемберлену.

Мы выкинули на мороз все зависимости. Наша логика простая как выстрел: один прямой UNION-запрос (собираем данные сразу из нескольких таблиц за один заход), кристально чистая потоковая буферизация в XML-строку и жёсткий роутинг. Никакого мусора, только чистые такты процессора. Чтобы не дёргать базу при каждом чихе ИИ-краулера, мы используем стратегию дефрагментации на диск. Скрипт отрабатывает и сохраняет статический rss.xml.

try {
    // Путь к файлу и конфигурация
    $rss_file = ROOT_DIR . 'rss.xml';
    $site_url = "https://yourdomain.com"; // Укажи свой домен (без слэша на конце)
    
    // Универсальный SQL-запрос (замени таблицы и поля на свои)
    $rss_sql = "(SELECT id, title, content, 'section_one' as src, file_name as f_check, date_add, keywords 
                 FROM table_one WHERE is_active = 1) 
                UNION 
                (SELECT id, title, content, 'section_two' as src, file_path as f_check, date_add, keywords 
                 FROM table_two WHERE is_active = 1) 
                ORDER BY date_add DESC LIMIT 15";
                
    $rss_stmt = $pdo->query($rss_sql);
    $rss_items = $rss_stmt->fetchAll(PDO::FETCH_ASSOC);

    $xml = '<?xml version="1.0" encoding="UTF-8"?>' . PHP_EOL;
    $xml .= '<rss xmlns:yandex="http://news.yandex.ru" xmlns:media="http://search.yahoo.com/mrss/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/" version="2.0">' . PHP_EOL;
    $xml .= '<channel>' . PHP_EOL;
    $xml .= '  <title>Название вашего ресурса</title>' . PHP_EOL;
    $xml .= '  <link>' . $site_url . '</link>' . PHP_EOL;
    $xml .= '  <atom:link href="' . $site_url . '/rss.xml" rel="self" type="application/rss+xml" />' . PHP_EOL;
    $xml .= '  <description>Описание вашего ресурса для поисковых роботов и агрегаторов</description>' . PHP_EOL;
    $xml .= '  <language>ru</language>' . PHP_EOL;
    $xml .= '  <lastBuildDate>' . date(DATE_RSS) . '</lastBuildDate>' . PHP_EOL;

    foreach ($rss_items as $rss_i) {
        // Универсальный роутинг для страниц контента
        $rss_item_url = $site_url . "/" . urlencode($rss_i['src']) . "?id=" . (int)$rss_i['id'];
        $is_section_two = ($rss_i['src'] === 'section_two');
        
        $xml .= '    <item>' . PHP_EOL;
        $xml .= '      <title>' . ($is_section_two ? '[📎] ' : '') . htmlspecialchars($rss_i['title'], ENT_XML1, 'UTF-8') . '</title>' . PHP_EOL;
        $xml .= '      <link>' . $rss_item_url . '</link>' . PHP_EOL;
        
        // Безопасная обработка текста
        $rss_clean_text = strip_tags($rss_i['content']);
        $rss_clean_safe = str_replace(']]>', ']]&gt;', $rss_clean_text);
        
        $xml .= '      <description><![CDATA[' . mb_strimwidth($rss_clean_safe, 0, 300, "...") . ']]></description>' . PHP_EOL;
        
        // Уникальный GUID записи
        $xml .= '      <guid isPermaLink="false">core-' . $rss_i['src'] . '-' . (int)$rss_i['id'] . '</guid>' . PHP_EOL;
        $xml .= '      <pubDate>' . gmdate(DATE_RSS, strtotime($rss_i['date_add'])) . '</pubDate>' . PHP_EOL;

        // Обработка прикрепленных файлов / медиа
        if (!empty($rss_i['f_check'])) {
            $rss_subfolder = $is_section_two ? 'folder_two' : 'folder_one';
            $rss_file_path = ROOT_DIR . 'storage/' . $rss_subfolder . '/' . $rss_i['f_check'];

            if (file_exists($rss_file_path)) {
                $rss_file_size = filesize($rss_file_path);
                $rss_ext = strtolower(pathinfo($rss_i['f_check'], PATHINFO_EXTENSION));
                
                $rss_mime = match($rss_ext) {
                    'webp'        => 'image/webp',
                    'jpg', 'jpeg' => 'image/jpeg',
                    'png'         => 'image/png',
                    'svg'         => 'image/svg+xml',
                    'gz'          => 'application/gzip',
                    'tar'         => 'application/x-tar',
                    'zip'         => 'application/zip',
                    default       => 'application/octet-stream'
                };

                //  Чистый роутинг для скачивания файлов через скрипт или напрямую
                if ($is_section_two) {
                    $rss_img_url = $site_url . "/section_two?get_file=1&amp;id=" . (int)$rss_i['id'];
                } else {
                    $rss_img_url = $site_url . "/storage/folder_one/" . rawurlencode($rss_i['f_check']);
                    $rss_img_url = str_replace('%2F', '/', htmlspecialchars($rss_img_url, ENT_XML1, 'UTF-8'));
                }

                if (str_starts_with($rss_mime, 'image/')) {
                    $xml .= '        <media:content url="' . $rss_img_url . '" type="' . $rss_mime . '" />' . PHP_EOL;
                }
                $xml .= '        <enclosure url="' . $rss_img_url . '" type="' . $rss_mime . '" length="' . $rss_file_size . '" />' . PHP_EOL;
            }
        }

        // Передача полного текста для ИИ-краулеров и GEO оптимизации
        $xml .= '      <yandex:full-text><![CDATA[' . $rss_clean_safe . ']]></yandex:full-text>' . PHP_EOL;
        $xml .= '      <content:encoded><![CDATA[' . $rss_clean_safe . ']]></content:encoded>' . PHP_EOL;
       
        // Теги категорий / Ключевые слова
        if (!empty($rss_i['keywords'])) {
            $keywords = array_filter(array_map('trim', explode(',', $rss_i['keywords'])));
            foreach ($keywords as $keyword) {
                $xml .= '      <category>' . htmlspecialchars($keyword, ENT_XML1, 'UTF-8') . '</category>' . PHP_EOL;
            }
        }

        $xml .= '    </item>' . PHP_EOL;
    }

    $xml .= '  </channel>' . PHP_EOL . '</rss>';
    file_put_contents($rss_file, $xml);
    $report .= " > RSS_GEN | STATUS: SUCCESS - CLEAN_TEMPLATE ✅\n";

} catch (PDOException $e) {
    $report .= " > RSS_GEN | ERROR: " . $e->getMessage() . "\n";
}

Примеры интеграции: Как внедрить подобный RSS-генератор в свой проект:

Вариант А: Интеграция в админку (Событийная)

Вызывайте генератор строго в момент нажатия кнопки «Сохранить» внутри вашей панели управления. Это полностью исключит нагрузку на СУБД при просмотре фида роботами.

    // Внутри обработчика вашей админки
    if ($sql_success) {
    // Запускаем мгновенную пересборку статического XML-файла
    include_once __DIR__ . '/cron/rss_machine.php'; 
    // Бросаем чистый редирект, юзер доволен
    header("Location: /admin.php?status=ok");
    exit;
}

Вариант Б: Жёсткое простукивание через системный Cron

Если контент залетает через API или парсеры, просто повесьте скрипт на нативный планировщик вашего VDS, Сервера, Etc; . Никакого докера, чисто нативный crontab.

//Обновляем статику раз в 15 минут
*/15 * * * * /usr/bin/php /var/www/html/cron/rss_machine.php > /dev/null 2>&1

Выводы.

  1. Никакого мусора в ОЗУ. Мы не создаем объекты FeedGeneratorFactoryInterface, мы просто пишем строки.

  2. Атомарность. Запись в статический файл защищает базу от DDoS-атак ботов-агрегаторов. Пусть Nginx потеет, отдавая статику, а PHP спит.

  3. Жёсткий роутинг. Мы контролируем каждый байт. Если файл в библиотеке — мы принудительно ведем бота через роут со счетчиком. Если картинка в журнале — отдаем напрямую.

Спасибо за прочтение.