Communitygithub.com

laravel-patterns

Laravel Architekturmuster für Routing/Controller, Eloquent ORM, Service-Schichten, Warteschlangen, Events, Caching und API-Ressourcen für Produktionsanwendungen.

Was ist laravel-patterns?

Dieses Skill bietet umfassende Architekturmuster für Laravel, die auf skalierbare und wartbare Produktionsanwendungen abzielen. Es behandelt Schlüsselbereiche wie Controller-Schichten, Eloquent-Modellierung, Service-Container-Bindungen, API-Ressourcen, Formularvalidierung, Transaktionen und Hintergrundjobs. Entwickler können es nutzen, um saubere Grenzen zwischen HTTP-Controllern, Service-Schichten und Aktionen zu wahren, wie im empfohlenen Verzeichnislayout (`app/Actions`, `app/Services`) gezeigt. Plattformunabhängig: Es funktioniert mit jeder Laravel-Anwendung (≥9.x) und kann in Claude Code, Cursor, Codex oder jedem anderen KI-Assistenten verwendet werden. Die Anleitung basiert auf der offiziellen SKILL.md-Dokumentation und umfasst konkrete Codebeispiele für Route-Model-Binding, benutzerdefinierte Casts, Query-Scopes, Migrationsnamen und API-Paginierung. Ziel ist es, typische Fehler wie N+1-Probleme, fehlende Autorisierung oder inkonsistente API-Antworten durch klare Muster zu vermeiden.

Funktioniert mit~Claude Code~Codex CLI~Cursor
npx skills add https://github.com/affaan-m/ECC/tree/main/skills/laravel-patterns

In Ihrer bevorzugten KI fragen

Öffnet einen neuen Chat, in dem dieser Agent-Skill bereits geladen ist.

Dokumentation

Laravel Entwicklungsmuster

Produktionsreife Laravel Architekturmuster für skalierbare, wartbare Anwendungen.

Wann verwenden

  • Erstellen von Laravel Webanwendungen oder APIs
  • Strukturieren von Controllern, Services und Domänenlogik
  • Arbeiten mit Eloquent Modellen und Beziehungen
  • Entwerfen von APIs mit Ressourcen und Paginierung
  • Hinzufügen von Warteschlangen, Events, Caching und Hintergrundjobs

Wie es funktioniert

  • Strukturieren Sie die App um klare Grenzen (Controller -> Services/Actions -> Modelle).
  • Verwenden Sie explizite Bindungen und Scoped-Bindungen, um das Routing vorhersehbar zu halten; erzwingen Sie dennoch Autorisierung für die Zugriffskontrolle.
  • Bevorzugen Sie typisierte Modelle, Casts und Scopes, um die Domänenlogik konsistent zu halten.
  • Verlagern Sie IO-intensive Arbeiten in Warteschlangen und cachen Sie teure Lesevorgänge.
  • Zentralisieren Sie die Konfiguration in config/* und halten Sie Umgebungen explizit.

Beispiele

Projektstruktur

Verwenden Sie ein konventionelles Laravel-Layout mit klaren Schichtgrenzen (HTTP, Services/Actions, Modelle).

Empfohlenes Layout

app/
├── Actions/            # Einzweck-Anwendungsfälle
├── Console/
├── Events/
├── Exceptions/
├── Http/
│   ├── Controllers/
│   ├── Middleware/
│   ├── Requests/       # Form-Request-Validierung
│   └── Resources/      # API-Ressourcen
├── Jobs/
├── Models/
├── Policies/
├── Providers/
├── Services/           # Koordinierende Domänendienste
└── Support/
config/
database/
├── factories/
├── migrations/
└── seeders/
resources/
├── views/
└── lang/
routes/
├── api.php
├── web.php
└── console.php

Controller -> Services -> Actions

Halten Sie Controller schlank. Verlagern Sie Orchestrierung in Services und Einzwecklogik in Actions.

final class CreateOrderAction
{
    public function __construct(private OrderRepository $orders) {}

    public function handle(CreateOrderData $data): Order
    {
        return $this->orders->create($data);
    }
}

final class OrdersController extends Controller
{
    public function __construct(private CreateOrderAction $createOrder) {}

    public function store(StoreOrderRequest $request): JsonResponse
    {
        $order = $this->createOrder->handle($request->toDto());

        return response()->json([
            'success' => true,
            'data' => OrderResource::make($order),
            'error' => null,
            'meta' => null,
        ], 201);
    }
}

Routing und Controller

Bevorzugen Sie Route-Model-Binding und Ressourcen-Controller für Klarheit.

use Illuminate\Support\Facades\Route;

Route::middleware('auth:sanctum')->group(function () {
    Route::apiResource('projects', ProjectController::class);
});

Route Model Binding (Scoped)

Verwenden Sie Scoped-Bindungen, um mandantenübergreifenden Zugriff zu verhindern.

Route::scopeBindings()->group(function () {
    Route::get('/accounts/{account}/projects/{project}', [ProjectController::class, 'show']);
});

Verschachtelte Routen und Binding-Namen

  • Halten Sie Präfixe und Pfade konsistent, um doppelte Verschachtelung zu vermeiden (z.B. conversation vs. conversations).
  • Verwenden Sie einen einzelnen Parameternamen, der dem gebundenen Modell entspricht (z.B. {conversation} für Conversation).
  • Bevorzugen Sie Scoped-Bindungen bei Verschachtelung, um Eltern-Kind-Beziehungen zu erzwingen.
use App\Http\Controllers\Api\ConversationController;
use App\Http\Controllers\Api\MessageController;
use Illuminate\Support\Facades\Route;

Route::middleware('auth:sanctum')->prefix('conversations')->group(function () {
    Route::post('/', [ConversationController::class, 'store'])->name('conversations.store');

    Route::scopeBindings()->group(function () {
        Route::get('/{conversation}', [ConversationController::class, 'show'])
            ->name('conversations.show');

        Route::post('/{conversation}/messages', [MessageController::class, 'store'])
            ->name('conversation-messages.store');

        Route::get('/{conversation}/messages/{message}', [MessageController::class, 'show'])
            ->name('conversation-messages.show');
    });
});

Wenn Sie möchten, dass ein Parameter zu einer anderen Modellklasse aufgelöst wird, definieren Sie eine explizite Bindung. Für benutzerdefinierte Bindungslogik verwenden Sie Route::bind() oder implementieren Sie resolveRouteBinding() im Modell.

use App\Models\AiConversation;
use Illuminate\Support\Facades\Route;

Route::model('conversation', AiConversation::class);

Service Container Bindungen

Binden Sie Schnittstellen an Implementierungen in einem Service-Provider für klare Abhängigkeitsverkabelung.

use App\Repositories\EloquentOrderRepository;
use App\Repositories\OrderRepository;
use Illuminate\Support\ServiceProvider;

final class AppServiceProvider extends ServiceProvider
{
    public function register(): void
    {
        $this->app->bind(OrderRepository::class, EloquentOrderRepository::class);
    }
}

Eloquent Modell-Muster

Modellkonfiguration

final class Project extends Model
{
    use HasFactory;

    protected $fillable = ['name', 'owner_id', 'status'];

    protected $casts = [
        'status' => ProjectStatus::class,
        'archived_at' => 'datetime',
    ];

    public function owner(): BelongsTo
    {
        return $this->belongsTo(User::class, 'owner_id');
    }

    public function scopeActive(Builder $query): Builder
    {
        return $query->whereNull('archived_at');
    }
}

Benutzerdefinierte Casts und Value Objects

Verwenden Sie Enums oder Value Objects für strenge Typisierung.

use Illuminate\Database\Eloquent\Casts\Attribute;

protected $casts = [
    'status' => ProjectStatus::class,
];
protected function budgetCents(): Attribute
{
    return Attribute::make(
        get: fn (int $value) => Money::fromCents($value),
        set: fn (Money $money) => $money->toCents(),
    );
}

Eager Loading zur Vermeidung von N+1

$orders = Order::query()
    ->with(['customer', 'items.product'])
    ->latest()
    ->paginate(25);

Query-Objekte für komplexe Filter

final class ProjectQuery
{
    public function __construct(private Builder $query) {}

    public function ownedBy(int $userId): self
    {
        $query = clone $this->query;

        return new self($query->where('owner_id', $userId));
    }

    public function active(): self
    {
        $query = clone $this->query;

        return new self($query->whereNull('archived_at'));
    }

    public function builder(): Builder
    {
        return $this->query;
    }
}

Global Scopes und Soft Deletes

Verwenden Sie Global Scopes für Standard-Filterung und SoftDeletes für wiederherstellbare Datensätze. Verwenden Sie entweder einen Global Scope oder einen benannten Scope für denselben Filter, nicht beide, es sei denn, Sie beabsichtigen ein geschichtetes Verhalten.

use Illuminate\Database\Eloquent\SoftDeletes;
use Illuminate\Database\Eloquent\Builder;

final class Project extends Model
{
    use SoftDeletes;

    protected static function booted(): void
    {
        static::addGlobalScope('active', function (Builder $builder): void {
            $builder->whereNull('archived_at');
        });
    }
}

Query Scopes für wiederverwendbare Filter

use Illuminate\Database\Eloquent\Builder;

final class Project extends Model
{
    public function scopeOwnedBy(Builder $query, int $userId): Builder
    {
        return $query->where('owner_id', $userId);
    }
}

// In Service, Repository usw.
$projects = Project::ownedBy($user->id)->get();

Transaktionen für mehrschrittige Aktualisierungen

use Illuminate\Support\Facades\DB;

DB::transaction(function (): void {
    $order->update(['status' => 'paid']);
    $order->items()->update(['paid_at' => now()]);
});

Migrationen

Benennungskonvention

  • Dateinamen verwenden Zeitstempel: YYYY_MM_DD_HHMMSS_create_users_table.php
  • Migrationen verwenden anonyme Klassen (keine benannte Klasse); der Dateiname kommuniziert die Absicht
  • Tabellennamen sind snake_case und standardmäßig plural

Beispiel-Migration

use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

return new class extends Migration
{
    public function up(): void
    {
        Schema::create('orders', function (Blueprint $table): void {
            $table->id();
            $table->foreignId('customer_id')->constrained()->cascadeOnDelete();
            $table->string('status', 32)->index();
            $table->unsignedInteger('total_cents');
            $table->timestamps();
        });
    }

    public function down(): void
    {
        Schema::dropIfExists('orders');
    }
};

Form Requests und Validierung

Halten Sie die Validierung in Form Requests und transformieren Sie Eingaben in DTOs.

use App\Models\Order;

final class StoreOrderRequest extends FormRequest
{
    public function authorize(): bool
    {
        return $this->user()?->can('create', Order::class) ?? false;
    }

    public function rules(): array
    {
        return [
            'customer_id' => ['required', 'integer', 'exists:customers,id'],
            'items' => ['required', 'array', 'min:1'],
            'items.*.sku' => ['required', 'string'],
            'items.*.quantity' => ['required', 'integer', 'min:1'],
        ];
    }

    public function toDto(): CreateOrderData
    {
        return new CreateOrderData(
            customerId: (int) $this->validated('customer_id'),
            items: $this->validated('items'),
        );
    }
}

API-Ressourcen

Halten Sie API-Antworten mit Ressourcen und Paginierung konsistent.

$projects = Project::query()->active()->paginate(25);

return response()->json([
    'success' => true,
    'data' => ProjectResource::collection($projects->items()),
    'error' => null,
    'meta' => [
        'page' => $projects->currentPage(),
        'per_page' => $projects->perPage(),
        'total' => $projects->total(),
    ],
]);

Events, Jobs und Warteschlangen

  • Emittieren Sie Domänen-Events für Nebeneffekte (E-Mails, Analysen)
  • Verwenden Sie queued Jobs für langsame Arbeiten (Berichte, Exporte, Webhooks)
  • Bevorzugen Sie idempotente Handler mit Wiederholungen und Backoff

Caching

  • Cachen Sie leseintensive Endpunkte und teure Abfragen
  • Invalidieren Sie Caches bei Modell-Events (created/updated/deleted)
  • Verwenden Sie Tags beim Cachen verwandter Daten für einfache Invalidierung

Konfiguration und Umgebungen

  • Halten Sie Geheimnisse in .env und Konfiguration in config/*.php
  • Verwenden Sie umgebungsspezifische Konfigurationsüberschreibungen und config:cache in der Produktion

Individual skills in this repo

This repo contains 20 individual skills — each has its own dedicated page.

accessibility

Design, implement, and audit inclusive digital products using WCAG 2.2 Level AA. Use when building or auditing UI that must meet WCAG 2.2 Level AA, or when reviewing a change for keyboard, contrast, or screen-reader support.

affaan-m/content-engine

Create platform-native content systems for X, LinkedIn, TikTok, YouTube, newsletters, and repurposed multi-platform campaigns. Use when the user wants social posts, threads, scripts, content calendars, or one source asset adapted cleanly across platforms.

affaan-m/ECC

Multi-platform content distribution across X, LinkedIn, Threads, and Bluesky. Adapts content per platform using content-engine patterns. Never posts identical content cross-platform. Use when the user wants to distribute content across social platforms.

affaan-m/fal-ai-media

Unified media generation via fal.ai MCP — image, video, and audio. Covers text-to-image (Nano Banana), text/image-to-video (Seedance, Kling, Veo 3), text-to-speech (CSM-1B), and video-to-audio (ThinkSound). Use when the user wants to generate images, videos, or audio with AI.

affaan-m/manim-video

日本語翻訳:このファイルは manim-video 用の日本語翻訳が必要です

affaan-m/remotion-video-creation

Remotion のベストプラクティス - React で動画を作成する。3D、アニメーション、音声、字幕、チャート、トランジションなどをカバーするドメイン固有の29のルール。

affaan-m/video-editing

AI-assisted video editing workflows for cutting, structuring, and augmenting real footage. Covers the full pipeline from raw capture through FFmpeg, Remotion, ElevenLabs, fal.ai, and final polish in Descript or CapCut. Use when the user wants to edit video, cut footage, create vlogs, or build video content.

agent-architecture-audit

Full-stack diagnostic for agent and LLM applications. Audits the 12-layer agent stack for wrapper regression, memory pollution, tool discipline failures, hidden repair loops, and rendering corruption. Produces severity-ranked findings with code-first fixes. Essential for developers building agent applications, autonomous loops, or any LLM-powered feature. Use when an agent or LLM feature misbehaves and the failing layer is unknown, or before shipping an agent stack.

agent-eval

Head-to-head comparison of coding agents (Claude Code, Aider, Codex, etc.) on custom tasks with pass rate, cost, time, and consistency metrics. Use when choosing between coding agents, or when a change to an agent setup needs measured pass rate, cost, and time rather than an impression.

agent-harness-construction

Design and optimize AI agent action spaces, tool definitions, and observation formatting for higher completion rates. Use when defining or revising an agent

agentic-engineering

Operate as an agentic engineer using eval-first execution, decomposition, and cost-aware model routing. Use when planning or executing engineering work that agents will carry out end to end.

agentic-os

Build persistent multi-agent operating systems on Claude Code. Covers kernel architecture, specialist agents, slash commands, file-based memory, scheduled automation, and state management without external databases. Use when building a persistent multi-agent system on Claude Code with its own memory, commands, and scheduling.

agent-introspection-debugging

Structured self-debugging workflow for AI agent failures using capture, diagnosis, contained recovery, and introspection reports. Use when an agent run fails and you need a reproducible diagnosis instead of a retry.

agent-payment-x402

Add x402 payment execution to AI agents with per-task budgets, spending controls, and non-custodial wallets. Supports Base through agentwallet-sdk and X Layer through OKX Payments / OKX Agent Payments Protocol. Use when an agent must pay for something itself and needs per-task budgets, spending controls, and a non-custodial wallet.

agent-self-evaluation

Use after completing any non-trivial task. The agent self-rates its output on 5 axes — accuracy, completeness, clarity, actionability, conciseness — with concrete evidence per criterion. Produces a structured 1-5 scorecard with specific improvement suggestions.

agent-sort

Build an evidence-backed ECC install plan for a specific repo by sorting skills, commands, rules, hooks, and extras into DAILY vs LIBRARY buckets using parallel repo-aware review passes. Use when ECC should be trimmed to what a project actually needs instead of loading the full bundle.

ai-first-engineering

Engineering operating model for teams where AI agents generate a large share of implementation output. Use when setting team process, review gates, or ownership rules for a codebase largely written by agents.

ai-regression-testing

Regression testing strategies for AI-assisted development. Sandbox-mode API testing without database dependencies, automated bug-check workflows, and patterns to catch AI blind spots where the same model writes and reviews code. Use when adding regression coverage to AI-assisted code, or when the same model both wrote and reviewed a change.

android-clean-architecture

Clean Architecture patterns for Android and Kotlin Multiplatform projects — module structure, dependency rules, UseCases, Repositories, and data layer patterns. Use when structuring modules, layers, or data flow in an Android or KMP project.

angular-developer

Generates Angular code and provides architectural guidance. Trigger when creating projects, components, or services, or for best practices on reactivity (signals, linkedSignal, resource), forms, dependency injection, routing, SSR, accessibility (ARIA), animations, styling (component styles, Tailwind CSS), testing, or CLI tooling.

Verwandte Skills