DEV Community

Cover image for 🚀 Introducing Laravel ObjectId — The Fastest MongoDB-Style Identifier for Laravel Models
Hamada Habib
Hamada Habib

Posted on

🚀 Introducing Laravel ObjectId — The Fastest MongoDB-Style Identifier for Laravel Models

Works seamlessly with MySQL, MariaDB, and PostgreSQL — no MongoDB required.

Every Laravel developer has been there — you start a new project, define your migrations, and by default, your models use auto-incrementing IDs. It works fine... until your app grows, you need distributed systems, API integrations, or microservices. Suddenly, those integer IDs start to look like a limitation.

That’s where Laravel ObjectId comes in — a drop-in, ultra-fast, globally unique identifier system inspired by MongoDB’s ObjectIds, designed for MySQL, MariaDB, and PostgreSQL — no MongoDB required.


💡 Why ObjectId?

Unlike UUIDs or ULIDs, ObjectIds are compact 12-byte identifiers that encode timestamp, randomness, and a counter — making them sortable, lightweight, and unique across systems.

In numeric terms, they’re up to 3× faster to generate and smaller in size, which directly improves database performance and indexing.

✅ Works natively with MySQL, MariaDB, and PostgreSQL
🚫 No MongoDB driver or extension required


🧬 How ObjectId Works Internally

ObjectIds are 12-byte (96-bit) identifiers consisting of four key parts:

Segment Size Description
Timestamp 4 bytes UNIX epoch seconds — makes IDs sortable by creation time
Machine Identifier 5 bytes Randomly generated, unique per host
Process ID 2 bytes Uniquely identifies the generating process
Counter 3 bytes Incrementing counter initialized randomly per process

➡️ Total = 4 + 5 + 2 + 3 = 12 bytes = 24 hex characters

This design ensures uniqueness without any central generator and preserves chronological order, making it ideal for distributed systems.

For more details, check:


🧩 The Ecosystem

The Laravel package is built on top of our core PHP library:

Both packages are open-source under the MIT license, created by WooServ Labs.


⚡ Installation

composer require wooserv/laravel-objectid
Enter fullscreen mode Exit fullscreen mode

🧱 Usage

Model Example

use WooServ\LaravelObjectId\Concerns\HasObjectIds;
use Illuminate\Database\Eloquent\Model;

class Post extends Model
{
    use HasObjectIds;
}
Enter fullscreen mode Exit fullscreen mode

Migration Example

Schema::create('posts', function (Blueprint $table) {
    $table->objectId(); // Creates a 24-char string primary key
    $table->string('title');
    $table->timestamps();
});
Enter fullscreen mode Exit fullscreen mode

Generate IDs Anywhere

$id = objectid(); // e.g. 6730b6a0d8a28f890b7c9f40
Enter fullscreen mode Exit fullscreen mode

🔬 Benchmark Results

Laravel ObjectId Performance (10,000 iterations)

----------------------------------------------------------
ObjectId             : 0.412 µs per ID
objectid() helper    : 0.417 µs per ID
UUID                 : 1.283 µs per ID
ULID                 : 1.147 µs per ID
----------------------------------------------------------
Fastest: ObjectId 🚀
Enter fullscreen mode Exit fullscreen mode

Database Insert Benchmark (1,000 inserts)

----------------------------------------------------------
ObjectId   : 14.78 ms total (0.015 ms/insert)
UUID       : 15.48 ms total (0.015 ms/insert)
ULID       : 15.17 ms total (0.015 ms/insert)
----------------------------------------------------------
Enter fullscreen mode Exit fullscreen mode

⚔️ ObjectId vs UUID vs ULID

Feature ObjectId UUID ULID
Length 24 chars 36 chars 26 chars
Bytes 12 16 16
Sortable ✅ (timestamp prefix)
Randomness
Readability 🟢 Compact 🔴 Long 🟢 Fair
Speed 🚀 Fastest 🐢 Slowest ⚡ Medium
Works with MySQL/MariaDB/PostgreSQL
Requires MongoDB

Verdict: ObjectId is the best balance between compactness, performance, and chronological order — and it’s fully compatible with standard SQL databases.


🧠 Why Developers Love It

  • Automatic assignment — no need to manually generate IDs.
  • ⚙️ Migration macro $table->objectId() — clean and intuitive.
  • 🧩 Framework-agnostic core — works outside Laravel too.
  • 📦 Compact storage — saves DB space compared to UUID.
  • 🕒 Sortable by creation time — built-in timestamp encoding.
  • 🧰 Database-compatible — works with MySQL, MariaDB, and PostgreSQL seamlessly.

🌍 Open Source Philosophy

Both packages are released under the MIT License and maintained by WooServ Labs, a collective of developers building open, high-performance PHP tooling for modern web apps.

We believe that open-source should be:

  • Simple to install.
  • Fun to use.
  • Fast by default.

If you share that philosophy — star the repo, contribute, or just spread the word 💫


📎 Resources


⭐ If you like it — give it a Star on GitHub and share it with your fellow Laravel devs!

Top comments (6)

Collapse
 
xwero profile image
david duymelinck

I never understood why people need to sort on id. In Laravel if you want to sort on timestamp use the created and updated columns. In the migrations they made a easy to use function to add them.

I do understand wanting to have an unique id, if you are at the stage that you need to divide tables over multiple instances. But you can do that with more proven technology.

The problem of having identifiable parts, is that it makes it weaker from a security perspective.
That is also why i have seen quite a few posts about the timestamp in UUID v7.

Collapse
 
ihfbib profile image
Hamada Habib

That’s a really good point — and totally valid for most Laravel apps 👏

You’re right: if you only need chronological sorting, created_at does the job.
But ObjectId targets a slightly different layer — index-level ordering and cross-table temporal consistency, especially when IDs are used externally (APIs, queues, logs, caching layers).

When IDs carry a time prefix, databases can keep index inserts sequential, reducing B-Tree fragmentation and write amplification.
It’s not about business sorting, but storage locality & index performance.

Regarding the timestamp visibility — absolutely, it’s a trade-off.
That’s why our upcoming binary mode will keep the timestamp component internal (not human-readable), while maintaining the same ordered properties.

Appreciate you bringing this up — that balance between readability, performance, and security is exactly what we’re exploring 🚀

Collapse
 
xwero profile image
david duymelinck

At what point are relational databases suffering from B-Tree fragmentation?
And isn't the simple fix perodic index rebuilding?

Thread Thread
 
ihfbib profile image
Hamada Habib

That’s a great question — and you’re right, periodic index rebuilds do solve fragmentation in theory.

But in high-write or high-churn systems (think logs, events, order pipelines), fragmentation isn’t the only concern — it’s write amplification and page splits happening continuously.

When inserts aren’t sequential (like with random UUIDs), the B-Tree keeps rebalancing in memory, causing extra disk I/O and cache churn.
Sequential keys (like ObjectId or UUIDv7) keep inserts append-like, which maintains cache locality and improves throughput between rebuilds.

So yes — rebuilds help maintenance, but ordered IDs help avoid the constant micro-fragmentation in the first place.

Thread Thread
 
xwero profile image
david duymelinck

Wouldn't it be better to use a database system that can handle those loads with less effort. I know the Postgres can do everything articles tell you otherwise.
But if you are in that situation changing the id format seems like a quick patch solution.
I'm not saying the format is a bad idea. It could be a solution for a specific case, and I'm glad it exists.

Thread Thread
 
ihfbib profile image
Hamada Habib

You're absolutely right — switching databases is usually the real long-term solution when scaling becomes a bottleneck.

Our goal with PHP & Laravel ObjectId isn’t to “fix” database limitations, but to offer a compact, timestamp-ordered ID format that works seamlessly inside existing systems — especially for teams that can’t migrate off MySQL yet, or need sortable unique keys in distributed setups.

PostgreSQL is definitely a powerhouse (and we benchmarked it too).
The nice part is: ObjectId performs identically across MySQL and Postgres, so developers can keep their stack while gaining predictable ordering and smaller index sizes.

It’s less of a “quick patch,” and more of a “drop-in upgrade” for people already invested in Laravel’s ecosystem.