在聊天中查询用户的未读消息

我正在尝试建立越来越难的查询... 我正在使用Laravel开发具有简单结构的聊天应用程序:

  • 聊天有很多消息。
  • 每个消息都属于一个用户。
  • 在用户和邮件之间
  • n:m以保存已读邮件。

所以

Chat.php

pre=pre+al.get(i);
perm(pre,al,--k,real);

Message.php

public function messages() {
    return $this->hasMany(Message::class)
}

User.php

public function user() {
    return $this->belongsTo(User::class);
}

public function reads() {
    return $this->belongsToMany(User::class,'reads');
}

好吧,现在我要下一个查询

  

将所有未读邮件的聊天记录给我(登录用户)

这意味着这样:

public function messages() {
    return $this->hasMany(Message::class);
}

public function reads() {
    return $this->belongsToMany(Message::class,'reads');
}

但是那是行不通的,因为如果Chat读取了一条消息,它就会被忽略:(

也许我可以仅将聊天范围限定为 LAST 来实现此目的?或者也许我可以进行这样的操作:

  • 计算所有聊天消息
  • 计算我阅读的所有聊天消息
  • 进行减法运算,如果不为0,则考虑此Chat:D

但是我不知道如何与Eloquent进行这种“操作”。

请帮忙。 谢谢!

gelanxier1989 回答:在聊天中查询用户的未读消息

您阅读的所有聊天的第一个首选ID。

import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyForm extends StatefulWidget {
  @override
  State createState() {
    return _MyFormState();
  }
}

class _MyFormState extends State<MyForm> {
  static final GlobalKey<FormState> _formKey = GlobalKey<FormState>();
  final Map<int,String> model = Map<int,String>();

  @override
  void initState() {
    print('initState()');
    for (int i = 0; i < 20; i++) {
      model[i] = null;
    }
    super.initState();
  }

  String validate(String value) {
    return value.isEmpty ? 'Cannot be blank!' : null;
  }

  void submitForm() {
    final FormState formState = _formKey.currentState;

    if (formState.validate()) {
      print('form is valid');
      formState.save();
    } else {
      print('form is invalid');
    }
  }

  @override
  Widget build(BuildContext context) {
    List<Widget> fields = [];

    for (int i = 0; i < 20; i++) {
      Widget widget = TextFormField(
        initialValue: model[i],decoration: InputDecoration(
          labelText: 'field $i',),validator: validate,onFieldSubmitted: (String value) {
          print('field $i onFieldSubmitted()');
          setState(() {
            model[i] = value;
          });
        },onChanged: (String value) {
          print('field $i onChanged()');
          setState(() {
            model[i] = value;
          });
        },onSaved: (String value) {
          print('field $i onSaved()');
          setState(() {
            model[i] = value;
          });
        },);
      fields.add(widget);
    }

    fields.add(RaisedButton(
      child: Text('save'),onPressed: submitForm,));

    return Form(
      key: _formKey,child: ListView(
        children: fields,);
  }
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',theme: ThemeData(
        primarySwatch: Colors.blue,home: Scaffold(
        appBar: AppBar(
          title: Text('form test'),body: MyForm(),);
  }
}

然后申请

$pluckedId=Chat::has('messages.reads',function (Builder $q) {
            return $q->where('user_id',auth()->id());
        })->pluck('id');
,

好吧,我终于找到了一种方法,该方法仅提取聊天的最后一条消息,并使用查询生成器方法检查特定用户是否已阅读了该消息。

在这里,我使用子查询发布魔法范围;)

public function scopeUnreadBy(Builder $builder,int $userId)
{
    //First,look for Chats with Messages
    return $builder->whereHas('messages',function (Builder $q) use ($userId) { 
        $q->select(['last_message' => function(\Illuminate\Database\Query\Builder $sub) {
            // Then,take only last one Message
            $sub->select('id')
                ->from('messages')
                ->where('chat_id','chats.id')
                ->latest()
                ->limit(1);
        }])->whereDoesntHave('reads',function(Builder $q) use ($userId) {
            // Finally,check that last one has not been read :D
            return $q->where('user_id',$userId);
        });
    });
}

Ph,那很难。

我希望它对其他人有帮助!

请记住,所有这些都可以通过一个查询完成;)

本文链接:https://www.f2er.com/3161134.html

大家都在问