Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Cruddy Laravel Package

kalnoy/cruddy

Cruddy is a Laravel package for building admin CRUD panels with minimal code. Define controllers with fields, columns, filters, and actions to get ready-made index, create, edit, and delete screens. A clean, customizable structure keeps lists, forms, and permissions easy to tailor.

View on GitHub
Deep Wiki
Context7

Getting Started

Step 0 is an install attempt, and it is expected to fail. Cruddy's only release is 2014-12-26, which predates Laravel 5.0. On anything from Laravel 5 through 11, composer require kalnoy/cruddy will conflict out against your illuminate/* constraints before a single file lands. Confirm that in five minutes, record the failure, and then decide what you're actually doing — reading it, or porting it. There is no third option where you require it and move on.

Where to look first, in this order:

  1. The controller layer. Cruddy's whole premise is one controller per Eloquent model, carrying a declarative description of the resource — the columns shown in the list, the fields shown in create/edit, the validation rules, and which attributes are sortable/searchable/filterable. Read this first; it is 80% of the package's value and it fits on a couple of screens.
  2. The field/column type handling. How each declared type maps to a form control and to a cell renderer, and how belongsTo / many-to-many are resolved. This is where the real design decisions live.
  3. The published Blade views. These are Laravel 4 syntax and will not degrade gracefully, but they show you the intended template override seam.
  4. The routes file / service provider. Smallest surface, least interesting, but confirms there's no authorization layer hiding in there — there isn't.

First use case: a single admin resource over a boring model — a Post or a Product — with a list screen (search, sort, pagination), a create form, and an edit form. Do it once by hand against Cruddy's config shape so you feel where the boilerplate actually is. That exercise, not the package, is the deliverable.

If you're on Laravel 4.2 with Cruddy already in the tree, the first use case is different: pick the one endpoint your ops team actually uses, write a characterization test around it, and only then touch anything.

Implementation Patterns

The core pattern: configuration on the controller, generation everywhere else. Every legitimate use of Cruddy is a variation on "declare the resource, let the base class do the rest." Internalize the shape:

  • List config — which columns render, their labels, which are sortable, which are searchable, which accept filters, and the pagination size.
  • Form config — field name → control type (text, textarea, select, checkbox, date), option sources for selects, and relation fields for belongsTo / many-to-many.
  • Validation rules — co-located with the fields, applied on store and update.
  • Relations — declared so the list view can render a related label without an N+1 storm, and the form can render a select rather than a raw foreign key.

Pattern 1 — thin controller, fat config. Never override the generated actions to add "just one" behavior. The moment you do, you've written a bespoke admin controller with a scaffolding package bolted on, and you've lost the only benefit Cruddy offers. If you need per-resource behavior, add a hook to the config, not a hand-written method.

Pattern 2 — one resource per model, no shared controllers. Cruddy's mental model is a 1:1 mapping. Resist the urge to build a generic "manage anything" controller on top of it; that's a different, harder product.

Pattern 3 — authorization belongs in your middleware, not the package. Cruddy does not ship policies or gates. The idiomatic integration is to wrap the generated resource routes in a route group with your auth/admin middleware, and to add a per-resource gate check in the controller constructor. Do this before the first feature, not after — retrofitting authorization onto generated endpoints means auditing every route.

Pattern 4 — override views, not logic. Publishing and editing the Blade templates is the intended customization seam. UI changes go in templates; behavior changes go in config; anything else is a fork.

Pattern 5 — the portable one: reimplement the config object on your current stack. This is how you actually leverage Cruddy day-to-day in 2024+. Take the declarative shape and build it yourself in a few hundred lines:

abstract class CrudController extends Controller
{
    abstract protected function columns(): array;   // list screen
    abstract protected function fields(): array;    // create/edit
    abstract protected function rules(?Model $model = null): array;

    public function index(Request $request) { /* whitelisted sort/filter/paginate */ }
    public function store(FormRequest $request) { /* validated create */ }
    public function update(FormRequest $request, Model $model) { /* validated update */ }
}

Then: a FormRequest whose rules() delegates to the controller's rules(), a set of Blade components (<x-field.text>, <x-field.select) that replace the old Form/Html helpers, resource routes, and a policy check in authorizeResource. You keep the declarative ergonomics, you own the write path, and you get route-model binding, FormRequests, and policies for free — the three things Cruddy structurally cannot give you.

Migration mapping, if you're porting a 4.2 install: illuminate/html → laravelcollective/html or Blade components; Input:: facade → Request; concrete Illuminate\Validation\Validator type hints → contracts; lists() → pluck(); array_get → data_get / Arr::get; {{ }} in L4 views → verify escaping semantics, they changed.

Integration tip — eager loading. Add the relations rendered in the list to the query's with() in one place. Cruddy-era configs typically don't do this for you, and an admin list over a belongsTo is the classic place an N+1 hides for months.

Gotchas and Tips

Assume the write path is unsafe until proven otherwise. CRUD generators of this vintage routinely do $model->fill(Input::all()) with no $fillable/$guarded discipline. Before anything touches a network: grep the source for fill(, confirm $fillable is set on every model, and confirm there is no fillable bypass. This is the failure that matters — remote and quiet.

Sort and filter parameters are attacker-controlled column names. Check whether orderBy and filter clauses are built directly from request input. If they are, whitelist against a declared sortable/filterable list before the query builder ever sees them. Both mass assignment and this are the same class of bug and both are likely present.

No policies, no gates, no roles. The generated endpoints are role-less. Any access control is entirely the host application's job, and the package will not remind you. Put a gate in front of every resource route before you demo it to anyone.

Composer will not resolve on modern Laravel — don't fight it. PHP 5.4–5.6 and Laravel 4.0–4.2 is the only environment it was built against, and that framework's security support ended in 2017. Even a working install means EOL everything.

PHP 8 deprecations surface as errors. Dynamic property creation (deprecated in 8.2) and removed helpers will bite on minor upgrades. There is no upstream to patch them — you are the maintainer from the first commit.

Blade escaping semantics changed between L4 and L5. If you port views, check every {{ }}: things that were previously unescaped are now escaped (double-escaping HTML), and existing {{{ }}} or raw blocks may now mean something different. Visual bugs here look like data corruption.

Pagination defaults are a scaling cliff. If the config doesn't specify a page size, or specifies a large one, admin lists become unbounded queries. Set it explicitly and cap it.

Filter/sort applied in PHP after retrieval is the other scaling trap — it works fine at 500 rows and dies at 500,000. Push it into SQL.

Customization creep is the structural risk. The package's value is that the resource is declarative. One-off overrides — a custom action here, a hand-rendered column there — erode that until you're maintaining a bespoke admin framework nobody signed up for. If you need a custom behavior more than twice, make it a first-class config option or don't build it.

Extension points, such as they are: published views, and subclassing the controller. That's it. There is no event system, no field-type registry, no plugin surface. Anything beyond templates and config is a fork.

Documentation is a decade old and thin on the parts that matter. Authorization, validation behavior, and query construction are undocumented — you will read source to answer those questions. Write down what you learn, with a named owner, because knowledge concentration on a single engineer is a real operational risk here.

Zero dependents means no community fork and no shared patches. No Stack Overflow corpus from the last decade either. Every question is answered by reading 2014 source, by you.

The honest day-to-day summary: on a modern stack you don't run this package, you read it for an afternoon and steal the config shape. On a legacy 4.2 app you fork it, pin it, and treat it as owned code — because it is. Adopting it saves a few days of scaffolding and costs a permanent unsupported fork sitting in the write path of internal tooling, which is the worst place to carry technical debt.

Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
mrnewport/laravel-plaid
mrnewport/laravel-repo
mrnewport/laravel-docsign
mrnewport/laravel-stow
mrnewport/laravel-flow
mrnewport/laravel-priceable
mrnewport/laravel-nestedterms
fredmeng/laravel-apidoc-generator
itstructure/laravel-multilingual-tools
pdustdar/elasticsearch
markupai/php-sdk
rlacerda83/lumem-microservice-shipment
uni-method/symfony-lib
tacticmedia/scim-server-bundle
neika-ai/symfony-bundle
mattleads/agent-publishing-bundle
glavweb/framework-bundle
glavweb/extra-bundle
glavweb/api-bundle
glavweb/admin-bundle