Una RFC de PHP de Larry Garfield e Ilija Tovilo propone el operador is para pattern matching. Expresiones como $value is int o una respuesta comparada con un rango de status devuelven un booleano, mientras patrones más ricos describen estructura y extraen valores.
El atractivo está en la lectura de datos complejos. El PHP actual suele combinar instanceof, isset, verificaciones de tipo, condiciones anidadas y asignaciones manuales. Pattern matching permite declarar la forma aceptada cerca de la rama que la usa. Rust, Python, C#, Scala y Swift ofrecen ideas relacionadas, aunque la semántica exacta varía.
La propuesta pertenece a una exploración más amplia de algebraic data types, tagged unions, value types y destructuring. Tiene implementación y semántica detallada, pero seguía en discusión y no en votación en la fecha del artículo. Ese estado separa una señal de diseño útil de una función que el equipo puede planificar.
Describir la forma en el punto del branch
La ganancia operativa aparece cuando la forma aceptada queda al lado de la rama que la usa. Hoy un endpoint que recibe un array mezclado con un DTO hace instanceof, isset, is_int, array_key_exists y asignaciones manuales. El lector reconstruye el contrato después de ocho líneas. El autor también, seis meses después.
Con $payload is ['user' => $user & AuthenticatedUser(role: 'admin'), ...], el contrato cabe en una expresión. El binding solo ocurre si el patrón entero casa. Una variable preexistente se queda si falla. Eso reduce una clase de bug en la que el código extrae $id y solo después descubre que el resto era inválido.
Los object patterns leen propiedades accesibles en el alcance. Un hook get dispara. Una propiedad no inicializada genera error. __get entra en la comparación. Eso importa para código con hooks y para objetos incompletos de ORM. Un patrón Point(x: 3, y: $y) no es un isset silencioso.
Los patrones de array asociativo ignoran el orden de las claves y tratan una clave ausente sin warning de undefined, a diferencia de $foo['c'] === 3. Los patrones posicionales, en la implementación en discusión, se acercan a claves numéricas secuenciales; los autores todavía piden opinión sobre si deben llamar array_is_list() internamente, lo que tiene costo. Quien hoy compara arrays con === y depende del orden necesita saber que el operador no es un sinónimo.
mixed funciona como comodín: la clave o la propiedad tiene que existir, el valor puede ser cualquiera. Útil para "este campo llegó, todavía no decido el tipo". Literales, constantes de clase, uniones | e intersecciones & (en DNF, como en los tipos) entran en el mismo sistema. Dos patrones con binding no pueden unirse con OR, porque la variable quedaría indefinida según el brazo.
match() y los puntos todavía abiertos
La RFC esboza dos grafías para match(): match ($var) is { ... } aplicando patrón en todos los brazos, o is en cada arm para mezclar igualdad y patrón. Los autores están divididos. Ruby mezcla menos; la mayoría de los lenguajes relevados es siempre-patrón. Ese detalle cambia la guía de estilo del equipo, así que no conviene copiar snippets de blog como si fueran la gramática final.
Hay implementación (PR 20574 en php-src) y semántica larga. Estado en la wiki: en discusión, no en votación. La versión nombrada en el texto es PHP 8.6. Planear "cuando salga 8.6, reescribimos los controllers" trata una discusión como un release. 8.6 ya carga otras RFC. Esta puede atrasarse, encogerse o cambiar el match.
El is nuevo choca con una constante global o una función no instancia llamada is (case insensitive: IS, Is). Un inventario de function is( y define('IS' vale más, hoy, que un spike de sintaxis. Es el único BC break anunciado además de la keyword nueva.
Ranges compactos, regex, captura del resto del array después de ... y un marcador de clave opcional están en future scope. ADT y enums con valores asociados son el horizonte declarado, con una posición reservada en la sintaxis de objeto. Ninguno de esos ítems debe entrar en la misma tarjeta de Jira que "estudiar el operador".
Experimento local, fuera del roadmap de versión
El lugar correcto para probar es un módulo aislado: validación de respuesta HTTP, parsing de un array de config, tests de shape en fixtures. PHPUnit en la versión actual sigue siendo el contrato de la tubería. Un fork del engine o un polyfill mental no entra en producción.
Yo usaría la RFC como vocabulario de review. "Acá el shape cabe en un patrón" es un comentario útil incluso sin la sintaxis. Empuja el código de hoy hacia early return y extracción explícita. Cuando (y si) el operador exista, la traducción queda mecánica. Reescribir helpers de type check "para quedar listos" gasta un sprint en una gramática que todavía puede cambiar el match.
Criterio para parar el experimento: si el módulo aislado no queda más legible con la forma de la RFC, el equipo no tiene un caso de uso, tiene curiosidad. La curiosidad cabe en un brown bag. No cabe en un piso de versión.
También me niego a atar tagged unions, value types y destructuring en la misma inversión. La RFC dice que matching es un peldaño. Cada peldaño tendrá votación propia. Un architecture decision record puede registrar "seguimos rfc/pattern-matching; no pineamos versión". Eso es una decisión. Reservar 8.7 en el roadmap porque un post citó 2028 es otra cosa.
Lo que la propuesta no cubre en el código de negocio
La validación que consulta la base, una política de autorización, i18n o una regla que no se expresa como patrón sigue afuera. El operador no sustituye una schema library ni un form request. Comprime chequeos de forma que el programa ya hace con instanceof y array_key_exists.
El código que ya usa is como nombre necesita un rename antes de cualquier adopción. El código que dependía del warning de clave ausente para "detectar" un payload malformado pasa a silencio en el patrón asociativo; la ausencia se vuelve false del is, no un notice. Eso es ventaja en la mayoría de los controllers y es diferencia en scripts que trataron el notice como señal.
Mientras la discusión no se vuelva voto, la decisión del equipo es negativa y barata: no reservar sprint, no pinar una versión futura, no prometer ADT en el Q3. Leer la RFC todavía vale. Describe, con precisión, el tipo de dato que el PHP de producción ya intenta validar a mano. Ese mapa sirve hoy, en la revisión de un if encadenado, aunque el operador demore.
Si tu empresa está evaluando algo parecido, escríbeme por LinkedIn o por WhatsApp.