PHP81 Compatibility - sebiboga/testlink-upgraded GitHub Wiki

PHP 8.1+ Compatibility

Issue #140

Modernized TestLink for PHP 8.1+ support with zero breaking changes.

What Changed

1. strftime() Deprecation

Problem: PHP 8.1 deprecated strftime(). Many TestLink functions used this for date formatting.

Solution: Created tlStrftime() wrapper function that:

  • Uses IntlDateFormatter for locale-aware formatting (PHP 8.1+)
  • Falls back to date() conversion
  • Maintains backward compatibility with PHP 7.4+

Usage:

// Old (deprecated)
$date = @strftime("%Y-%m-%d", time());

// New (recommended)
$date = tlStrftime("%Y-%m-%d", time());

2. Count Type Safety

Problem: PHP 8.1 enforces strict typing. count() on non-countable values throws TypeError.

Solution: Created type-safe helpers:

// tlCount() - returns 0 for non-countable
$count = tlCount($items);  // Safe even if $items is null

// tlEnsureCountable() - converts to array
$items = tlEnsureCountable($query_result);
$count = count($items);

3. Variable Syntax

Status: Already fixed. All ${var} replaced with {$var} in strings.

Compatibility Layer

New File: lib/functions/php81_compat.php

Three helper functions:

tlStrftime($format, $timestamp)

  • Modern date formatting
  • Locale-aware (PHP 8.1+)
  • Format strings: %Y, %m, %d, %H, %M, %S, %A, %B, %c, %x, %X

tlCount($value, $mode)

  • Safe count for any type
  • Returns 0 for null/non-countable
  • Supports COUNT_NORMAL and COUNT_RECURSIVE

tlEnsureCountable($value)

  • Converts values to countable
  • Returns empty array if null
  • Safe for subsequent count()

Affected Files

  • date_api.php
  • lang_api.php
  • testcase.class.php
  • print.inc.php
  • logger.class.php
  • resultsMoreBuildsGUI.php
  • tcCreatedPerUserOnTestProject.php
  • reqOverview.php
  • stashrestInterface.class.php
  • jiraCommons.class.php
  • gforgesoapInterface.class.php
  • TestlinkXMLRPCServerTest.php

Testing

Check PHP Version

php -v

Run with Strict Error Reporting

error_reporting(E_ALL);
ini_set('display_errors', '1');

Test Date Formatting

$date = tlStrftime("%Y-%m-%d", time());
echo $date;  // 2026-08-16

Test Safe Counting

$items = null;
$count = tlCount($items);
echo $count;  // 0 (no error)

Compatibility Matrix

PHP Version Status Notes
7.4 LTS ✅ Full Tested
8.0 ✅ Full Tested
8.1 ✅ Full Recommended
8.2 ✅ Full Tested
8.3 ✅ Full Tested

Performance

  • IntlDateFormatter: Minimal overhead, proper locale support
  • Fallback date(): Near-native performance
  • tlCount(): Negligible overhead (type check + count)

Format String Reference

Common strftime format strings supported by tlStrftime():

Code Meaning Example
%Y 4-digit year 2026
%y 2-digit year 26
%m Month (01-12) 08
%d Day (01-31) 16
%H Hour (00-23) 14
%M Minute (00-59) 30
%S Second (00-59) 45
%A Full weekday Saturday
%a Abbreviated day Sat
%B Full month August
%b Abbreviated month Aug
%c Locale date/time Sat Aug 16 14:30:45 2026

Migration Guide

For Developers

When adding new date formatting:

// ✅ DO: Use tlStrftime()
$date = tlStrftime("%Y-%m-%d", $timestamp);

// ❌ DON'T: Use strftime() directly
$date = strftime("%Y-%m-%d", $timestamp);

When working with counts:

// ✅ DO: Use tlCount()
if (tlCount($results) > 0) { ... }

// ❌ DON'T: Call count() on potentially null values
if (count($results) > 0) { ... }  // May throw TypeError

Documentation

See docs/PHP81_COMPATIBILITY.md for detailed technical documentation.

Related Links


Status: ✅ Completed
Issue: #140
Commits: 628457552, 1f85af2c7
Min PHP: 7.4
Recommended: 8.1+