【问题标题】:Model with multiple polymorphic fields具有多个多态字段的模型
【发布时间】:2016-12-14 14:03:17
【问题描述】:

我需要在我的系统中添加一个功能,它是一个库存控制系统。

要添加的功能是关于在不同模型中开始聊天的可能性。我有 Products、Sellers、ProductCollections 和更多对象,我需要在它们中开始对话。

所以我考虑制作一个包含三个多态字段的表,以使其完全可用于任何变体。这是字段

sender_id
sender_type

topic_id
topic_type

receiver_id
receiver_type

以及使对话成为可能的适当字段(消息、in_reply_of 等...)

发送者和接收者需要是多态的,因为系统用户和客户之间可以进行对话。

我的方法是否正确?这会以这种方式工作吗?另外我不知道如何保存聊天实体。

【问题讨论】:

  • SystemUsers 和Customers 还有其他共同的关系吗? topic_id 中将使用的其他模型呢。
  • 我想使用 topic_id 和 topic_type 来保存任何对象,所以我无法将聊天功能添加到系统中的任何模型
  • 我上一个问题问的共同关系呢?
  • 哦,对不起,不,他们没有任何共同的关系。一个是登录内网系统,一个是给客户的..
  • 最后一个问题... 我如何保存聊天实体是什么意思?

标签: php laravel eloquent polymorphic-associations


【解决方案1】:

如果您想为多个发送者、接收者和主题设置聊天,我相信这种关系很好。

另外,我无法理解您所说的 Chat 实体的确切含义,但下面的方法应该可以消除您对此方法可能存在的任何疑问。

以下是完成工作的方法!

设置关系

按以下方式设置关系

class Chat
{
  public function sender()
  {
    return $this->morphTo();
  }

  public function topic()
  {
    return $this->morphTo();
  }

  public function receiver()
  {
    return $this->morphTo();
  }
}

class SystemUser
{
  public function sentChats()
  {
    return $this->morphMany('App\Chat', 'sender');
  }

  public function receivedChats()
  {
    return $this->morphMany('App\Chat', 'receiver');
  }
}

class Customer
{
  public function sentChats()
  {
    return $this->morphMany('App\Chat', 'sender');
  }

  public function receivedChats()
  {
    return $this->morphMany('App\Chat', 'receiver');
  }
}

class Illustrate
{
  public function illustrable()
  {
    return $this->morphTo();
  }

  public function chats()
  {
    return $this->morphMany('App\Chat', 'topic');
  }
}

创建聊天

如何创建聊天

public function create()
{
  $inputs = request()->only([
    'sender_id', 'sender_type', 'receiver_id', 'receiver_type', 'topic_id', 'topic_type',
    'message', 'in_reply_of',
  ]);

  $sender = $this->getSender($inputs);
  $receiver = $this->getReceiver($inputs);
  $topic = $this->getTopic($inputs);

  if($sender && $receiver && $topic) {
    $chat = $sender->sentChats()->create([
              'receiver_id' => $receiver->id,
              'receiver_type' => get_class($receiver),
              'topic_id' => $topic->id,
              'topic_type' => get_class($topic),
              'message' => $inputs['message'],
              'in_reply_of' => $inputs['in_reply_of'],
            ]);
  }
}

private function getSender($inputs)
{
  if(isset($inputs['sender_type'], $inputs['sender_id']) && is_numeric($inputs['sender_id'])) {
    switch($inputs['sender_type']) {
      case 'SystemUser':
        return SystemUser::find($inputs['sender_id']);
      case 'Customer':
        return Customer::find($inputs['sender_id']);
      default:
        return null;
    }
  }
}

private function getReceiver($inputs)
{
  if(isset($inputs['receiver_type'], $inputs['receiver_id']) && is_numeric($inputs['receiver_id'])) {
    switch($inputs['receiver_type']) {
      case 'SystemUser':
        return SystemUser::find($inputs['receiver_id']);
      case 'Customer':
        return Customer::find($inputs['receiver_id']);
      default:
        return null;
    }
  }
}

private function getTopic($inputs)
{
  if(isset($inputs['topic_type'], $inputs['topic_id']) && is_numeric($inputs['topic_id'])) {
    switch($inputs['topic_type']) {
      case 'Illustrate':
        return Illustrate::find($inputs['topic_id']);
      default:
        return null;
    }
  }
}

聊天

public function get($id) {
  $chat = Chat::find($id);

  $sender = $chat->sender;

  // Inverse
  // $systemUser = SystemUser::find($id);
  // $systemUser->sentChats->where('id', $chatId);

  $receiver = $chat->receiver;

  // Inverse
  // $customer = Customer::find($id);
  // $customer->receivedChats->where('id', $chatId);

  $topic = $chat->topic;

  // Inverse
  // $illustrate = Illustrate::find($id);
  // $illustrate->chats;
}

注意:-请理解我还没有测试过这些...这只是一个关于如何完成工作的小例子。

如果您在理解这一点时遇到任何问题,请告诉我。

【讨论】:

  • 太棒了。感谢您的宝贵时间。
  • @Alan 很高兴我能帮上忙 :)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-08-17
  • 2017-04-23
  • 2011-08-05
  • 1970-01-01
相关资源
最近更新 更多