2012-03-11 37 views
17

Tôi đang theo dõi chương bảo mật của cuốn sách Symfony 2.Xóa bản ghi trong bảng nhiều người

Có một ví dụ với bảng USERSGROUPS. Có mối quan hệ nhiều đến nhiều giữa USERSGROUPS, tạo cơ sở dữ liệu trong bảng có tên là USERGROUPS.

Những gì tôi muốn là để xóa một bản ghi từ USERGROUPS, ví dụ:

DELETE from USERGROUPS WHERE user_id = 1 and group_id = 1 

Tôi không biết làm thế nào để làm điều này vì tôi không có một tập tin USERGROUPS.php bảng.

Sử dụng DQL, ví dụ, tôi muốn để có thể làm điều này:

$em = $this->getDoctrine()->getEntityManager(); 
$query = $em->createQuery(
    'DELETE FROM AcmeStoreBundle:UserGroups ug WHERE ug.user_id = :user 
    and ug.group_id = :group' 
)->setParameter(array('user' => $userid, 'group' => $groupid)); 

tôi hy vọng bạn sẽ có được ý tưởng.

Sau đó, làm cách nào để xóa khỏi bảng này?

Trả lời

17

Học thuyết nghĩ về dữ liệu dưới dạng đối tượng chứ không phải là hàng trong bảng. Vì vậy, trong các thuật ngữ của Doctrine, có các đối tượng Group (giữ các nhóm người dùng, trong số những thứ khác) và có các đối tượng User (mỗi đối tượng có một thuộc tính lưu trữ các Nhóm mà người dùng đang ở). Nhưng không có đối tượng UserGroup. Ý tưởng của Doctrine (và bất kỳ hệ thống ORM nào) là để cho nhà phát triển quên đi những bảng trung gian này mà cơ sở dữ liệu có thể cần nhưng điều đó không cần thiết về mặt mô hình đối tượng của chương trình.

Vì vậy, những gì bạn muốn làm là tải lên đối tượng người dùng có liên quan, hãy xóa nhóm khỏi thuộc tính $ nhóm và duy trì đối tượng người dùng đã sửa đổi. (Hoặc ngược lại, tức là tải lên đối tượng Group có liên quan và loại bỏ User khỏi nó.) DQL có thể xử lý được điều này, nhưng tôi nghĩ nó dễ dàng hơn khi thực hiện nó mà không có DQL như câu lệnh DELETE của DQL là xóa toàn bộ đối tượng, sửa đổi các thuộc tính của chúng.

Hãy thử:

$user = $em->find('User', $userId); 
$user->removeGroup($groupId); //make sure the removeGroup method is defined in your User model. 
$em->persist($user); 
$em->flush(); //only call this after you've made all your data modifications 

Lưu ý: nếu bạn không có một phương pháp removeGroup() trong mô hình tài khoản của bạn (tôi nghĩ Symfony có thể tạo ra một cho bạn, nhưng tôi có thể là sai), phương pháp này có thể trông như sau.

//In User.php, and assuming the User's groups are stored in $this->groups, 
//and $groups is initialized to an empty ArrayCollection in the User class's constructor 
//(which Symfony should do by default). 

class User 
{ 
    //all your other methods 

    public function removeGroup($group) 
    { 
     //optionally add a check here to see that $group exists before removing it. 
     return $this->groups->removeElement($group); 
    } 
} 
+0

Ethan. Cảm ơn bạn rất nhiều! Nó hoạt động :) Tại sao symfony không tự động tạo phương thức này? Tôi tin rằng đó là một nhiệm vụ thực sự phổ biến để xóa một cái gì đó từ nhiều của bạn đến nhiều bảng. –

+0

Vâng, tôi luôn tự hỏi tại sao symfony không tạo ra các phương thức remove (vì nó tạo ra addMethods). Vui mừng nó đã làm việc! – Ethan

+3

Điều gì xảy ra nếu có 1.000.000 bản ghi trong bảng nhiều người liên quan đến người dùng này và tôi chỉ cần xóa một bản ghi? Doctrine sẽ tải tất cả các bản ghi? –

4

Ngoài câu trả lời của @ Ethan, loại bỏ một chiều không hoạt động. Đối với manyToMany mối quan hệ như vậy, bạn phải gọi remove phương pháp từ cả hai thực thể, ví dụ,

$user = $em->findOneById($userId); 
$group = $em->findOneById($groupId); 

$user->removeGroup($group); 
$group->removeUser($user); 

$em->persist($user); 
$em->flush(); 
+0

Giải pháp của bạn có tương đương với Xóa khỏi Bảng nơi col1 = và col2 = không? Liệu nó làm cho truy vấn trong bảng gia nhập? – Volatil3

+0

Dường như là như vậy – Sithu

Các vấn đề liên quan