Skip to content

Support refinement for the mb_convert_encoding function for PHP 8+ #13064

@stof

Description

@stof

Feature request

The mb_convert_encoding function has a return type of array|string|false. phpstan should be able to refine the type:

  • removing either array or string from the return type is based on the type of $string (this seems to be done already)
  • on PHP 8+, returning false is only possible in one specific case: when $from_encoding triggers encoding detection to guess it and it fails (this also triggers a warning)
  • on PHP 7.x, false was also returned when passing unsupported encodings (on 8.x, it throws a ValueError instead), which would make refinement harder (unless the supported encodings can be known)

From what I can see from the code, it also seems to remove failed conversions from the array when guessing fails on an array $input instead of returning false for the whole result. So an array input might maybe skip false entirely (but invalid any non-empty-array flag)

$from_encoding supports the following values:

  • null: uses the mbstring.internal_encoding encoding, so no guessing is happening
  • string[]: triggers encoding guessing when the array contains multiple items
  • string containing a comma-separated list of values: parse the comma-separated list and triggers guessing
  • string not containing a comma: no guessing is happening

When passing a constant string as $from_encoding, it would be great to toggle the usage of the false return type based on the absence of comma. This would remove false from the return type when writing code like mb_convert_encoding('🔥 Все буде добре 🔥', 'EUC-JP', 'UTF-8')
Bonus point: add an accessory type for the string value returned by mb_detect_encoding (which returns either false or a string representing a single encoding), so that this refinement also works for such code pattern:

$charset = mb_detect_encoding($string, $charsetList);

if ($charset !== 'UTF-8' && $charset !== false) {
      $header = mb_convert_encoding($string, 'UTF-8', $charset);
}

Did PHPStan help you today? Did it make you happy in any way?

No response

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions