PHP / Magento Dev Blog

  • Publikacje
  • O autorze
  • Kontakt

PHP 8.0 – release and first impressions of the new features

by Henryk Tews / Thursday, 26 November 2020 / Published in PHP

PHP 8.0 was officially released on 26 November 2020. I wrote about the previews in July – now that I have the final version, it is time for first practical impressions. I check what works as promised, what surprised me, and what to watch out for when migrating older projects.

Match expression – I use it immediately

<?php

declare(strict_types=1);

// Old code - switch was silent on an unknown status
function getStatusLabel(int $status): string
{
    switch ($status) {
        case 1: return 'Active';
        case 2: return 'Inactive';
        // forgot case 3 - switch returns null, code continues silently
    }
}

// PHP 8.0 - match throws UnhandledMatchError on unknown status
function getStatusLabel(int $status): string
{
    return match($status) {
        1 => 'Active',
        2 => 'Inactive',
        3 => 'Pending verification',
        default => throw new \InvalidArgumentException("Unknown status: {$status}"),
    };
}

Named Arguments in practice – code readability

<?php

// Who remembers the parameter order of array_slice?
$page = array_slice($items, offset: ($currentPage - 1) * $pageSize, length: $pageSize);

// str_contains, str_starts_with, str_ends_with - new in PHP 8.0
$sku = 'MG-RED-XL-42';

if (str_starts_with($sku, 'MG-')) echo 'Magento product';
if (str_ends_with($sku, '-42'))   echo 'Size 42';
if (str_contains($sku, '-RED-'))  echo 'Colour: red';

// Replaces: strpos($sku, '-RED-') !== false
// Clearly more readable

str_contains, str_starts_with, str_ends_with – underrated additions

<?php

// Old approach - unreadable
if (strpos($url, '/admin') === 0)              { /* ... */ }
if (strpos($email, '@example.com') !== false)  { /* ... */ }
if (substr($filename, -4) === '.php')          { /* ... */ }

// PHP 8.0 - intent is clear immediately
if (str_starts_with($url, '/admin'))           { /* ... */ }
if (str_contains($email, '@example.com'))      { /* ... */ }
if (str_ends_with($filename, '.php'))          { /* ... */ }

Constructor Promotion in Magento 2 – proceed with care

<?php

declare(strict_types=1);

// Safe - DTO/Value Object outside DI
class OrderExportDto
{
    public function __construct(
        public readonly int $orderId,
        public readonly string $status,
        public readonly float $grandTotal,
        public readonly \DateTimeImmutable $createdAt
    ) {}
}

// Caution - class injected by Magento DI
// Keep the old style for safety on older Magento versions
class OrderExportService
{
    private OrderRepositoryInterface $orderRepository;
    private \Psr\Log\LoggerInterface $logger;

    public function __construct(
        OrderRepositoryInterface $orderRepository,
        \Psr\Log\LoggerInterface $logger
    ) {
        $this->orderRepository = $orderRepository;
        $this->logger          = $logger;
    }
}

Nullsafe operator – practical use

<?php

// Real Magento usage - method chains that can return null
$countryId         = $order?->getShippingAddress()?->getCountryId();
$customerGroupCode = $quote?->getCustomer()?->getGroupId();

// Note: nullsafe does not replace exception handling
// getById() throws NoSuchEntityException, it does not return null
try {
    $product = $productRepository->getById(42);
    $price   = $product->getPrice();
} catch (\Magento\Framework\Exception\NoSuchEntityException $e) {
    $price = 0.0;
}

Summary

PHP 8.0 is the best PHP version ever. Match, named arguments, str_contains and the nullsafe operator enter code immediately. Union types and constructor promotion need more thought when integrating with Magento. Migration from PHP 7.4 is painless if the project does not use deprecated functions – run PHP Compatibility Checker before upgrading.

About Henryk Tews

What you can read next

PHP 7.2 – object type hint, sodium instead of mcrypt, deprecations

© 2026 Created by

TOP
Zarządzaj zgodą
Aby zapewnić jak najlepsze wrażenia, korzystamy z technologii, takich jak pliki cookie, do przechowywania i/lub uzyskiwania dostępu do informacji o urządzeniu. Zgoda na te technologie pozwoli nam przetwarzać dane, takie jak zachowanie podczas przeglądania lub unikalne identyfikatory na tej stronie. Brak wyrażenia zgody lub wycofanie zgody może niekorzystnie wpłynąć na niektóre cechy i funkcje.
Funkcjonalne Always active
Przechowywanie lub dostęp do danych technicznych jest ściśle konieczny do uzasadnionego celu umożliwienia korzystania z konkretnej usługi wyraźnie żądanej przez subskrybenta lub użytkownika, lub wyłącznie w celu przeprowadzenia transmisji komunikatu przez sieć łączności elektronicznej.
Preferencje
Przechowywanie lub dostęp techniczny jest niezbędny do uzasadnionego celu przechowywania preferencji, o które nie prosi subskrybent lub użytkownik.
Statystyka
Przechowywanie techniczne lub dostęp, który jest używany wyłącznie do celów statystycznych. Przechowywanie techniczne lub dostęp, który jest używany wyłącznie do anonimowych celów statystycznych. Bez wezwania do sądu, dobrowolnego podporządkowania się dostawcy usług internetowych lub dodatkowych zapisów od strony trzeciej, informacje przechowywane lub pobierane wyłącznie w tym celu zwykle nie mogą być wykorzystywane do identyfikacji użytkownika.
Marketing
Przechowywanie lub dostęp techniczny jest wymagany do tworzenia profili użytkowników w celu wysyłania reklam lub śledzenia użytkownika na stronie internetowej lub na kilku stronach internetowych w podobnych celach marketingowych.
  • Manage options
  • Manage services
  • Manage {vendor_count} vendors
  • Read more about these purposes
Zobacz preferencje
  • {title}
  • {title}
  • {title}