Bài 08: Sử dụng Controller trong laravel

Sau khi route nhận được request thì sẽ chuyển hướng request đến cho controller và giao cho controller này xử lý.  Controller sẽ gọi tới Model để tương tác với cơ sở dữ liệu (database) và  đưa dữ liệu tới View và View sẽ nhận dữ liệu và chuyển thành những đoạn mã HTML rồi gửi về cho Client. Hiện tại tới bài này là chúng ta đang học Controller chứ chưa học Model và View nên mình chỉ giới thiệu Controller và cách sử dụng thôi nhé.

1. Tạo controller trong laravel

Tất cả controller trong laravel được chứa trong thư mục app/controllers và việc tạo tên file, đặt tên controller cũng phải tuân theo nguyên tắc của nó như sau:

  • Trước tiên tôi muốn giới thiệu với các bạn lớp  Controller của Laravel, đây là một lớp xử lý controller chính của Laravel nên tất cả các  Controller mới  phải thừa kế (extends) từ lớp này.
  • Nêu bạn muốn kế thừa từ một Controller khác thì lớp đó phải kế thừa từ lớp  Controller của Laravel. Lúc này  Controller mới tạo sẽ extends từ lớp Controller khác đó.
  • Tên Controller phải trùng với tên File. Ví dụ bạn tạo Controller tên DemoController thì file phải tên là DemoController.php

Tạo Controller kế thừa trực tiếp từ Controller của Laravel

Bước 1: Bạn tạo file DemoController.php nằm trong thư mục app/controllers

Bước 2: Bạn viết code tạo Controller trong file DemoController.php như sau:

<?php
class DemoController extends Controller{
		
}
Lưu ý là trong đó mình có kế thừa từ lớp  Controller của Laravel. Vậy là bạn đã tạo thành công một Controller rồi đấy.

Tạo Controller kế thừa từ một Controller khác

Bây giờ mình sẽ tạo một ExtController và DemoController, DemoController sẽ kế thừa từ ExtController.

Bước 1: Tạo ExtController, bạn tạo file ExtController.php nằm trong folder app/controllers với nội dung như sau:

class ExtController extends Controller{

}
Bước 2: Tạo DemoController, bạn tạo file DemoController.php nằm trong folder app/controllers  với nội dung như sau:

class DemoController extends ExtController{

}
Tới đây bạn sẽ có thắc mắc rằng tại sao lớp ExtController chưa load vào mà trong lớp DemoController có thể kế thừa được? Lý do là Laravel đã load sẵn cho chúng ta nhé.

Việc sử dụng kế thừa qua controller khác như thế này nhằm mục đích tạo ra những hành động dùng chung cho một nhóm controller khác. Ví dụ bạn muốn filter trong các controller của backend xem đã đăng nhập chưa, thay vì bạn filter trong từng controller thì có thể tạo 1 controller AdminController rồi cho các controller khác extends lại.

Tạo Controller trong thư mục con (sub folder)

Ngoài ra chúng ta cũng có thể tạo Controller nằm trong một subfolder.  Ví dụ bạn tạo thư mục con backend trong thư mục app/controllers và tạo một controller AdminController trong thư mục này và đặt tên controller tuân theo quy tắc trên là được. Nhưng để laravel có thể hiểu hiểu được AdminController này thì ngay sau khi tạo controller bạn phải chạy lệnh sau (run command): php artisan dump-autoload

Như bạn thấy đó, việc tạo controller trong sub folder trong laravel rất đơn giản phải không.

2. Tạo Action Controller trong Laravel

Tạo action mới thì bạn cần lưu ý những điều dưới đây.

Khi làm việc với Route::controller thì bạn chú ý việc đặt tên action phải tuân theo quy tắc methodUri như sau:

  • method là post, get, ... và viết thường
  • Uri: Chữ cái đầu tiên của Uri sẽ bắt buộc viết in hoa, cứ 1 chữ in hoa sẽ được tính là 1 đoạn uri được phân cách bởi dấu -

Ví dụ: action getDemoAction sẽ có method là get và Uri là demo-action

Khi làm việc với Route::resource thì controller laravel hỗ trợ 8 action: index, create, store, show, edit, update, destroy nhưng trong controller không nhất thiết phải tạo đủ 8 action này.

Ngoại trừ những điều trên thì action bạn có thể đặt tên tùy ý.

Truyền tham số vào action

Làm việc với Route::controller:

Quay lại ví dụ trên mình viết action hiển thị chi tiết tin tức mà chưa truyền ID vào phải không nào? Bây giờ ta sẽ sửa lại một chút để nhận tham số ID trên URL để sử dụng nhé.

Bước 1: Bạn tạo một Route mới như sau:

Route::controller('/news','NewsController');
Bước 2: Bạn sửa lại file NewsController.php như sau:

class NewsController extends Controller{
    public function getDetailAction($id)
    {
            dd($id);
    }
}

Bước 3: Bạn bạn truy cập URL: http://tênmiềnảocủabạn/news/detail-action/3 bạn sẽ nhận được kết quả $id=3

Làm việc với Route::resource:

Trường hợp này thì bạn xem lại phần cuối bài  Sử dụng Route::controller và Route::resource trong laravel

Các trường hợp khác:

Ngoại trừ hai trường hợp trên thì thông thường khi truyền tham số vào Action bạn phải tuân theo cú pháp như sau:

  • Tên tham số trong route đặt trong cặp thẻ {}, ví dụ {id}
  • Trong action sẽ nhận tham số tương ứng. Ví dụ ta có route là '/chitiet-{id}-{title}' thì trong action sẽ nhận hai tham số tương ứng là nameAction($id, $title)

Ví dụ: Bạn thay đổi nội dung ở Route lại như sau:

Route::get('/chitiet-{id}','NewsController@detail');

Thì khi bạn truy cập URL: http://tênmiềnảocủabạn/chitiet-3 bạn sẽ nhận được biến $id = 3.

3. Sử dụng filter trong controller.

Ngoài việc sử dụng filter ngay trong file routes.php thì khi khai báo route bạn có thể đặt nó trong controller, cụ thể là trong hàm khởi tạo  function __construct của controller bằng cách sử dụng con trỏ $this trỏ tới function beforFilter (filter trước khi bất kỳ action nào được quy định được gọi) hoặc afterFilter (filter sau khi controller được gọi). Cu pháp như sau:

public function __construct(){
	$this->beforeFilter( $filter, $options);
}
Trong đó:

  • $filter là tên của filter trong file filters.php
  • $option là mảng các tùy chọn trong đó
    • on: filter trên method nào
    • except: filter trên tất cả các action của controller trừ  action được khai báo
    • only: chỉ filter trên các action được khai báo}

Ví dụ:

//gọi bộ lọc auth trên tất cả các action trong controller trừ action getLogin
$this->beforeFilter('auth', array('except' => 'getLogin'));

//gọi bộ lọc csrf trên tất cả các action trong controller có method là post
$this->beforeFilter('csrf', array('on' => 'post'));

//sau khi 2 action fooAction và barAction xử lý xong thì filter log được gọi
$this->afterFilter('log', array('only' => array('fooAction', 'barAction')));

Bạn cũng có thể dùng action trong chính controller để sử dụng làm filter bằng cách sử dụng ký tự @ để khai báo, tuy nhiên cách này ít khi được sử dụng. Cú pháp như sau:

public function __construct(){
    $this->beforeFilter('@filterRequests');
}

public function filterRequests($route, $request){
    //
}

4. Kết luận

Như vậy trong bài này mình đã giới thiệu qua về cách khai báo và sử dụng controller một cách cơ bản. Ở bài sau mình sẽ giới thiệu cách bạn tương tác với View bằng Controller.

Nguồn: freetuts.net

Profile photo of adminTheHalfHeart

TheHalfHeart

Có sở thích viết tuts nên đã từng tham gia viết ở một số diễn đàn, đến năm 2014 mới có điều kiện sáng lập ra freetuts.net. Sinh năm 90 và có 1 vợ 2 con, thích ca hát và lập trình.

ĐĂNG BÌNH LUẬN: Đăng câu hỏi trên Facebook để được hỗ trợ nhanh nhất.