---
title: 'PHP 8.3: Typed Constants, #[Override], json_validate & Upgrade Notes | DevSense'
description: 'Guida a PHP 8.3 da PHP 8.2: #[Override], costanti di classe tipizzate, modifiche alla clonazione readonly, json_validate, str_increment/str_decrement, miglioramenti a range().'
faq:
    - { question: "Cosa fa l'attributo #[Override] in PHP 8.3?", answer: "L'attributo #[Override] contrassegna un metodo che deve sovrascrivere un metodo genitore o una dichiarazione di interfaccia. Se il metodo genitore viene rinominato o rimosso, PHP genererà un Fatal Error a tempo di compilazione." }
    - { question: 'Come funzionano le costanti di classe tipizzate in PHP 8.3?', answer: 'Le costanti di classe, interfaccia, trait ed enum possono ora dichiarare tipi specifici (come string, int, bool, float o array). I valori assegnati devono corrispondere rigorosamente a questo tipo in fase di compilazione.' }
    - { question: 'Qual è il vantaggio di json_validate() in PHP 8.3?', answer: 'json_validate() verifica se una stringa è un JSON valido senza decodificarla, eliminando il notevole sovraccarico di CPU e memoria associato a json_decode() per le sole attività di convalida.' }
    - { question: 'Come cambia la clonazione delle proprietà readonly in PHP 8.3?', answer: "Le proprietà readonly possono ora essere reinizializzate all'interno del metodo `__clone()`, semplificando la clonazione profonda (deep cloning) e la modifica di strutture immutabili." }
published: '2026-05-31'
---
# PHP 8.3: Funzionalità principali

Una versione di affinamento per i team che utilizzano PHP 8.2.x: vincoli più forti (`#[Override]`, costanti tipizzate), migliore ergonomia per JSON e stringhe (`json_validate`, `str_increment`/`str_decrement`), e una serie di piccole modifiche a runtime che si manifestano sotto carico o in percorsi di esecuzione specifici.

## Indice
* [`#[\Override]` — rilevare la mancata sovrascrittura a tempo di compilazione](#override-attribute)
* [Costanti di classe tipizzate](#typed-constants)
* [Readonly: classi anonime e clonazione](#readonly-tweaks)
* [Miglioramenti nell'usabilità del linguaggio](#language-qol)
* [Nuove funzioni da adottare (`json_validate`, `str_*`, DOM, Random)](#new-functions)
* [Modifiche non retrocompatibili (note di migrazione)](#backward-incompatible)
* [Deprecazioni (incremento/decremento di stringhe, `get_class()`, opzioni INI per assert)](#deprecations)
* [Altre modifiche e operazioni (gc_status, stream, evidenze)](#other-changes)
* [Errori comuni](#common-mistakes)
* [Quiz di autovalutazione](#self-test-quiz)

---

PHP 8.3 si concentra sul rafforzamento della sicurezza dei contratti e sull'ottimizzazione dell'uso delle risorse. Introducendo costanti di classe tipizzate e l'attributo `#[\Override]`, PHP rende il refactoring più sicuro e previene derive silenziose delle API. Per gli sviluppatori che gestiscono API ad alto traffico, la nuova funzione `json_validate()` introduce un metodo leggero per convalidare i payload senza allocare memoria per il parsing completo. Tuttavia, questi miglioramenti sono accompagnati da regole di convalida più severe nella libreria standard (in particolare per la funzione `range()` e le funzioni socket) e dalla deprecazione dei vecchi comportamenti di incremento delle stringhe. Ecco come aggiornare le tue applicazioni in modo trasparente.

<a id="override-attribute"></a>
## `#[\Override]` — rilevare la mancata sovrascrittura a tempo di compilazione

Contrassegna i metodi destinati a sovrascrivere un metodo genitore o di un'interfaccia. Se il nome è errato o se il metodo genitore viene rimosso, **PHP genererà un errore immediato** invece di definire silenziosamente un nuovo metodo.

> [!NOTE]
> **Lo sapevi?**
> L'attributo `#[Override]` viene completamente ignorato dall'engine al momento dell'esecuzione! Si tratta esclusivamente di un controllo a tempo di compilazione progettato per rilevare errori di refactoring e discrepanze con le definizioni delle interfacce prima dell'avvio del codice.

```php
// app/Services/Loggers/FileLogger.php
interface Logger
{
    public function log(string $message): void;
}

final class FileLogger implements Logger
{
    #[\Override]
    public function log(string $message): void
    {
        // ...
    }
}
```

Utilizza questo attributo specialmente in codebase di grandi dimensioni dove le attività di refactoring modificano i nomi dei metodi delle interfacce.

---

<a id="typed-constants"></a>
## Costanti di classe tipizzate

Le costanti su **classi, interfacce, trait ed enum** possono ora dichiarare un tipo, allineando la firma delle costanti con il resto del sistema dei tipi.

```php
// app/Config/AppConfig.php
interface Config
{
    public const string APP_NAME = 'MyApp';
}
```

Questo previene bug legati al \"tipo di costante errato\" che in precedenza emergevano solo nei punti di utilizzo del valore.

---

<a id="readonly-tweaks"></a>
## Readonly: classi anonime e clonazione

* **Le classi anonime** possono essere dichiarate come `readonly`.
* **Le proprietà readonly** possono essere **reinizializzate all'interno di `clone`** (nel metodo magico `__clone()`), il che rende la clonazione di strutture immutabili molto più agevole rispetto ai pattern di PHP 8.2.

---

<a id="language-qol"></a>
## Miglioramenti nell'usabilità del linguaggio

* **Accesso dinamico alle costanti di classe**: `SomeClass::{$name}` per valutare i nomi delle costanti a runtime.
* **Gli inizializzatori di variabili statiche** possono usare espressioni arbitrarie (anziché solo costanti).
* **Parola chiave `final` sui metodi dei trait** quando viene importato un metodo di un trait.
* **Le closure generate da metodi magici** possono ricevere **argomenti con nome** al momento dell'invocazione.
* **`php.ini`**: sintassi per valori di fallback/predefiniti per file di configurazione più puliti.

---

<a id="new-functions"></a>
## Nuove funzioni da adottare

### `json_validate()`

Valida una stringa JSON **senza decodificarla** in strutture PHP—ideale per API, code di messaggi e controlli preliminari rapidi prima di effettuare un costoso `json_decode()`.

> [!NOTE]
> **Lo sapevi?**
> La funzione `json_validate()` consuma molta meno memoria rispetto a `json_decode()` poiché non alloca spazio per array o oggetti PHP in memoria! Scansiona semplicemente la sintassi della stringa, rendendosi ideale per convalidare grossi payload prima della lavorazione.

```php
// app/Http/Middleware/JsonValidateMiddleware.php
if (!json_validate($payload)) {
    throw new InvalidArgumentException('JSON non valido');
}
$data = json_decode($payload, true, flags: JSON_THROW_ON_ERROR);
```

### `str_increment()` / `str_decrement()`

Sostituti raccomandati per i vecchi comportamenti degli operatori `++`/`--` sulle stringhe (vedi deprecazioni). Da utilizzare per contatori alfanumerici dove in precedenza si faceva affidamento sugli operatori di incremento.

```php
// app/Services/CounterService.php
$next = str_increment('a9'); // incremento prevedibile senza usare ++ sulla stringa
$prev = str_decrement($next);
```

### DOM, Intl, Random, POSIX, ecc.

PHP 8.3 aggiunge molti metodi **DOM** (es. `insertAdjacentElement`, `getRootNode`, `replaceChildren`), helper di calendario **Intl**, metodi di supporto **Random** su `Randomizer` (`getFloat`, `nextFloat`, …), e funzioni **POSIX** `sysconf`/`pathconf`/`eaccess`—utili per script di sistema e tool da riga di comando.

---

<a id="backward-incompatible"></a>
## Modifiche non retrocompatibili (note di migrazione)

### Stack / timer / fiber

* **Ricorsione profonda**: chiamate ricorsive vicine al limite dello stack possono lanciare un `Error` al superamento del parametro `zend.max_allowed_stack_size` ; le fiber utilizzano il parametro `fiber.stack_size` nello stesso modo.
* **Zend Max Execution Timers**: abilitati per impostazione predefinita per le build ZTS su Linux—attenzione ai processi worker CLI a lunga esecuzione.

### Processi

* **`proc_get_status()`** su sistemi POSIX restituisce i valori corretti anche in caso di chiamate **ripetute**; i risultati possono essere **memorizzati in cache** (verifica la chiave `"cached"`). Richiamare **`proc_close()`** dopo `proc_get_status()` restituisce ora il codice di uscita effettivo (non più `-1`).

### Array e trait

* **Visibilità delle costanti di classe**: la covarianza viene ora applicata quando le costanti vengono ereditate da **interfacce**—i codici che facevano affidamento su una visibilità più flessibile potrebbero necessitare di correzioni.
* **Array vuoto + primo indice negativo**: la chiave implicita successiva seguirà la regola `n+1` (non riparte da `0`).
* **Trait con proprietà statiche**: le proprietà statiche ereditate dal padre vengono **ridefinite** per ogni classe che utilizza il trait (spazi di memoria separati)—questo può influenzare comportamenti basati sullo stato statico.

### Libreria standard (alto impatto)

* **`range()`**: convalida più severa (`TypeError`/`ValueError` per input non validi), maggiori avvisi in caso di intervalli incoerenti e comportamenti differenti per intervalli di caratteri qualora i limiti sembrino numerici—**riesegui i test** su tutti i codici che generano intervalli a partire da input degli utenti.
* **`number_format()`**: l'uso di un valore negativo per `$decimals` esegue ora l'arrotondamento **prima** del punto decimale (in precedenza veniva ignorato).
* **`file()`**: le combinazioni di flag non valide vengono ora rifiutate (es. `FILE_APPEND` veniva accettato silenziosamente in precedenza).

### Date / DOM / FFI / Opcache

* **Date**: sono state introdotte le gerarchie **`DateError`/`DateException`** al posto di warning o eccezioni generiche—aggiorna i tuoi blocchi `catch`.
* **DOM**: comportamento conforme alle specifiche per i nodi orfani; correzioni a `createAttributeNS()`; nuovi metodi o proprietà possono entrare in **conflitto** con le classi derivate create dall'utente—verifica la compatibilità delle firme.
* **FFI**: le funzioni C dichiarate come `void` restituiscono ora **`null`**, non più un oggetto fittizio di tipo `FFI\CData:void`.
* **Opcache**: l'opzione `opcache.consistency_checks` è stata **rimossa** (risultava non funzionante in combinazione con il JIT JIT tracing ed il cache dell'ereditarietà).

### WeakMap

* **Chiavi con riferimenti circolari** all'interno di una `WeakMap` possono essere rimosse dal Garbage Collector nei cicli in cui la raggiungibilità è limitata alla sola iterazione della mappa—verifica i pattern di caching complessi.

---

<a id="deprecations"></a>
## Deprecazioni (incremento/decremento stringhe, `get_class()`, assert INI)

### Operatori `++` / `--` su stringhe

L'incremento/decremento su stringhe **vuote o non numeriche** è deprecato; l'**incremento non numerico** è considerato formalmente deprecato. Preferisci le funzioni **`str_increment()`** / **`str_decrement()`** per il nuovo codice.

### `get_class()` / `get_parent_class()` senza argomenti

L'invocazione di queste funzioni **senza argomenti** è deprecata—passa esplicitamente un oggetto o il nome della classe.

### Assert

* **`assert_options()`** e le relative **costanti** sono deprecate.
* Le impostazioni **INI `assert.*`** sono deprecate—migra ai parametri indicati nelle note di migrazione di PHP 8.3 sotto la voce \"INI handling\".

---

<a id="other-changes"></a>
## Altre modifiche e operazioni

* **`gc_status()`** fornisce informazioni temporali più dettagliate (tempo di raccolta/distruttore/liberazione)—utile per l'ottimizzazione di processi ad alto consumo di memoria.
* **Stream**: la funzione `fread()` sui socket può ritornare prima se sono presenti dati memorizzati nel buffer.
* **`open_basedir`**: a runtime, la chiamata `ini_set` rifiuta i percorsi contenenti `..` anche se preceduti da `./`.

---

<a id="common-mistakes"></a>
## ⚠️ Errori comuni

Ecco alcuni degli errori tipici riscontrati nell'uso delle novità di PHP 8.3:

### 1. Utilizzo dell'operatore di incremento (++) sulle stringhe
In PHP 8.3, l'uso degli operatori `++` o `--` su stringhe non numeriche genera un avviso di deprecazione.

```php
// app/Services/Counter.php
// ERRATO: genera un avviso di deprecazione in PHP 8.3
$code = 'a9';
$code++; 

// CORRETTO: usa la nuova funzione helper str_increment
$code = str_increment('a9'); // 'b0'
```

### 2. Incompatibilità delle costanti tipizzate nelle sottoclassi
Se una classe genitore definisce una costante tipizzata, le classi figlie che sovrascrivono tale costante devono dichiarare esattamente lo stesso tipo.

```php
// app/Config/DatabaseConfig.php
class ParentConfig {
    public const string DRIVER = 'mysql';
}

// ERRATO: Fatal Error: ChildConfig::DRIVER type (int) is not compatible with ParentConfig::DRIVER type (string)
class ChildConfig extends ParentConfig {
    public const int DRIVER = 123; 
}
```

### 3. Richiamo di `get_class()` senza argomenti
Richiamare la funzione `get_class()` senza passare alcun argomento per ottenere il nome della classe corrente è deprecato in PHP 8.3.

```php
// app/Services/LogService.php
// ERRATO: genera un avviso di deprecazione in PHP 8.3
class LogService {
    public function log(): void {
        echo "Logging from " . get_class(); 
    }
}

// CORRETTO: usa self::class o passa $this esplicitamente
class LogService {
    public function log(): void {
        echo "Logging from " . self::class; 
        // OPPURE: echo "Logging from " . get_class($this);
    }
}
```

---

<a id="self-test-quiz"></a>
## Quiz di autovalutazione

Metti alla prova la tua comprensione delle novità di PHP 8.3.

### Domanda 1: Cosa succede se in PHP 8.3 definisci una costante di classe con un tipo e le assegni un valore di tipo differente (es. `public const int NAME = 'MyApp';`)?
* A) Viene generato un avviso di deprecazione, ma il codice viene eseguito con successo.
* B) PHP converte automaticamente la stringa nel valore intero `0`.
* C) Viene lanciato un `Fatal Error` in fase di compilazione.

<details>
<summary>Clicca per vedere la risposta</summary>

**Risposta: C**  
In PHP 8.3, le costanti di classe tipizzate vengono sottoposte a controlli rigorosi a tempo di compilazione. L'assegnazione di un valore incompatibile a una costante tipizzata produce un Fatal Error.
</details>

### Domanda 2: Perché dovresti utilizzare `json_validate()` al posto di `json_decode()` se desideri esclusivamente verificare che una stringa contenga un JSON valido?
* A) `json_validate()` è più veloce e consuma molta meno memoria perché non costruisce le strutture di array o oggetti PHP.
* B) `json_validate()` supporta formati JSON che `json_decode()` non è in grado di analizzare.
* C) `json_decode()` verrà deprecato nelle future versioni di PHP.

<details>
<summary>Clicca per vedere la risposta</summary>

**Risposta: A**  
La funzione `json_validate()` analizza esclusivamente la sintassi della stringa JSON senza allocare spazio in memoria per le strutture decodificate, offrendo prestazioni nettamente migliori per le semplici attività di convalida.
</details>

---

## Riassunto

PHP 8.3 punta a rafforzare la sicurezza dei contratti di codice e a ottimizzare il consumo delle risorse. Grazie all'introduzione delle costanti di classe tipizzate e dell'attributo `#[Override]`, l'attività di refactoring diventa più sicura e si prevengono disallineamenti silenti delle API.