Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .gitattributes
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ examples export-ignore
tests export-ignore
.gitattributes export-ignore
.gitignore export-ignore
.php_cs.dist export-ignore
.php-cs-fixer.dist.php export-ignore
dockerfile.sh export-ignore
phpunit.xml.dist export-ignore
psalm.xml export-ignore
13 changes: 3 additions & 10 deletions .github/workflows/qa.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,24 +11,17 @@ jobs:
matrix:
operating-system: [ubuntu-latest]
env:
- PHP_IMAGE: php:7.3-cli

- PHP_IMAGE: php:7.4-cli
COVERAGE_FILE: coverage.clover

- PHP_IMAGE: php:8.0-cli
QA: 1

- PHP_IMAGE: php:8.1-cli
- PHP_IMAGE: php:8.2-cli
COVERAGE_FILE: coverage.clover
- PHP_IMAGE: php:8.3-cli
QA: 1
- PHP_IMAGE: php:8.4-cli
- PHP_IMAGE: php:8.5-cli

runs-on: ${{ matrix.operating-system }}
steps:
- name: Checkout
uses: actions/checkout@v2
uses: actions/checkout@v6

- name: Build docker image
env: ${{ matrix.env }}
Expand Down
43 changes: 33 additions & 10 deletions .php_cs.dist → .php-cs-fixer.dist.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,22 +3,35 @@
namespace MessagePack;

use PhpCsFixer\Config;
use PhpCsFixer\Fixer\ConfigurableFixerInterface;
use PhpCsFixer\Fixer\ConstantNotation\NativeConstantInvocationFixer;
use PhpCsFixer\Fixer\FixerInterface;
use PhpCsFixer\Fixer\FunctionNotation\NativeFunctionInvocationFixer;
use PhpCsFixer\FixerConfiguration\FixerConfigurationResolver;
use PhpCsFixer\FixerDefinition\FixerDefinition;
use PhpCsFixer\FixerDefinition\FixerDefinitionInterface;
use PhpCsFixer\Tokenizer\Tokens;

final class FilterableFixer implements FixerInterface
final class FilterableFixer implements ConfigurableFixerInterface
{
private $fixer;
private $pathRegex;
private ConfigurableFixerInterface $fixer;
private string $pathRegex;

public function __construct(FixerInterface $fixer, string $pathRegex)
public function __construct(ConfigurableFixerInterface $fixer, string $pathRegex)
{
$this->fixer = $fixer;
$this->pathRegex = $pathRegex;
}

public function configure(array $configuration): void
{
$this->fixer->configure($configuration);
}

public function getConfigurationDefinition(): FixerConfigurationResolver
{
return $this->fixer->getConfigurationDefinition();
}

public function isCandidate(Tokens $tokens) : bool
{
return $this->fixer->isCandidate($tokens);
Expand Down Expand Up @@ -52,7 +65,12 @@ public function supports(\SplFileInfo $file) : bool

return $this->fixer->supports($file);
}
};

public function getDefinition() : FixerDefinitionInterface
{
return $this->fixer->getDefinition();
}
}

$header = <<<EOF
This file is part of the rybakit/msgpack.php package.
Expand All @@ -63,7 +81,7 @@ public function supports(\SplFileInfo $file) : bool
file that was distributed with this source code.
EOF;

return Config::create()
return (new Config())
->setUsingCache(false)
->setRiskyAllowed(true)
->registerCustomFixers([
Expand All @@ -75,13 +93,17 @@ public function supports(\SplFileInfo $file) : bool
'@Symfony:risky' => true,
'array_syntax' => ['syntax' => 'short'],
'binary_operator_spaces' => ['operators' => ['=' => null, '=>' => null]],
'is_null' => false, // https://github.com/FriendsOfPHP/PHP-CS-Fixer/issues/4015
'fully_qualified_strict_types' => false,
'integer_literal_case' => false,
'is_null' => false,
'native_constant_invocation' => false,
'native_function_invocation' => false,
'FilterableFixer/native_constant_invocation' => true,
'FilterableFixer/native_function_invocation' => true,
'FilterableFixer/native_constant_invocation' => ['strict' => false],
'FilterableFixer/native_function_invocation' => ['strict' => false],
'no_useless_else' => true,
'no_useless_return' => true,
'no_useless_concat_operator' => false,
'no_superfluous_phpdoc_tags' => false,
'ordered_imports' => [
'sort_algorithm' => 'alpha',
'imports_order' => ['class', 'function', 'const'],
Expand All @@ -90,6 +112,7 @@ public function supports(\SplFileInfo $file) : bool
'phpdoc_order' => true,
'phpdoc_to_comment' => false,
'return_type_declaration' => ['space_before' => 'one'],
'statement_indentation' => false,
'strict_comparison' => true,
'header_comment' => [
'comment_type' => 'PHPDoc',
Expand Down
2 changes: 1 addition & 1 deletion LICENSE
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
The MIT License (MIT)

Copyright (c) 2015-2025 Eugene Leonovich
Copyright (c) 2015-2026 Eugene Leonovich

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
Expand Down
22 changes: 11 additions & 11 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ composer require rybakit/msgpack

### Packing

To pack values you can either use an instance of a `Packer`:
To pack values, you can either use an instance of a `Packer`:

```php
$packer = new Packer();
Expand All @@ -66,8 +66,8 @@ $packed = MessagePack::pack($value);

In the examples above, the method `pack` automatically packs a value depending on its type. However, not all PHP types
can be uniquely translated to MessagePack types. For example, the MessagePack format defines `map` and `array` types,
which are represented by a single `array` type in PHP. By default, the packer will pack a PHP array as a MessagePack
array if it has sequential numeric keys, starting from `0` and as a MessagePack map otherwise:
which are represented by a single `array` type in PHP. By default, the packer will pack a PHP array as a MessagePack
array if it has sequential numeric keys starting from `0`, and as a MessagePack map otherwise:

```php
$mpArr1 = $packer->pack([1, 2]); // MP array [1, 2]
Expand Down Expand Up @@ -144,7 +144,7 @@ $packer = new Packer(PackOptions::FORCE_FLOAT32 | PackOptions::FORCE_FLOAT64);

### Unpacking

To unpack data you can either use an instance of a `BufferUnpacker`:
To unpack data, you can either use an instance of a `BufferUnpacker`:

```php
$unpacker = new BufferUnpacker();
Expand All @@ -159,8 +159,8 @@ or call a static method on the `MessagePack` class:
$value = MessagePack::unpack($packed);
```

If the packed data is received in chunks (e.g. when reading from a stream), use the `tryUnpack` method, which attempts
to unpack data and returns an array of unpacked messages (if any) instead of throwing an `InsufficientDataException`:
If the packed data is received in chunks (e.g. when reading from a stream), use the `tryUnpack` method, which attempts
to unpack the data and returns an array of unpacked messages (if any) instead of throwing an `InsufficientDataException`:

```php
while ($chunk = ...) {
Expand Down Expand Up @@ -286,8 +286,8 @@ $packedArray = $packer->pack([1, 2, 3]);

As with type objects, type transformers are only responsible for *serializing* values. They should be
used when you need to serialize a value that does not implement the [CanBePacked](src/CanBePacked.php)
interface. Examples of such values could be instances of built-in or third-party classes that you don't
own, or non-objects such as resources.
interface. Examples of such values include instances of built-in or third-party classes that you do not
own, or non-objects such as resources.

A transformer class must implement the [CanPack](src/CanPack.php) interface. To use a transformer,
it must first be registered in the packer. Here is an example of how to serialize PHP streams into
Expand Down Expand Up @@ -346,7 +346,7 @@ $timestamp = MessagePack::unpack($packedTimestamp);

In addition, the format can be extended with your own types. For example, to make the built-in PHP `DateTime` objects
first-class citizens in your code, you can create a corresponding extension, as shown in the [example](examples/MessagePack/DateTimeExtension.php).
Please note, that custom extensions have to be registered with a unique extension ID (an integer from `0` to `127`).
Please note that custom extensions must be registered with a unique extension ID (an integer from `0` to `127`).

> *More extension examples can be found in the [examples/MessagePack](examples/MessagePack) directory.*

Expand All @@ -371,7 +371,7 @@ Run tests as follows:
vendor/bin/phpunit
```

Also, if you already have Docker installed, you can run the tests in a docker container. First, create a container:
Also, if you already have Docker installed, you can run the tests in a Docker container. First, create a container:

```sh
./dockerfile.sh | docker build -t msgpack -
Expand All @@ -396,7 +396,7 @@ docker run --rm -v $PWD:/msgpack -w /msgpack msgpack
#### Fuzzing

To ensure that the unpacking works correctly with malformed/semi-malformed data, you can use a testing technique
called [Fuzzing](https://en.wikipedia.org/wiki/Fuzzing). The library ships with a help file (target)
called [fuzzing](https://en.wikipedia.org/wiki/Fuzzing). The library ships with a helper file (target)
for [PHP-Fuzzer](https://github.com/nikic/PHP-Fuzzer) and can be used as follows:

```sh
Expand Down
9 changes: 5 additions & 4 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,14 @@
}
],
"require": {
"php": "^7.1.1|^8"
"php": "^8.2"
},
"require-dev": {
"ext-decimal": "*",
"ext-gmp": "*",
"friendsofphp/php-cs-fixer": "^2.14",
"phpunit/phpunit": "^7.1|^8|^9",
"vimeo/psalm": "^3.9|^4"
"friendsofphp/php-cs-fixer": "^3",
"phpunit/phpunit": "^11",
"vimeo/psalm": "^5 || ^6"
},
"suggest": {
"ext-decimal": "For converting overflowed integers to Decimal objects",
Expand Down
19 changes: 13 additions & 6 deletions examples/MessagePack/DateTimeExtension.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,23 @@
use MessagePack\Extension;
use MessagePack\Packer;

class DateTimeExtension implements Extension
final class DateTimeExtension implements Extension
{
private $type;

public function __construct(int $type)
{
$this->type = $type;
public function __construct(
private readonly int $type,
) {
}

#[\Override]
public function getType() : int
{
return $this->type;
}

/**
* @param mixed $value
*/
#[\Override]
public function pack(Packer $packer, $value) : ?string
{
if (!$value instanceof \DateTimeInterface) {
Expand All @@ -38,6 +41,10 @@ public function pack(Packer $packer, $value) : ?string
return $packer->packExt($this->type, $value->format('YmdHisue'));
}

/**
* @return \DateTimeImmutable|false
*/
#[\Override]
public function unpackExt(BufferUnpacker $unpacker, int $extLength)
{
return \DateTimeImmutable::createFromFormat('YmdHisue', $unpacker->read($extLength));
Expand Down
9 changes: 3 additions & 6 deletions examples/MessagePack/StructList.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,8 @@

final class StructList
{
/** @readonly */
public $list;

public function __construct(array $list)
{
$this->list = $list;
public function __construct(
public array $list,
) {
}
}
26 changes: 19 additions & 7 deletions examples/MessagePack/StructListExtension.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,23 @@
use MessagePack\Extension;
use MessagePack\Packer;

class StructListExtension implements Extension
final class StructListExtension implements Extension
{
private $type;

public function __construct(int $type)
{
$this->type = $type;
public function __construct(
private readonly int $type,
) {
}

#[\Override]
public function getType() : int
{
return $this->type;
}

/**
* @param mixed $value
*/
#[\Override]
public function pack(Packer $packer, $value) : ?string
{
if (!$value instanceof StructList) {
Expand All @@ -40,7 +43,12 @@ public function pack(Packer $packer, $value) : ?string
return $packer->packArray($value->list);
}

$keys = \array_keys(\reset($value->list));
$first = \reset($value->list);
if (false === $first) {
return $packer->packArray($value->list);
}

$keys = \array_keys($first);

$values = '';
foreach ($value->list as $item) {
Expand All @@ -56,6 +64,10 @@ public function pack(Packer $packer, $value) : ?string
);
}

/**
* @return array<int, array<array-key, mixed>>
*/
#[\Override]
public function unpackExt(BufferUnpacker $unpacker, int $extLength)
{
$keys = $unpacker->unpackArray();
Expand Down
11 changes: 4 additions & 7 deletions examples/MessagePack/Text.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,15 +13,12 @@

final class Text
{
/** @readonly */
public $str;

public function __construct(string $str)
{
$this->str = $str;
public function __construct(
public readonly string $str,
) {
}

public function __toString()
public function __toString() : string
{
return $this->str;
}
Expand Down
Loading