Skip to content

Add allowedClasses option to UnserializeCast - #1220

Merged
rubenvanassche merged 2 commits into
mainfrom
rubenvanassche/spatie-laraveldata-unserialize-rce
Oct 26, 2026
Merged

rubenvanassche merged 2 commits into
mainfrom
rubenvanassche/spatie-laraveldata-unserialize-rce

Conversation

@rubenvanassche

Copy link
Copy Markdown
Member

Adds an allowedClasses option to UnserializeCast, which is passed to unserialize() to limit which classes can be created. The default stays true, so existing behaviour does not change.

The cast was not documented yet, so this also adds a section to the casts docs explaining how to use it and noting that it should not be used on user input.

@rubenvanassche
rubenvanassche force-pushed the rubenvanassche/spatie-laraveldata-unserialize-rce branch from 79effe4 to 0293c73 Compare October 26, 2026 09:05
@rubenvanassche
rubenvanassche force-pushed the rubenvanassche/spatie-laraveldata-unserialize-rce branch from 0293c73 to ee623ff Compare October 26, 2026 09:08
@rubenvanassche
rubenvanassche merged commit 23d0748 into main Oct 26, 2026
48 checks passed
albertcht pushed a commit to hypervel/data that referenced this pull request Nov 4, 2026
Data objects can now restore values that were stored with serialize(),
such as serialized database columns or cache entries, through
#[WithCast(UnserializeCast::class)]. The cast can fail silently, leaving
the value to the built-in conversion, and allowedClasses limits which
classes unserialize() may create.

Port of spatie/laravel-data#1220 at main a161f325d5.

Hypervel adaptations:

- allowedClasses defaults to false, so no objects are restored unless
  their classes are listed. Spatie allows every class by default, which
  runs __wakeup() and __destruct() for any class named in the value.
  Pass true to allow every class.
- failSilently no longer turns coroutine cancellation into a failed
  cast. The restore hooks of allowed classes can suspend, such as
  SerializesModels querying the database.
- The docs cover the allowed classes, including nested ones, and warn
  against unserializing untrusted data. Their failSilently example lists
  the class it restores.

All upstream UnserializeCast tests are ported, with coverage for the
default, a data object restoring only allowed classes, and cancellation
during a restore hook. The cast tests, analysis and formatting pass.
albertcht pushed a commit to hypervel/docs that referenced this pull request Nov 4, 2026
Data objects can now restore values that were stored with serialize(),
such as serialized database columns or cache entries, through
#[WithCast(UnserializeCast::class)]. The cast can fail silently, leaving
the value to the built-in conversion, and allowedClasses limits which
classes unserialize() may create.

Port of spatie/laravel-data#1220 at main a161f325d5.

Hypervel adaptations:

- allowedClasses defaults to false, so no objects are restored unless
  their classes are listed. Spatie allows every class by default, which
  runs __wakeup() and __destruct() for any class named in the value.
  Pass true to allow every class.
- failSilently no longer turns coroutine cancellation into a failed
  cast. The restore hooks of allowed classes can suspend, such as
  SerializesModels querying the database.
- The docs cover the allowed classes, including nested ones, and warn
  against unserializing untrusted data. Their failSilently example lists
  the class it restores.

All upstream UnserializeCast tests are ported, with coverage for the
default, a data object restoring only allowed classes, and cancellation
during a restore hook. The cast tests, analysis and formatting pass.
@freekmurze
freekmurze deleted the rubenvanassche/spatie-laraveldata-unserialize-rce branch November 5, 2026 10:39
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant