Heim >Backend-Entwicklung >PHP-Tutorial >Entwerfen einer skalierbaren Repository-Struktur in Laravel mit queryFi

Entwerfen einer skalierbaren Repository-Struktur in Laravel mit queryFi

Linda Hamilton
Linda HamiltonOriginal
2024-12-25 18:03:17567Durchsuche

Designing a Scalable Repository Structure in Laravel with queryFi

Einführung

Als ich ein neues Laravel-Projekt startete, fragte ich mich oft, welche Struktur ich verwenden sollte.
Laravel ist sehr gut strukturiert, verstehen Sie mich nicht falsch, es ist schwierig, Dinge durcheinander zu bringen.
Es gibt jedoch einen Haken: Wie vermeiden wir, die gesamte Logik, die wir benötigen, in einen Controller wie UserController.php zu packen?
In diesem Artikel konzentrieren wir uns auf dieses Problem. Ich werde meine bevorzugte Struktur zur Abdeckung meiner Anwendungsfälle zusammen mit einigen Best Practices teilen und erklären, wie queryFi integriert wird.


Erste Schritte

Da Sie hier sind, gehe ich davon aus, dass Sie bereits ein Laravel-Projekt haben oder wissen, wie man eines erstellt, sodass wir diesen Schritt überspringen können. Stellen Sie einfach sicher, dass die API eingerichtet ist.

Wir verwenden die folgende Struktur:

app
├── Repositories
|   ├── Interfaces
|   |   ├── EloquentRepositoryInterface.php
|   └── Eloquent
|       ├── BaseRepository.php
|       └── UserRepository.php
├── Resources
    ├── BaseResource.php
    └── ExtendedJsonResource.php

Hier finden Sie den Ordner Ressourcen sowie einen benutzerdefinierten Logger.


1. Installieren Sie queryFi

# Backend
composer require z3rka/queryfi

# Frontend
npm i queryfi

2. Repository-Schnittstellen hinzufügen

<?php

namespace App\Repositories\Interfaces;

use Illuminate\Http\Resources\Json\JsonResource;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Http\Request;

interface EloquentRepositoryInterface
{
    public function create(array $attributes = [], ?string $successMessage, ?string $errorMessage): JsonResource;

    public function all(Request $request, ?string $errorMessage): JsonResource;

    public function one(Request $request, Model $model, ?string $errorMessage): JsonResource;

    public function update(Request $request, Model $model, ?string $successMessage, ?string $errorMessage): JsonResource;

    public function destroy(Request $request, ?string $successMessage, ?string $errorMessage): JsonResource;
}


3. Fügen Sie die Basis-Repository-Klasse hinzu

Ich füge hier nur drei Methoden hinzu, um alles sauber zu halten und zu vermeiden, dass der Platz mit sich wiederholendem Code überfüllt wird.
Den Rest finden Sie hier.

<?php

namespace App\Repositories\Eloquent;

use Z3rka\Queryfi\HasRelations;

class BaseRepository implements EloquentRepositoryInterface {
    use HasRelations;

    public function __construct(protected Model $model)
    {
        //
    }

    public function create(array $attributes = [], ?string $successMessage, ?string $errorMessage): BaseResource
    {
        try {
            return new BaseResource(
                true,
                $successMessage,
                $this->model->create($attributes)
            );
        } catch (Exception $e) {
            return new BaseResource(
                false,
                $errorMessage,
                [
                    'error' => $e
                ]
            );
        }
    }

    public function all(Request $request, ?string $errorMessage): BaseResource
    {
        try {
            return new BaseResource(
              true, 
              'Success', 
              $this->processModel($request, $this->model)
            );
        } catch (Exception $e) {
            $this->spitError($e);
            return new BaseResource(
                false,
                "Fail",
                $this->model->get(),
                [
                    "error" => $e,
                ]
            );
        }
    }

    public function one(Request $request, Model $model, ?string $errorMessage): BaseResource
    {
        try {
            return new BaseResource(
              true, 
              "success", 
              $this->processModel($request, $model)
            )
        } catch (Exception $e) {
            $this->spitError($e);
            return new BaseResource(
                false,
                "Fail",
                $model,
                [
                    "error" => $e,
                ]
            );
        }
    }
}

Um etwas von einem Modell zurückzugeben, muss man normalerweise ->get() oder find und ->first() verwenden, das ist hier nicht der Fall, da wir das queryFi-Paket verwenden und wir können Folgendes tun:

$this->processModel($request, $this->model)

Dies deckt automatisch ->get() standardmäßig ab, wenn in der Abfrage kein Getter (überprüfen Sie die Getter hier) konfiguriert ist.


4. Benutzer-Repository

<?php

namespace App\Repositories\Eloquent;
use App\Models\User;
use Z3rka\Queryfi\HasRelations;

class UserRepository extends BaseRepository
{
    use HasRelations;

    public function __construct(User $model)
    {
        parent::__construct($model);
    }
}

5. Benutzercontroller

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Repositories\Eloquent\UserRepository;

class UserController extends Controller
{
    public function __construct(public UserRepository $userRepository)
    {
    }

    public function index(Request $request)
    {
      return $this->userRepository
                  ->all($request, "Ooops, there was an error fetching all the users.")
    }

    public function show(Request $request, User $user)
    {
      return $this->userRepository->one(
            $request,
            $user,
            "Ooops, there was an error fetching the user."
        );
    }
}

6. Die API-Route

Route::resource('users', UserController::class)->only(['index', 'show'])

Sobald wir alles eingerichtet haben, können wir Anfragen vom Browser stellen, indem wir Abfrageparameter direkt übergeben, wie zum Beispiel:

url?where[name]=john&select=name&getter=first

Alternativ können wir für einen saubereren Ansatz das queryFi TypeScript-Paket im Frontend verwenden.

import { createQuery } from "queryfi";

const query = createQuery('/api/users', {
    baseUrl: "http://localhost:8000"
  })
  .where({
    id: 1
  })
  .first() // will return an object with the user if it exists.

Die generierte Abfrage sieht folgendermaßen aus:

http://localhost:8000/api/users?where[id]=1&getter=first

Dieser Codeteil gibt den Benutzer mit der ID = 1 zurück.
Wenn Sie .find() verwenden, ist die Antwort automatisch ein Objekt.
Wenn Sie .get() verwenden, wird ein Array zurückgegeben.

Sie können es auf dem Spielplatz ausprobieren, um zu sehen, wie die Reaktion aussieht.

Da wir das HasRelations-Merkmal verwenden, können wir Frontend-Abfragen verketten, um die Daten direkt im Backend umzuwandeln, bevor sie zurückgegeben werden, wie hier gezeigt.

import { createQuery } from "queryfi";

const query = createQuery('/api/users', {
    baseUrl: "http://localhost:8000"
  })
  .where({
    id: 1
  })
  .select(['email', 'id', 'name'])
  .get() // will return an array with one entry if it exists.

Weitere Methoden, die Sie verwenden können, finden Sie in der Dokumentation zu queryFi


ENDE

Und das ist es! ? Jetzt haben Sie einen soliden und leistungsstarken Ausgangspunkt, um Ihre APIs wie ein Profi zu erstellen.
Machen Sie weiter, lassen Sie Ihre Programmiermuskeln spielen und erschaffen Sie etwas Großartiges! ??

Kontaktieren Sie Github, Linkedin, queryFi

Das obige ist der detaillierte Inhalt vonEntwerfen einer skalierbaren Repository-Struktur in Laravel mit queryFi. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn