CVE-2026-49208 Overview
CVE-2026-49208 affects Symfony UX, a JavaScript ecosystem for Symfony applications. The vulnerability resides in the LiveComponentHydrator::hydrateObjectValue() method within the LiveComponent package. When a #[LiveProp] is typed as DateTimeInterface without an explicit format, the hydrator falls back to new $className($value), which accepts client-supplied relative strings such as now, tomorrow, or +10 years.
Attackers can supply these relative date expressions to shift writable, format-less date properties past time-based business logic checks. The flaw is classified as improper input validation [CWE-20]. Affected versions span from 2.8.0 through 2.36.0, and version 3.1.0 also receives the fix.
Critical Impact
Remote unauthenticated attackers can bypass time-based business logic by injecting relative date strings into LiveComponent date properties, potentially manipulating expiration checks, scheduling constraints, or access windows.
Affected Products
- Symfony UX LiveComponent versions 2.8.0 through 2.35.x
- Symfony UX LiveComponent version 3.0.0
- Any Symfony application using #[LiveProp] typed as DateTimeInterface without an explicit format option
Discovery Timeline
- 2026-07-17 - CVE-2026-49208 published to NVD
- 2026-07-21 - Last updated in NVD database
Technical Details for CVE-2026-49208
Vulnerability Analysis
The vulnerability originates in src/LiveComponent/src/LiveComponentHydrator.php. When Symfony UX rehydrates a LiveComponent from client input, it processes each #[LiveProp] property based on its declared type. For properties typed as DateTimeInterface or subclasses like DateTime and DateTimeImmutable, the hydrator branches on whether a format argument was supplied.
Without an explicit format, the code path invokes new $className($value). The PHP DateTime constructor accepts a wide range of natural-language expressions parsed by strtotime. Values like now, tomorrow, yesterday, +10 years, or -1 day become valid dates relative to the server clock. Attackers exploit this to submit values that always satisfy comparisons such as $expiresAt > new DateTime().
The issue is exploitable over the network without authentication or user interaction, because LiveComponent endpoints accept model updates from any client rendering the component.
Root Cause
The root cause is missing strict format validation on deserialized date values. The hydrator trusted the DateTime constructor to reject invalid input, but that constructor is intentionally lenient and interprets relative expressions. No allow-list of acceptable formats was enforced when the developer omitted the format option.
Attack Vector
An attacker crafts a LiveComponent update request that sets a DateTimeInterface-typed prop to a relative string. When the server hydrates the component, the property becomes a fresh date derived from that expression, bypassing checks that assume the client can only supply concrete timestamps.
// Security patch in src/LiveComponent/src/LiveComponentHydrator.php
// Source: https://github.com/symfony/ux/commit/d24d78fda6df2d5964312255943ebf3a217b79a2
throw new BadRequestHttpException(\sprintf('The model path "%s" was sent an invalid data type "%s" for a date.', $propertyPathForError, get_debug_type($value)));
}
- if (null !== $dateFormat) {
- return $className::createFromFormat($dateFormat, $value) ?: throw new BadRequestHttpException(\sprintf('The model path "%s" was sent invalid date data "%s" or in an invalid format. Make sure it\'s a valid date and it matches the expected format "%s".', $propertyPathForError, $value, $dateFormat));
- }
+ $effectiveDateFormat = $dateFormat ?: \DateTimeInterface::RFC3339;
- return new $className($value);
+ return $className::createFromFormat($effectiveDateFormat, $value) ?: throw new BadRequestHttpException(\sprintf('The model path "%s" was sent invalid date data "%s" or in an invalid format. Make sure it\'s a valid date and it matches the expected format "%s".', $propertyPathForError, $value, $effectiveDateFormat));
}
if (is_a($className, AbstractUid::class, true)) {
The patch removes the fallback to new $className($value) and instead defaults to RFC 3339 parsing via createFromFormat(). Any value that fails strict format matching triggers a BadRequestHttpException.
Detection Methods for CVE-2026-49208
Indicators of Compromise
- HTTP requests to LiveComponent endpoints containing relative date strings such as now, today, tomorrow, yesterday, +, or next in the model payload
- Repeated POST requests targeting the same LiveComponent with varying date field values
- Server logs showing successful state transitions on records with time-based constraints without corresponding elapsed time
Detection Strategies
- Inspect access logs for LiveComponent update requests containing non-numeric, non-ISO-8601 values in date fields
- Add application-layer logging around LiveComponentHydrator::hydrateObjectValue() to capture raw input values for date-typed props
- Correlate business logic outcomes (subscription renewals, coupon redemptions, scheduled unlocks) with the request payloads that produced them
Monitoring Recommendations
- Alert when LiveComponent payloads include reserved strtotime keywords in properties bound to date types
- Monitor for unexpected changes to date-sensitive records without matching business events
- Track Symfony UX package versions across deployed applications to identify unpatched instances
How to Mitigate CVE-2026-49208
Immediate Actions Required
- Upgrade Symfony UX LiveComponent to version 2.36.0 or 3.1.0
- Audit every #[LiveProp] typed as DateTimeInterface, DateTime, or DateTimeImmutable and add an explicit format argument
- Review time-based business logic that consumes hydrated date props for evidence of manipulation
Patch Information
The fix is included in Symfony UX 2.36.0 and 3.1.0. Refer to the GitHub Security Advisory GHSA-89g7-22c8-3j23 and the upstream commit d24d78f. Release notes are available at Symfony UX v2.36.0 and Symfony UX v3.1.0.
Workarounds
- Add an explicit format argument to every date #[LiveProp], for example #[LiveProp(format: 'Y-m-d H:i:s')]
- Server-side validate incoming date strings against a strict regular expression before assigning to component state
- Enforce authorization checks that do not rely solely on client-supplied date values
# Update Symfony UX via Composer
composer require symfony/ux-live-component:^2.36.0
# or for the 3.x branch
composer require symfony/ux-live-component:^3.1.0
composer update symfony/ux-live-component
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

