$ lexprog.com

// notes from an old coder -- php, databases, and the occasional rant

[March 11, 2026] MongoDB

MongoDB Laravel Package Deep Dive

MongoDB Laravel Package: Tips & Tricks

────────────────────────────────────────────────────────

MongoDB Laravel Package: Tips & Tricks

Tip: Hybrid Queries

// Standard Eloquent syntax
Post::where('published', true)->where('tags', 'php')->get();

The package translates this to MongoDB queries.

Gotcha: EmbedsMany vs HasMany

// Embedded (stored in the same document)
public function comments(): EmbedsMany
{
    return $this->embedsMany(Comment::class);
}

// Referenced (separate collection)
public function comments(): HasMany
{
    return $this->hasMany(Comment::class);
}

Choose based on your access patterns.

Tip: Raw Queries for Advanced Features

Post::raw(function ($collection) {
    return $collection->aggregate([
        ['$match' => ['published' => true]],
        ['$group' => ['_id' => '$category', 'count' => ['$sum' => 1]]],
    ]);
});

Access the full MongoDB API when Eloquent isn't enough.

Gotcha: ObjectId Handling

use MongoDB\BSON\ObjectId;

Post::raw(fn($c) => $c->findOne(['_id' => new ObjectId($id)]));

Raw queries need ObjectId, not string IDs.

Tip: Query Builder Operators

Post::where('views', 'gt', 100)->get();
Post::where('tags', 'all', ['php', 'laravel'])->get();
Post::whereIn('status', ['published', 'draft'])->get();

Gotcha: Eager Loading Works Differently

Post::with('author')->get();

Under the hood, this does two separate queries and matches in PHP, not a JOIN.

Tip: Schema Builder for Validation

Schema::connection('mongodb')->create('posts', function ($collection) {
    $collection->string('title');
    $collection->string('slug');
});

Creates a collection with schema validation.

Gotcha: Pagination

Post::paginate(10);

Works, but MongoDB pagination is less efficient than SQL for large offsets.

Tip: Embed or Reference? The 80/20 Rule

If you always access data together, embed it. If you access it independently, reference it. The 16MB document size limit is the hard boundary — stay under 1MB for most documents.

Tip: Index Your Query Patterns, Not All Fields

Creating indexes on every field wastes RAM. Use explain() to find in-memory sorts and collection scans. Index only what your actual queries filter on.

Gotcha: No Transaction Rollback for Index Builds

Building an index on a large collection can take hours. If it fails midway, the partial index is silently discarded. Plan index builds during maintenance windows.

Senior Insight

MongoDB performance tuning is predominantly about ensuring the working set fits in RAM. Unlike PostgreSQL, which can use indexes effectively even when data exceeds RAM, MongoDB performance degrades sharply when the working set exceeds available memory. I calculate the working set size by monitoring page_faults in MongoDB metrics. An increasing page fault rate means the working set is growing beyond RAM, and it's time to either add memory, optimize indexes, or shard.

Source: MongoDB Developer Center (https://www.mongodb.com/developer/), MongoDB Engineering Blog (https://www.mongodb.com/blog/channel/engineering-blog), Studio 3T Blog (https://studio3t.com/blog/)

────────────────────────────────────────────────────────
<-- back to posts