jasonlewis/basset
Basset is an asset management package for Laravel that organizes CSS, JavaScript, and preprocessor files into bundles, compiles LESS/Sass/CoffeeScript, and serves cached, optimized assets via Blade helpers and Artisan commands.
Basset is a Laravel 4–era asset pipeline: you declare named collections of CSS/JS files, run them through filters (Less, Sass, CoffeeScript, etc.), and either serve them on the fly through a route or precompile them with an Artisan command. The whole package lives around three touchpoints — the config file, a collection definition, and two Blade calls.
Minimal setup, in order:
composer require jasonlewis/basset (the branch compatible with your Laravel 4.x version), then register 'JasonLewis\Basset\BassetServiceProvider' and the alias 'Basset' => 'JasonLewis\Basset\Facades\Basset' in app/config/app.php.php artisan config:publish jasonlewis/basset and open app/config/packages/jasonlewis/basset/config.php. This is the first place to look when something behaves oddly — build path, cache path, default filters, and the serve route all live here.Route::get('basset', 'Basset\Controller@serve') in routes.php), so collections work in development without a build step.app/start/global.php / a service provider, or in the config's collections array:Basset::collection('main', function ($collection) {
$collection->add('../vendor/bootstrap/less/bootstrap.less');
$collection->add('js/app.js');
});
{{ Basset::styles() }} in <head>, {{ Basset::scripts() }} before </body>.php artisan basset:build.The first use case to prove out is a single main collection combining your Less entry point and your application JS — if that renders in dev and builds into public/assets/build, you understand the package.
Collection-per-context, not per-file. Define vendor, app, and page-specific collections (admin, checkout) rather than one giant collection. Each collection becomes its own combined file, so unrelated pages don't download the admin bundle. Basset::css('collection') / Basset::js('collection') render a single collection; Basset::styles() / Basset::scripts() render all of them.
Keep a vendor/app split. Vendor libraries are added first in a vendor collection; application code goes in app and is added after it. This is the cheapest way to avoid re-downloading jQuery every time you touch one line of app JS, and it documents load order explicitly.
Use Basset::directory() for bulk includes deliberately. It adds every file in a path, but ordering is essentially alphabetical. Fine for images-adjacent CSS or icon sets; dangerous for JS with dependencies. Use add() when order matters.
Filters are a pipeline. Register them globally in config, or per-collection when defining it. Keep one filter per concern (Less compilation, CSS URI rewriting, minification) rather than writing a monolith.
Develop against the serve route, deploy against the build. The route re-runs filters on every request — correct and useful locally, wasteful in production. Make basset:build a deploy step (before or after composer install-style tasks in your release script) and confirm in staging that the layout is hitting built files, not the route.
Cache busting is the reason you build. Built filenames/URLs are versioned, so {{ Basset::styles() }} automatically changes when you rebuild. Never hardcode /assets/build/main.css in a layout — always echo the helper.
One layout partial. Put the helper calls in a single Blade partial (layouts/assets.blade.php) so swapping dev/prod behavior or adding a collection is a one-file change.
public/, not the app root or the package. add('js/app.js') means public/js/app.js. Half of all "file not found" errors are this.add() appends. If a plugin loads before jQuery, the build succeeds and the browser breaks — the error surfaces at runtime, not at build time.php artisan basset:clean then basset:build, and clear Laravel's own caches. When you edit the config (new collections, changed paths), assume a clean is required.<script>/<link> tags outside Basset.app/start definitions interact badly. If collections are defined in code that runs per-request, a cached config may not include them; if they're in the config array, a stale cached config hides new ones. Decide where collections live and be consistent.public/assets/build contain the expected combined file? Does the rendered HTML point at the build rather than the serve route? Does the collection list (Basset::collections() or dumping the config) include what you think? Is the filter throwing a swallowed exception? In that order.How can I help you explore Laravel packages today?