Laravel query with eloquent

  • November 25, 2023
  • 826

Sử dụng Eloquent(ORM) trong laravel để lấy dữ liệu từ database. 

Get data in one table

Lấy tất cả các sản phẩm có status = 1


// Sql
Select * from products where status = 1;

// ORM
Product::where(['status' => 1])->get();

Get data with relation

Lấy tất cả các sản phẩm có status =1 và các transactions của sản phẩm


Product::with(['transactions'])->where(['status' => 1])->get();

Where in

Lấy các danh mục theo mảng các id


Category::whereIn('id', [1,2])->get();

Where or

Tìm kiếm user theo name hoặc email


User::where(function ($q) use ($search) {
      $q->where('name', 'ilike', '%'.$search.'%')
      ->orWhere('email', 'ilike', '%'.$search.'%');
});

Create

create một user


User::create($data);

Create many records

create nhiều user


User:: insert($data);

Update

update user theo id


User::where('id', $id)->update($data);

UpdateOrCreate

update hoặc create user theo điều kiện


User::updateOrCreate($conditions, $data);

Delete

delete một user


User::where('id', $id)->delete();

Where between

Lấy tất cả các sản phẩm chuẩn bị đến thời gian mua bán, trong vòng 3 ngày trước khi mua bán.


Product::whereBetween('sell_start_at', [now()->startOfDay(), now()->addDays(3)->endOfDay()])->get();

When

Tìm kiếm khi người dùng nhập từ khoá, chỉ khi nào tồn tại $search thì query search trong callback của when mới được gọi.


Product::when($search, function ($q, $search) {
                $q->where(function ($q) use ($search) {
                    $q->where('name_ja', 'ilike', '%' . $search . '%')
                        ->orWhere('name_en', 'ilike', '%' . $search . '%')
                        ->orWhere('name_en', 'ilike', '%' . $search . '%');
                });
            })

Where date

Lấy user theo thời gian mong muốn


User::whereDate('created_at', '>=', $request->start_date);
User::->whereYear('created_at', now()->year);
User::->whereMonth('created_at', now()->month);
User::where('created_at', '>=', now()->toDateString());

Query by date

Lấy dữ liệu theo start_time, end_time

 Event::when($request->start_time, function ($q) use ($request) {
    $q->where(function ($q) use ($request) {
        $q->whereDate('start_time', '>=', $request->start_time)
            ->orWhereNull('start_time');
    });
})
->when($request->end_time, function ($q)  use ($request) {
    $q->where(function ($q) use ($request) {
        $q->whereDate('end_time', '<=', $request->end_time)
            ->orWhereNull('end_time');
    });
});

FindOrFail

Lấy user theo id, nếu id không đúng sẽ throw exception


User::findOrFail($id);

Chunk

Xử lý dữ liệu lớn với chunk, tránh limit memory do xử lý quá nhiều dữ liệu cùng 1 lúc.


Post::chunk(100, function ($posts) {
    foreach ($posts as $post) {
        // Process each post
    }
});

Exists

Kiểm tra xem bảng ghi có tồn tại không sử dụng exitsts sẽ nhanh hơn


Post::where('title', 'Laravel')->exists();

With

Query trong with, lấy relation thoả mãn theo điều kiện.


 Product::with([
          'users' => function ($q) {
                $q->where('user_id', Auth::id());
          }
 ]);

// Lấy relation theo điều kiện và chỉ lấy các trường mong muốn
 Product::with([
          'users' => function ($q) {
                $q->select('id', 'name)
                ->where('user_id', Auth::id());
          }
 ]);

// Chỉ lấy id, name trong relation
Product::with(['users:id,name']);

WhereHas

Lấy các transaction có user thoả mãn điều kiện.


Transaction::whereHas('users', function ($q) use ($conditions) {
       $q->where($conditions);
 });

WhereDoesntHave

Lấy các user không bị khoá tài khoản.


User::whereDoesntHave('userBlocked', function ($q) use ($userId) {
    $q->where([
        'blocker_id' => $userId
    ]);
});

SelectRaw

Lấy các thông tin thanh toán theo tháng.


Payment::query()
    ->selectRaw('EXTRACT(MONTH FROM created_at) as month,
        SUM(CASE WHEN currency = \'ja\' THEN price::numeric ELSE 0 END) as price_ja,
        SUM(CASE WHEN currency = \'en\' THEN price::numeric ELSE 0 END) as price_en,
        SUM(CASE WHEN currency = \'vi\' THEN price::numeric ELSE 0 END) as price_vi,
        COUNT(DISTINCT user_id) as count_payment')
    ->whereYear('created_at', $year)
    ->groupBy('month')
    ->orderBy('month')
    ->get();

OrderByRaw

Lấy các event ưu tiên sắp đến ngày diễn ra, sau đó đến event được tạo gần đây nhất.


Event::orderByRaw("
    CASE 
        WHEN time_start BETWEEN ? AND ? THEN 1 
        ELSE 2 
    END ASC",
    [now()->startOfDay(), now()->addDays(3)->endOfDay()]
)->orderBy('id', 'DESC')
->get();

Debug sql query

Debug sql query


DB::enableQueryLog();
$users = User::where('active', 1)->get();
dd(DB::getQueryLog());

Scopes query

Viết các query hay dùng với scopes để hạn chế lặp code


class User extends Model
{
    public function scopeActive($query)
    {
        return $query->where('active', 1);
    }
}

$activeUsers = User::active()->get();

Mutators & Accessors

Viết lại các thuộc tính sử dụng attribute. Trong database không có trường full_name chúng ta vẫn có thể dùng attribute để lấy fullname ($user->full_name).


class User extends Model
{
    public function getFullNameAttribute()
    {
        return "{$this->first_name} {$this->last_name}";
    }
}

DB transaction

Sử dụng transaction trong laravel theo functional.


$group = DB::transaction(function () use ($data, $userIds) {
    $group = $this->adminGroupRepository->create($data);
    $this->adminRepository->updateSystemUsersToGroup($userIds, $group->id);

    return $group;
});

Sử dụng db transaction trong try catch


try {
DB::beginTransaction();
 $group = $this->adminGroupRepository->create($data);
 $this->adminRepository->updateSystemUsersToGroup($userIds, $group->id);
DB::commit();
} catch (Exception $e) {
DB::rollBack();
}

Khi dùng db transaction ưu tiên dùng functional hơn, nhìn code sẽ ngắn ngọn.

Tổng kết

Trên đây là tổng hợp các hàm hay dùng khi xử dụng ORM trong laravel. Tham khảo thêm bài viết Multiple Where Laravel Eloquent.
Thanks for readding...