tourze/rss-feed-collect-bundle
A Symfony bundle from Tourze for collecting and aggregating RSS feeds, with configurable feed sources and scheduled fetching. It helps import feed entries into Symfony applications for storage, processing, or display.
composer require tourze/rss-feed-collect-bundle. Note the name: this is a Symfony bundle, not a Laravel package. It will not register itself via Laravel's package discovery, and there is no publishes() / service provider contract to lean on.composer.json (PHP version, whether it pulls symfony/http-client, symfony/framework-bundle, or a feed parser such as laminas-feed), the <Name>Bundle class in src/, then anything under src/Command, src/Service, and src/Resources/config. Those three locations tell you what you can actually call and what you'd have to wire yourself.HttpClientInterface, your Http::fake() calls in tests will not intercept it — see Gotchas.php artisan tinker, dump the result, then wrap it in a queued job. Do not start with scheduling; get one feed into one table first.RssFeedCollectServiceProvider that binds the bundle's collector/parser interfaces to their concrete classes, and expose a thin FeedCollector wrapper class as your app-facing API. Everything else in your codebase should depend on your wrapper, not on the bundle's namespace — that keeps a 0.0.x dependency contained to one file when the API shifts.Configuration + Extension pair, which Laravel doesn't execute. Port the meaningful keys into config/rss-feed-collect.php and inject them into the wrapper's constructor.$tries = 1 and a short retryUntil. A malformed feed should fail its own job, not abort a batch of twelve. Trigger the fan-out from a single scheduled command.feed_items row with a unique index on (feed_id, guid) falling back to (feed_id, link). Feed GUIDs are frequently absent, duplicated, or reused after edits; dedupe at the database, not in PHP.Carbon::parse() with a try/catch and store a nullable published_at rather than dropping the item.$schedule->job(new CollectFeeds)->hourly()->withoutOverlapping() is the whole integration. Add a per-feed last_fetched_at and skip feeds still inside a polite interval (5–15 min) regardless of schedule.Http::fake(). Keep three fixture files checked in: one RSS 2.0, one Atom, one deliberately malformed."tourze/rss-feed-collect-bundle": "0.0.1") rather than a caret constraint. Assume any 0.0.x bump can break your wrapper.EventDispatcherInterface, LoggerInterface), you may need Laravel's PSR-3 logger bound, or an adapter class; Symfony's EventDispatcherInterface in particular is not Laravel's dispatcher and is a common failure point.Http::fake() and Http::preventStrayRequests() only cover Laravel's Guzzle-backed client. If the bundle uses symfony/http-client, your tests will make real network calls unless you bind a stub implementation of HttpClientInterface. Verify this early — it's the single most likely source of flaky CI.<description>, mismatched content encodings, <link> that is relative rather than absolute, and Atom <link rel="alternate"> versus <link rel="self">. Sanitise description HTML before rendering, never after storage.User-Agent; several publishers reject requests without one. Log the raw response body at debug level before parsing so a parse failure is diagnosable after the fact.How can I help you explore Laravel packages today?