laravel-mongodb icon indicating copy to clipboard operation
laravel-mongodb copied to clipboard

Undefined array key "_id"

Open elihaidv opened this issue 1 year ago • 1 comments

  • Laravel-mongodb Version: 8.0
  • PHP Version: 8.1
  • Database Driver & Version: "jenssegers/mongodb": "^3.9",

Description:

When Update array in object in embedded array, An exception was thrown.

Steps to reproduce

  1. Query object in embedded array
  2. Update one an array field
  3. An exception was thrown, even update successful

Expected behaviour

Object update without exception

Actual behaviour

Object updated but an exception was thrown Weird thing is, when the field is already updated noting was thrown

Examle Code:

 $story = $user->stories()->where('WAID', $request->WAID)->first();
  if (count($request->reads) > 0 ) {

      $story->reads = $request->reads;
      $story->save(); // Here the exception has thrown
  }
  return $story;
Logs: ErrorException: Undefined array key "_id" in file /var/www/html/slots/vendor/jenssegers/mongodb/src/Relations/EmbedsMany.php on line 259

#0 /var/www/html/slots/vendor/jenssegers/mongodb/src/Relations/EmbedsMany.php(259): Illuminate\Foundation\Bootstrap\HandleExceptions->handleError() #1 /var/www/html/slots/vendor/jenssegers/mongodb/src/Relations/EmbedsMany.php(132): Jenssegers\Mongodb\Relations\EmbedsMany->associateExisting() #2 /var/www/html/slots/vendor/jenssegers/mongodb/src/Relations/EmbedsMany.php(89): Jenssegers\Mongodb\Relations\EmbedsMany->associate() #3 /var/www/html/slots/vendor/jenssegers/mongodb/src/Eloquent/Builder.php(51): Jenssegers\Mongodb\Relations\EmbedsMany->performUpdate() #4 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(1072): Jenssegers\Mongodb\Eloquent\Builder->update() #5 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Database/Eloquent/Model.php(987): Illuminate\Database\Eloquent\Model->performUpdate() #6 /var/www/html/slots/app/Http/Controllers/StoriesController.php(67): Illuminate\Database\Eloquent\Model->save() #7 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Controller.php(54): App\Http\Controllers\StoriesController->store() #8 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/ControllerDispatcher.php(45): Illuminate\Routing\Controller->callAction() #9 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Route.php(262): Illuminate\Routing\ControllerDispatcher->dispatch() #10 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Route.php(205): Illuminate\Routing\Route->runController() #11 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Router.php(721): Illuminate\Routing\Route->run() #12 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(128): Illuminate\Routing\Router->Illuminate\Routing{closure}() #13 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Middleware/SubstituteBindings.php(50): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #14 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Illuminate\Routing\Middleware\SubstituteBindings->handle() #15 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Middleware/ThrottleRequests.php(127): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #16 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Middleware/ThrottleRequests.php(103): Illuminate\Routing\Middleware\ThrottleRequests->handleRequest() #17 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Middleware/ThrottleRequests.php(55): Illuminate\Routing\Middleware\ThrottleRequests->handleRequestUsingNamedLimiter() #18 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Illuminate\Routing\Middleware\ThrottleRequests->handle() #19 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(103): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #20 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Router.php(723): Illuminate\Pipeline\Pipeline->then() #21 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Router.php(698): Illuminate\Routing\Router->runRouteWithinStack() #22 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Router.php(662): Illuminate\Routing\Router->runRoute() #23 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Routing/Router.php(651): Illuminate\Routing\Router->dispatchToRoute() #24 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php(167): Illuminate\Routing\Router->dispatch() #25 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(128): Illuminate\Foundation\Http\Kernel->Illuminate\Foundation\Http{closure}() #26 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TransformsRequest.php(21): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #27 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/ConvertEmptyStringsToNull.php(31): Illuminate\Foundation\Http\Middleware\TransformsRequest->handle() #28 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull->handle() #29 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TransformsRequest.php(21): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #30 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TrimStrings.php(40): Illuminate\Foundation\Http\Middleware\TransformsRequest->handle() #31 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Illuminate\Foundation\Http\Middleware\TrimStrings->handle() #32 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/ValidatePostSize.php(27): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #33 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Illuminate\Foundation\Http\Middleware\ValidatePostSize->handle() #34 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/PreventRequestsDuringMaintenance.php(86): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #35 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Illuminate\Foundation\Http\Middleware\PreventRequestsDuringMaintenance->handle() #36 /var/www/html/slots/vendor/fruitcake/laravel-cors/src/HandleCors.php(52): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #37 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Fruitcake\Cors\HandleCors->handle() #38 /var/www/html/slots/vendor/fideloper/proxy/src/TrustProxies.php(57): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #39 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(167): Fideloper\Proxy\TrustProxies->handle() #40 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(103): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline{closure}() #41 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php(142): Illuminate\Pipeline\Pipeline->then() #42 /var/www/html/slots/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php(111): Illuminate\Foundation\Http\Kernel->sendRequestThroughRouter() #43 /var/www/html/slots/public/index.php(52): Illuminate\Foundation\Http\Kernel->handle() #44 {main}

elihaidv avatar Jul 10 '22 17:07 elihaidv

Check the embedded collection being updated. This happens if there is an object with no _id in the embedded relation

Abbas-bz avatar Sep 12 '22 13:09 Abbas-bz

My object has _id property But I found that when I have another objects in the array with no _id, this exception has thrown. I think we need hear a more clear message

Anyway I updated all my embedded object to be with _id. If someone else has this issue, I posted here the query for generate _id for objects that has not.

db.users.find({"stories": {"$exists": true}}).forEach(function(u) {
            print("Updating user " + u.phone + " with " + u.stories.length + " stories");
            u.stories
            .filter(s=>!s._id)
            .forEach(function(s) {
                print("Updating story " + s.id);
                db.users.updateOne(
                    {"_id": u._id, "stories.id": s.id},
                    {"$set": {"stories.$._id": ObjectId()}}
                );
            });
        })

elihaidv avatar Nov 06 '22 16:11 elihaidv