Tiếp theo của: Ngu ngơ học làm web (x3) - CakePHP2 – MVC Layout Truy vấn
-----
Phần x4. CakePHP2
– Quan hệ bảng Containable
Xem (clip số 8 – chickenrainshop):
Giải thích về mối quan hệ một – nhiều (phút 0:39).
- một – nhiều
(hasMany >) – (< belongsTo)
Ví dụ:
(hasMany)
- Một book thì có một hoặc nhiều comment (một cuốn sách có
thể có một hoặc nhiều nhận xét)
- Một category thì có nhiều book (một lĩnh vực có thể có một
hoặc nhiều cuốn sách).
(belongsTo)
- Một comment thì phải thuộc về một book nào đó
- Một book thì phải thuộc về một category nào đó
Mối quan hệ này được thiết lập ngay từ khi tạo bảng, để ý
trong bảng comments sẽ có trường book_id, nghĩa là nó đã ngầm định là comment
này phải thuộc về book có id là book_id nào đó. Tương tự, trong bảng book, sẽ
có trường category_id.
Khi thực hiện sinh mã tự động bằng Cake console, thì mối
quan hệ này lại tiếp tục được ghi vào trong model. Tất nhiên, người lập trình
vẫn có thể thiết lập và chỉnh sửa các thông tin này.
Ví dụ,
[Book model]
public $belongsTo = array(
'Category'
=> array(
'className'
=> 'Category',
'foreignKey'
=> 'category_id',
'conditions'
=> '',
'fields'
=> '',
'order'
=> ''
)
);
public $hasMany = array(
'Comment'
=> array(
'className'
=> 'Comment',
'foreignKey'
=> 'book_id',
'dependent'
=> false,
'conditions'
=> '',
'fields'
=> '',
'order'
=> '',
'limit'
=> '',
'offset'
=> '',
'exclusive'
=> '',
'finderQuery'
=> '',
'counterQuery'
=> ''
)
);
[Comment model]
public $belongsTo = array(
'User'
=> array(
'className'
=> 'User',
'foreignKey'
=> 'user_id',
'conditions'
=> '',
'fields'
=> '',
'order'
=> ''
),
'Book'
=> array(
'className'
=> 'Book',
'foreignKey'
=> 'book_id',
'conditions'
=> '',
'fields'
=> '',
'order'
=> ''
)
);
- nhiều – nhiều
(hasAndBelongsToMany >) – (< hasAndBelongsToMany)
Ví dụ, book – writer
- Một cuốn sách có thể được viết bởi nhiều người và ngược
lại một người cũng có thể viết nhiều cuốn sách.
Mối quan hệ này cũng được thiết lập ngay từ khi tạo bảng, bằng cách ra tạo một bảng phụ để
thể hiện mối quan hệ này, ví dụ bảng books_writers.
Khi thực hiện sinh mã tự động bằng Cake console, thì mối
quan hệ này lại tiếp tục được ghi vào trong model.
Ví dụ,
[Book model]
public $hasAndBelongsToMany = array(
'Writer'
=> array(
'className'
=> 'Writer',
'joinTable'
=> 'books_writers',
'foreignKey'
=> 'book_id',
'associationForeignKey'
=> 'writer_id',
'unique'
=> 'keepExisting',
'conditions'
=> '',
'fields'
=> '',
'order'
=> '',
'limit'
=> '',
'offset'
=> '',
'finderQuery'
=> '',
)
);
[Writer model]
public $hasAndBelongsToMany = array(
'Book'
=> array(
'className'
=> 'Book',
'joinTable'
=> 'books_writers',
'foreignKey'
=> 'writer_id',
'associationForeignKey'
=> 'book_id',
'unique'
=> 'keepExisting',
'conditions'
=> '',
'fields'
=> '',
'order'
=> '',
'limit'
=> '',
'offset'
=> '',
'finderQuery'
=> '',
)
);
Xem (clip số 9 – chickenrainshop):
Sử dụng behavior Containable để lấy dữ liệu từ các bảng có
mối quan hệ với nhau (thay thế cho recursive) (phút 1:43)
- Khai báo trong model là sẽ sử dụng Containable,
class Book extends AppModel {
public $actsAs =
['Containable'];
- Ví dụ, trong controller Books, để lấy thêm dữ liệu từ hai
bảng Writers và Comments, sử dụng thêm tùy chọn contain trong hàm find(), cú
pháp là:
‘contain’ => [‘bảng1’, ‘bảng 2’]
Hoặc phức tạp hơn, hạn chế số field của các bảng lấy thêm.
‘contain’ => [
‘bảng 1’ => [‘fields’ => [
‘tên
trường 1’, ‘tên trường 2’
]
],
‘bảng 2’ => [‘fields’ => [
‘tên
trường 1’, ‘tên trường 2’
]
]
]
Ví dụ,
public function truyvan(){
$books
= $this->Book->find('all', [
'contain'
=> ['Writer', 'Comment']
]);
pr($books);exit;
}
Hạn chế số field của hai bảng lấy thêm:
public function truyvan(){
$books
= $this->Book->find('all', [
'fields'
=> ['id', 'title'],
'contain'
=> [
'Writer' => [
'fields' => ['id', 'name']
],
'Comment']
]);
pr($books);exit;
}
-----------
Cập nhật 23/4/2017
-----------