{"id":35784080,"url":"https://github.com/darsyn/unboxer","last_synced_at":"2026-01-07T06:38:25.106Z","repository":{"id":56962576,"uuid":"145865034","full_name":"darsyn/unboxer","owner":"darsyn","description":"Simple utility to unbox complex data structures (objects) to native data types.","archived":false,"fork":false,"pushed_at":"2021-03-09T12:30:29.000Z","size":17,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"develop","last_synced_at":"2024-05-03T08:20:50.501Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/darsyn.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2018-08-23T14:27:27.000Z","updated_at":"2024-05-03T08:20:50.502Z","dependencies_parsed_at":"2022-08-21T08:20:50.123Z","dependency_job_id":null,"html_url":"https://github.com/darsyn/unboxer","commit_stats":null,"previous_names":[],"tags_count":5,"template":false,"template_full_name":null,"purl":"pkg:github/darsyn/unboxer","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/darsyn%2Funboxer","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/darsyn%2Funboxer/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/darsyn%2Funboxer/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/darsyn%2Funboxer/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/darsyn","download_url":"https://codeload.github.com/darsyn/unboxer/tar.gz/refs/heads/develop","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/darsyn%2Funboxer/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28233393,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2026-01-07T02:00:05.975Z","response_time":58,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2026-01-07T06:38:20.931Z","updated_at":"2026-01-07T06:38:25.098Z","avatar_url":"https://github.com/darsyn.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"Simple utility to unbox complex data structures (objects) to native data types,\nsuitable for encoding (for example, JSON).\n\n# Documentation\n\n## Code of Conduct\n\nThis project includes and adheres to the [Contributor Covenant as a Code of\nConduct](CODE_OF_CONDUCT.md).\n\n## Supported Types\n\nThis library returns all scalar and null values as-is, plus recursively\nprocessing all array (and `stdClass`) types.\n\nWhen this library encounters an object that is an instance of a known type, it\nwill attempt to convert it by using the return value of a specific method.\nObject types supported by this library out-of-the-box include:\n\n- Dates (objects implementing `DateTimeInterface`) which are converted to\n  strings according to RFC3339 (eg, `2019-02-05T12:15:32+00:00`).\n- Timezones (objects implementing `DateTimeZone`) which result in a string\n  containing the timezone name (eg, `America/Vancouver`).\n- Exceptions and errors (objects implementing `Throwable`) which result in a\n  string containing the exception message.\n- JSON (objects implementing `JsonSerializable`) which result in the library\n  recursively iterating over the JSON data returned.\n- Doctrine collections (objects implementing `Collection` interface) which\n  result in the library iterating over each of the items inside the collection.\n\nAdditionally, any user-land object can implement `UnboxableInterface`. Similar\nto `JsonSerializable::jsonSerialize()` method, the `__unbox` method can return\nanything as a representation of its internal state.\nIt is recommended to return unboxable objects as-is, as everything returned from\n`UnboxableInterface::__unbox` is recursively iterated over anyway.\n\n## Brief Example\n\n```php\n\u003c?php declare(strict_types=1);\n\nuse Darsyn\\Unboxer\\Unboxer;\nuse Darsyn\\Unboxer\\UnboxableInterface;\nuse Darsyn\\Unboxer\\UnboxingException;\n\nclass Group implements UnboxableInterface {\n    public function __construct(\n        private string $name\n    ) {}\n\n    public function __unbox() {\n        return $this-\u003ename;\n    }\n}\n\nclass Options implements \\JsonSerializable {\n    public function __construct(\n        private bool $active,\n        private bool $verified,\n        private \\DateTimeZone $timezone\n    ) {}\n\n    public function jsonSerialize() {\n        return [\n            'active' =\u003e $this-\u003eactive,\n            'verified' =\u003e $this-\u003everified,\n            'tz' =\u003e $this-\u003etimezone,\n        ];\n    }\n}\n\nclass Member implements UnboxableInterface\n{\n    private ArrayCollection $groups;\n\n    public function __construct(\n        private int $id,\n        private string $username,\n        array $groups = [],\n        private ?Options $options = null\n    ) {\n        $this-\u003egroups = new ArrayCollection($groups);\n    }\n\n    public function __unbox()\n    {\n        return [\n            // Scalars are used as-is.\n            'id' =\u003e $this-\u003eid,\n            'username' =\u003e $this-\u003eusername,\n            // Objects of known types are returned as-is, but recursively iterated over.\n            'groups' =\u003e $this-\u003egroups,\n            // JSON-serializable objects are never actually run through json_encode().\n            'options' =\u003e $this-\u003eoptions ?: [],\n        ];\n    }\n}\n\n$member = new Member(123, 'dr-evil', [\n    new Group('admin'),\n    new Group('moderator'),\n    new Group('sharks-with-lasers'),\n], new Options(true, false, new \\DateTimeZone('America/Vancouver')));\n\ntry {\n    $output = (new Unboxer)-\u003eunbox($member);\n    var_dump($output);\n} catch (UnboxingException $e) {\n    echo $e-\u003egetMessage();\n}\n```\n\n`var_dump`ing the variable `$output` results in:\n\n```\narray(4) {\n  'id' =\u003e\n  int(123)\n  'username' =\u003e\n  string(7) \"dr-evil\"\n  'groups' =\u003e\n  array(3) {\n    [0] =\u003e\n    string(5) \"admin\"\n    [1] =\u003e\n    string(9) \"moderator\"\n    [2] =\u003e\n    string(18) \"sharks-with-lasers\"\n  }\n  'options' =\u003e\n  array(3) {\n    'active' =\u003e\n    bool(true)\n    'verified' =\u003e\n    bool(false)\n    'tz' =\u003e\n    string(17) \"America/Vancouver\"\n  }\n}\n```\n\nNote that returning multiple nested unboxable objects will result in the output\ncollapsing down into a single value:\n\n```php\n\u003c?php declare(strict_types=1);\n\nuse Darsyn\\Unboxer\\Unboxer;\nuse Darsyn\\Unboxer\\UnboxableInterface;\nuse Darsyn\\Unboxer\\UnboxingException;\n\n$data = new class implements UnboxableInterface {\n    public function __unbox() {\n        return new class implements UnboxableInterface {\n            public function __unbox() {\n                return new class implements UnboxableInterface {\n                    public function __unbox() {\n                        return new \\RuntimeException('Error Message');\n                    }\n                };\n            }\n        };\n    }\n};\n\ntry {\n    $output = (new Unboxer)-\u003eunbox($data);\n    var_dump($output);\n} catch (UnboxingException $e) {\n    echo $e-\u003egetMessage();\n}\n```\n\n```\nstring(13) \"Error Message\"\n```\n\n## Extending\n\nAdditional known object types can be added by extending `Unboxer` and overriding\nthe `getKnownDataTypes` method. For each known object type, either a closure or\nan array specifying which method to call on the object may can specified:\n\n```php\n\u003c?php declare(strict_types=1);\n\nuse Darsyn\\Unboxer\\Unboxer;\n\nclass MyUnboxer extends Unboxer {\n    protected function getKnownDataMethods(): iterable {\n        // Don't forget to return the known data methods defined in the original, parent Unboxer.\n        // The parent returns an array, but any iterable is acceptable.\n        yield from parent::getKnownDataMethods();\n\n        // Config array example.\n        // Must be in the format ['methodToCall', ['optional', 'arguments', 'array']].\n        yield \\DateTimeInterface::class =\u003e ['format', [\\DateTimeInterface::RFC3339]];\n\n        // Closure example.\n        yield \\DateTimeInterface::class =\u003e function (\\DateTimeInterface $date): string {\n            return $date-\u003eformat(\\DateTimeInterface::RFC3339);\n        };\n    }\n}\n```\n\nThe unboxer will, by default, convert any objects with the `__toString()` magic\nmethod to a string. To turn this functionality off, extend `Unboxer` and\noverride the class constant `STRINGIFY_OBJECTS`.\n\n```php\n\u003c?php declare(strict_types=1);\n\nuse Darsyn\\Unboxer\\Unboxer;\n\nclass MyUnboxer extends Unboxer {\n    public const STRINGIFY_OBJECTS = false;\n}\n```\n\n# License\n\nPlease see the [separate license file](LICENSE.md) included in this repository\nfor a full copy of the MIT license, which this project is licensed under.\n\n# Authors\n\n- [Zan Baldwin](https://zanbaldwin.com)\n\nIf you make a contribution (submit a pull request), don't forget to add your\nname here!\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdarsyn%2Funboxer","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdarsyn%2Funboxer","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdarsyn%2Funboxer/lists"}