问题
I am trying to make an "unread" function for my messenger. When I refresh try to refresh the database it shows
There is no column with name 'read' on table 'messages'.
This error and my "unread" feature is not working. I am using SQlite.
Here's my Unread migration:-
public function up()
{
Schema::table('messages', function (Blueprint $table) {
$table->boolean('read')->after('to')->default(false);
});
}
public function down()
{
Schema::table('messages', function (Blueprint $table) {
$table->dropColumn('read');
});
}
Here my Messages migration:-
public function up()
{
Schema::create('messages', function (Blueprint $table) {
$table->id();
$table->integer('from')->unsigned();
$table->integer('to')->unsigned();
$table->text('text');
$table->timestamps();
});
}
Here's my controller:-
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\User;
use App\Friend;
use App\Message;
use App\Events\NewMessage;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;
class ContactsController extends Controller
{
public function __construct()
{
$this->middleware('auth');
}
public function index()
{
return view('home');
}
public function get(){
$sem = Auth::user()->id;
$contacts = DB::table('friends')
->where('my_id', $sem)
->get();
// get a collection of items where sender_id is the user who sent us a message
// and messages_count is the number of unread messages we have from him
$unreadIds = Message::select(\DB::raw('`from` as sender_id, count(`from`) as messages_count'))
->where('to', auth()->id())
->where('read', false)
->groupBy('from')
->get();
// add an unread key to each contact with the count of unread messages
$contacts = $contacts->map(function($contact) use ($unreadIds) {
$contactUnread = $unreadIds->where('sender_id', $contact->friends_id)->first();
$contact->unread = $contactUnread ? $contactUnread->messages_count : 0;
return $contact;
});
return response()->json($contacts);
}
public function getMessagesFor($id)
{
$messages = Message::where('from', $id)->orWhere('to', $id)->get();
$messages = Message::where(function($q) use ($id) {
$q->where('from', auth()->id());
$q->where('to', $id);
})->orWhere(function($q) use ($id){
$q->where('from', $id);
$q->where('to', auth()->id());
})
->get();
return response()->json($messages);
}
public function send(Request $request)
{
$message = Message::create([
'from' => auth()->id(),
'to' => $request->contact_id,
'text' => $request->text
]);
broadcast(new NewMessage($message));
return response()->json($message);
}
}
This is where contacts Ids are coming from:-
public function up()
{
Schema::create('friends', function (Blueprint $table) {
$table->id();
$table->string('created_by');
$table->string('my_id');
$table->string('friends_id');
$table->string('name');
$table->timestamps();
});
}
I can't seem to figure out the problem and have been stuck with this since weeks, your help would really be appreciated.
回答1:
There are a few things that may be causing you issues with your migration.
You have a couple of reserved words in SQL (thought maybe not in SQLite) that could be causing an issue. I would remove them in favor of something that is not potentially causing a conflict.
You might assign foreign keys to the database so it will play nice with your models. Then you don't have to go through the whole
DB::raw('from...
stuff, it is automatically assigned by the model if you set up the relationships correctly.I think the issue you are having though, is that you may be using the migration a bit differently that expected. Why not put the boolean field on the original migration? If this migration isn't run, or is run in the wrong order, or if it is run in
down()
mode, thatread
field will not be in the database table.
I suggest to test, start with the following migration. Make note of the different (non-conflicting) field names and the auto-increment field:
Schema::create('messages', function (Blueprint $table) {
$table->increments('id');
$table->integer('from_id')->unsigned();
$table->integer('to_id')->unsigned();
$table->boolean('has_read')->default(false);
$table->text('text');
$table->timestamps();
});
Run a fresh migration on the database with this. Rework your controller code to work with the new field names and test. If this fixes the error:
There is no column with name 'read' on table 'messages'.
Then I would recommend adding in the foreign keys to those ids like this for example:
$table->foreign('from_id')->references('id')->on('users');
But this is a whole different issue and requires re-working of your controller db draws. For now, see if the above migration will solve the original error.
来源:https://stackoverflow.com/questions/62397745/unread-message-feature-not-working-in-laravel