아래 crud 예제를 스케폴딩 삼아 작업을 합니다.
시간이 괜찮으신 분들은 초급 예제를 해보는 것을 추천합니다
시간이 없고 옵저버만 알고 싶은 분들은 훑어보기만 해도 많은 도움이 될 것입니다.
Laravel CRUD 초급 예제
- Laravel 9 CRUD 초급 예제 1부 : Setting & Create- Laravel 9 CRUD 초급 예제 2부 : Read & Update & Delete
- Laravel 9 CRUD 예제 3부 : 페이지네이션(Pagination)
- Laravel 9 CRUD 예제 4부 : 유효성 검사(Validation)
라라벨 공부
개요
옵저버는 관측자라는 뜻으로 observer pattern의 그 observer가 맞습니다.
옵저버의 목록에 객체를 등록하면 객체가 행동을 취하면 옵저버에게 통지가 가고 옵저버는 그에 맞춘 행동을 취합니다.
그 스타의 옵저버와 역할이 같습니다.
상대방 기지를 몰래 감시하다가 상대 행동에 따라 맞춤형으로 대처하는 것이죠.
위에서 말했듯이 이전 글을 기초로 진행합니다.
이전 글을 모르시는 분은 간단한 CRUD로 Product 데이터를 등록하는 게시판이라고 이해하시면 됩니다.
사용해보자
Product 모델의 데이터를 관측할 것이므로 ProductObserver로 등록합니다.
php artisan make:observer ProductObserver --model=product
그러면 아래와 같이 옵저버 클래스가 생성됩니다.
<?php
namespace App\Observers;
use App\Models\product;
class ProductObserver
{
/**
* Handle the product "created" event.
*
* @param \App\Models\product $product
* @return void
*/
public function created(product $product)
{
//
}
/**
* Handle the product "updated" event.
*
* @param \App\Models\product $product
* @return void
*/
public function updated(product $product)
{
//
}
/**
* Handle the product "deleted" event.
*
* @param \App\Models\product $product
* @return void
*/
public function deleted(product $product)
{
//
}
/**
* Handle the product "restored" event.
*
* @param \App\Models\product $product
* @return void
*/
public function restored(product $product)
{
//
}
/**
* Handle the product "force deleted" event.
*
* @param \App\Models\product $product
* @return void
*/
public function forceDeleted(product $product)
{
//
}
}
위가 기본으로 만들어지는 옵저버 메서드들입니다.
연결된 모델이 생성, 수정, 삭제 등등의 작업이 일어날 시 실행됩니다.
그리고 우리가 만들 것은 Product (crud에서 사용) 모델의 이력을 쌓는 것입니다
이력 테이블의 모델과 마이그레이션을 만들어줍시다.
php artisan make:model ProductHistory -m
그리고 만들어진 product_hitories_table를 아래와 같이 수정합시다.
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('product_histories', function (Blueprint $table) {
$table->id();
$table->string("type");
$table->string("content");
$table->timestamp("created_at");
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('product_histories');
}
};
수정 후 적용시켜줍시다.
php artisan migrate:refresh
그리고 같이 만들어진 ProdcutHistory 모델은 아래처럼 채워줍시다.
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class ProductHistory extends Model
{
use HasFactory;
// created_at, updated_at을 넣어주는 기능을 끕니다
public $timestamps = false;
protected $fillable = [
'type', 'content', 'created_at'
];
public static function boot()
{
parent::boot();
// created_at을 자동으로 넣어줍니다.
static::creating(function ($model) {
$model->created_at = $model->freshTimestamp();
});
}
}
옵저버는 객체와 연결해야 합니다.
라라벨에서 옵저버가 관측할 객체는 바로 모델입니다.
아래처럼 옵저버와 모델을 연결해줍시다.
<?php
namespace App\Providers;
use App\Models\product;
use App\Observers\ProductObserver;
use Illuminate\Auth\Events\Registered;
use Illuminate\Auth\Listeners\SendEmailVerificationNotification;
use Illuminate\Foundation\Support\Providers\EventServiceProvider as ServiceProvider;
class EventServiceProvider extends ServiceProvider
{
...
/**
* Register any events for your application.
*
* @return void
*/
public function boot()
{
Product::observe(ProductObserver::class);
}
...
}
이제 옵저버와 모델의 연결을 끝냈습니다.
옵저버 클래스의 기능을 수정해줍시다.
app/Observers/ProductObserver.php
<?php
namespace App\Observers;
use App\Models\product;
use App\Models\ProductHistory;
class ProductObserver
{
private $productHistoy;
public function __construct(ProductHistory $productHistory){
$this->productHistoy = $productHistory;
}
/**
* Handle the product "created" event.
*
* @param \App\Models\product $product
* @return void
*/
public function created(product $product)
{
$this->productHistoy->create([
'type' => 'created',
'content' => json_encode($product)
]);
}
/**
* Handle the product "updated" event.
*
* @param \App\Models\product $product
* @return void
*/
public function updated(product $product)
{
$this->productHistoy->create([
'type' => 'updated',
'content' => json_encode($product)
]);
}
/**
* Handle the product "deleted" event.
*
* @param \App\Models\product $product
* @return void
*/
public function deleted(product $product)
{
$this->productHistoy->create([
'type' => 'deleted',
'content' => json_encode($product)
]);
}
}
위 코드는 Product를 추가하거나 수정하거나 삭제할 때 이력 테이블을 쌓습니다.
각각의 메서드에 매개변수로 오는 $product 값이 수정되거나 추가되고 삭제된 데이터를 의미하기에 해당 데이터를 이력으로 쓰기 위해 저장해줍시다, 어떻게 보면 백업이라고도 생각할 수 있겠네요.
참고로 updated 메서드 같은 경우는 데이터가 변경되지 않으면 실행되지 않습니다.
그러면 결과는 아래와 같습니다.
테이블에 저장된 데이터는 아래와 같습니다.
이렇게 간단하게 이력 쌓기 기능을 만들어보았습니다.
만약 작동하지 않는 다면 모델 클래스에 use HasEvents를 추가했는지 확인해봅시다.
궁금한 점이 있으시면 댓글 남겨주시기 바랍니다.
'PHP > Laravel' 카테고리의 다른 글
[Laravel9] 라라벨 테스팅 만들기 with Trait, Factory (0) | 2022.10.28 |
---|---|
[Laravel9] 라라벨 이메일 보내기 with Google SMTP, Markdown (0) | 2022.10.24 |
Laravel 라라벨 스케줄링(Scheduling)하기 with crontab (0) | 2022.09.15 |
Laravel9 라라벨 csv 읽어서 저장하기(CSV seeding) (0) | 2022.09.07 |
Laravel9 이미지 업로드 (with Dropzone) 2부 : Index & Destroy & Ajax (0) | 2022.08.30 |