PHP 7.2 è stato rilasciato ufficialmente. La release porta con sé nuove funzionalità, funzioni e miglioramenti che ci permetteranno di scrivere codice migliore. In questo post presento alcune delle funzionalità più interessanti apportate al linguaggio da PHP 7.2.

Aggiornamento: PHP 8.0 è ora disponibile per tutti i clienti Kinsta.

É possibile vedere l’elenco completo delle modifiche nella pagina Request For Comment.

Miglioramenti del Core

Dichiarazioni dei tipi degli argomenti

A partire da PHP 5 è stato consentito di specificare nella dichiarazione di una funzione il tipo di argomento che che ci si aspetta venga passato. Se il valore dato è di un tipo non corretto, allore PHP genera un errore.

Le dichiarazioni dei tipi degli argomenti (altrimenti note come type hints) specifica il tipo di una variabile che ci si aspetta venga passata ad una funzione o al metodo di una classe.

Ecco un esempio:

class MyClass {
	public $var = 'Hello World';
}

$myclass = new MyClass;

function test(MyClass $myclass){
	return $myclass->var;
}

echo test($myclass);

In questo codice, la funzione test aspetta una instanceof MyClass. Un data type incorretto genererebbe il seguente fatal error:

Fatal error: Uncaught TypeError: Argument 1 passed to test() must be an instance of MyClass, string given, called in /app/index.php on line 12 and defined in /app/index.php:8

A partire da PHP 7.2 i type hints possono essere utilizzati con il data type object, ed è questo un miglioramento che permette di dichiarare un oggetto generico come argomento di una funzione o di un metodo. Eccone un esempio:

class MyClass {
	public $var = '';
}

class FirstChild extends MyClass {
	public $var = 'My name is Jim';
}
class SecondChild extends MyClass {
	public $var = 'My name is John';
}

$firstchild = new FirstChild;
$secondchild = new SecondChild;

function test(object $arg) {
	return $arg->var;
}

echo test($firstchild);

echo test($secondchild);

In questo esempio, abbiamo invocato la funzione test due volte, passando un oggetto diverso ad ogni chiamata. Questo non era possibile nelle precedenti versioni di PHP.

Docker
Testing dei type hints con PHP 7.0 e PHP 7.2 in Docker

Dichiarazioni dei Tipi di Ritorno degli Oggetti

Se le dichiarazioni dei tipi di argomenti specificano il tipo atteso degli argomenti di una funzione, le dichiarazioni del tipo di ritorno specificano il tipo che si attende di ricevere per il valore restituito.

Le dichiarazioni dei tipi di ritorno specificano il tipo di una variabile che ci si attende di ricevere da una funzione.

A partire da PHP 7.2 è consentito utilizzare dichiarazioni del tipo di ritorno per il data type object. Ecco un esempio:

class MyClass {
	public $var = 'Hello World';
}

$myclass = new MyClass;

function test(MyClass $arg) : object {
	return $arg;
}

echo test($myclass)->var;

Le precedenti versioni di PHP generano il seguente messaggio di errore:

Fatal error: Uncaught TypeError: Return value of test() must be an instance of object, instance of MyClass returned in /app/index.php:10

Naturalmente, in PHP 7.2 questo codice genera la stringa ‘Hello World’.

Ampliamento dei Tipi di Parametri

Al momento PHP non consente alcuna varianza di parametri tra classi figlio e le loro classi genitori o interfacce. Cosa significa?
Cansideriamo il seguente codice:

<?php
class MyClass {
	public function myFunction(array $myarray) { /* ... */ }
}

class MyChildClass extends MyClass {
	public function myFunction($myarray) { /* ... */ }
}

Abbiamo omesso il tipo di parametro nella sottoclasse. In PHP 7.0 questo codice genera la seguente notifica:

Warning: Declaration of MyChildClass::myFunction($myarray) should be compatible with MyClass::myFunction(array $myarray) in %s on line 8

A partire da PHP 7.2, è consentito omettere il tipo in una sottoclasse senza generare errori. Questa proposta ci permetterà di fare l’upgrade delle classi e utilizzare il suggerimento dei tipi (type hint) nelle librerie senza dover aggiornare tutte le sottoclassi.

Virgole Finali nella Sintassi delle Liste

Una virgola finale dopo l’ultimo elemento di un array costituisce sistassi valida in PHP, e qualche volta è consigliato al fine di aggiungere facilmente nuovi elementi ed evitare errori di parsing dovuti ad una virgola mancante. A partire da PHP 7.2, è consentito utilizzare virgole finali nei gruppi di namespace.

Si legga Trailing Commas In List Syntax per un’analisi più approfondita di questa RFC e di alcuni esempi di codice.

Miglioramenti nella Sicurezza

Argon2 nell’hashing delle password

Argon2 è un potente algoritmo di hashing selezionato come vincitore della Password Hashing Competition del 2015, e PHP 7.2 ce lo mette a disposizione come alternativa sicura all’algoritmo Bcrypt.
La nuova versione di PHP introduce la costante PASSWORD_ARGON2I, che ora può essere utilizzata nelle funzioni password_*:

password_hash('password', PASSWORD_ARGON2I);

Diversamente da Bcrypt, che accetta solo un fattore di costo, Argon2 accetta tre fattori di costo, suddivisi come segue:

  • Un memory cost, che definisce il numero di KiB che dovrebbe essere consumato durante il processo di hashing (i valori predefiniti sono 1<<10, o 1024 KiB, o 1 MiB)
  • Un time cost, che definisce il numero di iterazioni compiute dall’algoritmo di hashing (il valore predefinito è 2)
  • Un parallelism factor, che stabilisce il numero dei thread paralleli che saranno utilizzati durante l’hashing (il valore predefinito è 2)

Tre nuove costanti definiscono i valori di costro predefiniti:

  • PASSWORD_ARGON2_DEFAULT_MEMORY_COST
  • PASSWORD_ARGON2_DEFAULT_TIME_COST
  • PASSWORD_ARGON2_DEFAULT_THREADS

Ecco un esempio:

$options = ['memory_cost' => 1< 4, 'threads' => 2];
password_hash('password', PASSWORD_ARGON2I, $options);

Si legga Argon2 Password Hash per maggiori informazioni.

Libsodium entra a far parte del core di PHP

A partire dalla versione 7.2, PHP include la libreria Sodium all’interno del core. Libsodium è una libreria multipiattaforma e multilingua per crittografia, decrittografia, firme, hashing delle password e altro ancora.
La libreria era in precedenza disponibile tramite PECL.
Per un elenco documentato delle funzioni di Libsodium, si faccia riferimento alla Quick Start Guide. Si veda anche PHP 7.2: The First Programming Language to Add Modern Cryptography to its Standard Library.

Deprecazioni

Quella che segue è una lista delle funzioni e delle funzionalità deprecate a partire da PHP 7.2, le quali saranno rimosse entro il rilascio di PHP 8.0:

La funzione __autoload è stata sostituita da spl_autoload_register in PHP 5.1. Ora un avvido di deprecazione sarà generato quando ne viene rilevata la presenza durante la compilazione.

La variabile $php_errormsg viene generata nel local scope quando viene emesso un errore non-fatale. A partire da PHP 7.2 dovrebbero essere utilizzate al suo posto error_get_last e error_clear_last.

create_function() permette la creazione di una funzione con un dato nome funzione, una lista di argomenti e un codice da eseguire passati come argomenti. Per problemi di sicurezza e cattive performance, questa funzione viene ora deprecata e viene suggerito al suo posto il ricorso alle enclosure.

L’impostazione ini mbstring.func_overload impostata ad un valore diverso da 0 viene deprecata.

(unset) cast è un’espressione che restituisce sempre null, ed è considerata inutile.

parse_str() converte una query string in un array se è presente il secondo argomento, oppure nella tabella dei simboli locale se non è presente. Dato che l’impostazione dinamica delle variabili nell’ambito delle funzioni è scoraggiata per ragioni di sicurezza, l’utilizzo di parse_str() senza il secondo argomento genererà un avviso di deprecazione.

gmp_random() è considerata essere dipendente dalla piattaforma e sarà deprecata. Al suo posto si utilizzeranno gmp_random_bits() and gmp_random_rage().

each() è utilizzata per iterare attraverso un array in modo simile a foreach(), ma foreach() è preferibile per diverse ragioni, compreso il fatto di essere 10 volte più veloce. Ora sarà generato un messaggio di deprecazione alla prima chiamata di un loop.

La funzione assert() verifica una data asserzione e adotta azioni appropriate se il risutato è FALSE. L’utilizzo di assert() con un argomento stringa è ora deprecato dato che apre una vulnerabilità RCE. L’opzione ini zend.assertion può essere utilizzata per prevenire valutazioni di espressioni di asserzione.

$errcontext è un array contenente le variabili locali esistenti nel momento in cui viene generato un errore. É passato come ultimo argomento agli handler di errore impostati con la funzione set_error_handler().

Cosa Significa PHP 7.2 per gli Utenti di WordPress?

Secondo quanto affermato nella pagina ufficiale delle statistiche di WordPress, nel momento in cui scriviamo solo il 19,8% degli utenti di WordPress è passato a PHP 7. E solo il 5% sta utilizzando PHP 7.1. É chiaro che una gran parte degli utenti, circa il 40%, sta utilizzando PHP 5.6. Quello che è ancora più preoccupante è che oltre il 39% degli utenti stanno utilizzando versioni non più supportate di PHP. A partire da dicembre 2016, WordPress.org emesso la raccomandazione ufficiale da PHP 5.6 a PHP 7 o superiore.

Versioni PHP
Statistiche WordPress PHP 7.1

I numeri indicati qui sopra sono particolarmente scoraggianti dal punto di vista delle performance, dato che PHP 7 ha mostrato di essere significativamente più veloce. Qui ci sono alcuni dati statistici:

  • I benchmark ufficiali di PHP mostrano che PHP 7 permette al sistema di eseguire il doppio delle richieste al secondo rispetto a PHP 5.6, a circa la metà della latenza.
  • Christian Vigh ha pubblicato anche un confronto delle performance di PHP nel quale ha scoperto che PHP 5.2 è più lento di PHP 7 del 400%.

Anche noi nel 2018 abbiamo eseguito i nostri benchmark delle prestazioni riportati in PHP 5.6 vs PHP 7 vs HHVM. E in modo simile ai benchmark di cui sopra, abbiamo visto che PHP 7.2 è in grado di eseguire quasi il triplo delle transazioni (richieste) al secondo rispetto a PHP 5.6.

Benchmark WordPress PHP
Benchmark WordPress
  • Risultati benchmark WordPress 4.9.4 PHP 5.6: 49.18 req/sec
  • Risultati benchmark WordPress 4.9.4 PHP 7.0: 133.55 req/sec
  • Risultati benchmark WordPress 4.9.4 PHP 7.1: 134.24 req/sec
  • Risultati benchmark WordPress 4.9.4 PHP 7.2: 148.80 req/sec ?
  • Risultati benchmark WordPress 4.9.4 HHVM: 144.76 req/sec

Molti sono lenti ad aggiornare a causa del tempo necessario a testare tutti i rispettivi temi e plugin di terze parti, per accertarsi che funzionino correttamente. Ma molte volte si tratta semplicemente del fatto che non lo hanno ancora fatto. Non sei sicuro di quale versione di PHP stai utilizzando? Uno dei modi più semplici è utilizzare uno strumento come Pingdom o Google Chrome Devtools. Il primo header di richiesta HTTP mostra normalmente la versione utilizzata.

Controllo Versione PHP
Controllo Versione PHP

Ciò dipende dal fatto che l’host non modifica il valore dell’intestazione X-Powered-By. Se dovessero farlo fanno, potresti non vedere la tua versione di PHP, nel qual caso dovreste caricare un file via FTP. Oppure puoi sempre contattare l’host e chiedere.

Aggiornare a PHP 7.2

PHP 7.2 non è ancora uscito, ma una volta che lo sarà, sarà anche possibile iniziare a effettuare i nostri test. Potreste testare il vostro sito WordPress localmente o controllare i vostri script in un ambiente come Docker, che permette di testare diverse versioni di PHP dalla riga di comando.

Oppure si può utilizzare un ambiente di staging, poiché questo sarà più simile a un sito in ambiente di produzione. Il 4 dicembre Kinsta ha reso disponibile PHP 7.2 per tutti i clienti. È possibile creare facilmente un ambiente di staging con un solo clic.

Ambiente di staging WordPress
Testare PHP 7.2 in ambiente di staging

Basta un solo clic per cambiare il motore PHP per il sito in staging dal menu “Strumenti” e iniziare i test per essere sicuri della compatibilità di plugin e temi di terze parti. Dopo aver verificato che tutto funziona correttamente, è possibile modificare il sito in produzione a PHP 7.2 o passare il sito da staging in produzione.

Passa a PHP 7.2
Passa a PHP 7.2

Conclusioni

Siete pronti a passare a PHP 7.2? Speriamo che ormai abbiate almeno fatto il passaggio a PHP 7. Se non l’avete ancora fatto, questo è il momento giusto per iniziare i test. Quindi, aggiornate i vostri script, controllate il vostro codice e fateci avere le vostre prime impressioni su PHP 7.2.

Lettura consigliata: PHP È Morto?

Carlo Daniele Kinsta

Carlo è cultore appassionato di webdesign e front-end development. Gioca con WordPress da oltre 20 anni, anche in collaborazione con università ed enti educativi italiani ed europei. Su WordPress ha scritto centinaia di articoli e guide, pubblicati sia in siti web italiani e internazionali, che su riviste a stampa. Lo trovate su LinkedIn.