{"id":46833988,"url":"https://github.com/reinder83/binary-flags","last_synced_at":"2026-03-10T11:04:38.626Z","repository":{"id":57046985,"uuid":"71803318","full_name":"reinder83/binary-flags","owner":"reinder83","description":"Simple BinaryFlags class to extend from","archived":false,"fork":false,"pushed_at":"2026-02-27T10:15:15.000Z","size":113,"stargazers_count":12,"open_issues_count":0,"forks_count":3,"subscribers_count":3,"default_branch":"master","last_synced_at":"2026-02-27T13:36:15.196Z","etag":null,"topics":["binary","bitwise","bitwise-operators","flags","php","php-library"],"latest_commit_sha":null,"homepage":"","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/reinder83.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null},"funding":{"github":"reinder83"}},"created_at":"2016-10-24T15:30:56.000Z","updated_at":"2026-02-27T10:13:04.000Z","dependencies_parsed_at":"2023-02-09T02:31:17.123Z","dependency_job_id":"8bc2b887-0e43-46ec-bf4e-c6d167cdc92b","html_url":"https://github.com/reinder83/binary-flags","commit_stats":{"total_commits":49,"total_committers":3,"mean_commits":"16.333333333333332","dds":"0.30612244897959184","last_synced_commit":"f42cf36f4a9d38fa1f0b4d77a1383fe9d9a2a7af"},"previous_names":[],"tags_count":13,"template":false,"template_full_name":null,"purl":"pkg:github/reinder83/binary-flags","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/reinder83%2Fbinary-flags","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/reinder83%2Fbinary-flags/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/reinder83%2Fbinary-flags/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/reinder83%2Fbinary-flags/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/reinder83","download_url":"https://codeload.github.com/reinder83/binary-flags/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/reinder83%2Fbinary-flags/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":30331646,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-03-10T05:25:20.737Z","status":"ssl_error","status_checked_at":"2026-03-10T05:25:17.430Z","response_time":106,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"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":["binary","bitwise","bitwise-operators","flags","php","php-library"],"created_at":"2026-03-10T11:04:38.012Z","updated_at":"2026-03-10T11:04:38.609Z","avatar_url":"https://github.com/reinder83.png","language":"PHP","funding_links":["https://github.com/sponsors/reinder83","https://www.buymeacoffee.com/reinder83"],"categories":[],"sub_categories":[],"readme":"[![test](https://github.com/reinder83/binary-flags/actions/workflows/test.yml/badge.svg)](https://github.com/reinder83/binary-flags/actions/workflows/test.yml)\n\n# BinaryFlags\nWith this class you can easily add flags to your projects.\n  \nThe number of flags you can use is limited to the architecture of your system, e.g.: 32 flags on a 32-bit system or 64 flags on 64-bit system.\nTo store 64-bit flags in a database, you will need to store it as UNSIGNED BIGINT in MySQL or an equivalent in your datastore.\n\nThis package also comes with a trait which you can use to implement binary flags directly in your own class.\n\n### Trait naming\nFor new code, prefer `Reinder83\\BinaryFlags\\Traits\\InteractsWithNumericFlags`.\n`Reinder83\\BinaryFlags\\Traits\\BinaryFlags` remains available for backward compatibility.\nFor enum-based usage, use `Reinder83\\BinaryFlags\\BinaryEnumFlags` (which uses `Traits\\InteractsWithEnumFlags`).\n\n\n## Installing\nTo install this package simply run the following command in the root of your project.\n```\ncomposer require reinder83/binary-flags\n```\n\n## Deprecation Notice (Upcoming v3.0.0 Breaking Change)\nStarting in `v2.1.0`, passing `float` values as masks or flags is deprecated.\n\n- Current `v2.x` behavior: floats are still accepted for backward compatibility, but trigger a deprecation warning.\n- `v3.0.0` behavior: masks and flags will be `int`-only.\n- `v3.0.0` behavior: `Bits::BIT_64` will be removed.\n\n### BIT_64 Notice\n`Bits::BIT_64` is being removed because PHP numbers for bitwise flags are signed. The 64th bit is the sign bit, so it cannot be used reliably as a normal flag.\n\nUsing integer-compatible bits (`BIT_1` through `BIT_63`) prevents these issues and is the supported path for `v3.0.0`.\n\nTo prepare for `v3.0.0`, cast incoming values before using the API:\n\n```php\n$flags-\u003esetMask((int) $maskFromLegacySource);\n$flags-\u003eaddFlag((int) $incomingFlag);\n```\n\nSee [UPGRADE-v3.md](UPGRADE-v3.md) for migration details.\n\n## Methods\nThe following methods can be used:\n\n##### setMask(int $mask)\nOverwrite the current mask.\nThis can be passed as first argument in the constructor.\n\n##### getMask(): int\nRetrieve the current mask.\n\nWhen using `BinaryEnumFlags`, `getMask()` returns a `Mask` object instead.\nUse `getMaskValue(): int` on enum-based flags if you need the numeric mask.\n\n##### getMaskValue(): int\n_Since: v2.1.0_ \\\nReturns the numeric mask value for storage/interoperability.\nThis method is only available on enum-backed flags (`BinaryEnumFlags`).\n\n##### setOnModifyCallback(callable $onModify)\nSet a callback function which is called when the mask changes. \nThis can be passed as second argument in the constructor.\n\n##### getFlagNames([int $mask, [bool $asArray=false]])\nGive the name(s) for the given `$mask` or the current mask when omitted.\nWhen `$asArray` is `true` the method will return an array with the names, \notherwise a comma separated string will be returned (default).\n\n##### addFlag(int $flag)\nAdds one or multiple flags to the current mask.\n\n##### removeFlag(int $flag)\nRemoves one or multiple flags from the current mask.\n\n##### checkFlag(int $flag, [bool $checkAll=true]): bool\nCheck if given flag(s) are set in the current mask. \nBy default, it will check all bits in the given flag. \nWhen you want to match any of the given flags set `$checkAll` to `false`.\n\n##### checkAnyFlag(int $mask): bool\n_Since: v1.0.1_ \\\nFor your convenience I've added an alias to checkFlag with `$checkAll` set to `false`.\n\n##### count(): int\n_Since: v1.2.0_ \\\nReturns the number of flags that have been set.\n\n##### jsonSerialize(): mixed\n_Since: v1.2.0_ \\\nReturn a value that can be encoded by json_encode() in the form of `[\"mask\" =\u003e 7]`. You should not have to call this method directly,\ninstead you can pass the BinaryFlags object to json_encode which will convert it to '{\"mask\": 7}'.\n\n## Static Methods\nThe following static methods can be used:\n\n##### getAllFlags(): array\n_Since: v1.1.0_ \\\nReturn all the flags with their names as an array, using their flag mask as key.\nThis method can also be overloaded to return custom names for the flags, \nwhich will be used by the `getFlagNames` method.\n\n##### getAllFlagsMask(): int\n_Since: v1.1.0_ \\\nReturn mask of all the flags together\n\n## Iteration\n_Since: v1.2.0_ \\\nYou can treat a BinaryFlags object as an iterable, where each iteration will return the next bit value that has been set including its description (or the name of the constant representing the bit value).\n\n## Example usage\n\nBelow is some example usage code\n\n##### Create classes\n```php\n// example classes which the following examples will refer to\nuse Reinder83\\BinaryFlags\\BinaryFlags;\nuse Reinder83\\BinaryFlags\\Bits;\n\nclass ExampleFlags extends BinaryFlags\n{\n    const FOO = Bits::BIT_1;\n    const BAR = Bits::BIT_2;\n    const BAZ = Bits::BIT_3;\n}\n```\n\n##### Simple usage\n```php\n$exampleFlags = new ExampleFlags();\n\n// add BAR flag\n$exampleFlags-\u003eaddFlag(ExampleFlags::BAR);\n\nvar_export($exampleFlags-\u003echeckFlag(ExampleFlags::FOO)); \n// false\nvar_export($exampleFlags-\u003echeckFlag(ExampleFlags::BAR)); \n// true\n\n// remove BAR flag\n$exampleFlags-\u003eremoveFlag(ExampleFlags::BAR);\n\nvar_export($exampleFlags-\u003echeckFlag(ExampleFlags::BAR)); \n// false\n```\n\n##### Usage with multiple flags\n```php\n$exampleFlags = new ExampleFlags();\n\n// add FOO and BAR\n$exampleFlags-\u003eaddFlag(ExampleFlags::FOO | ExampleFlags::BAR); \n\nvar_export($exampleFlags-\u003echeckFlag(ExampleFlags::FOO)); \n// true\n\nvar_export($exampleFlags-\u003echeckFlag(ExampleFlags::FOO | ExampleFlags::BAZ)); \n// false because BAZ is not set\n\nvar_export($exampleFlags-\u003echeckFlag(ExampleFlags::FOO | ExampleFlags::BAR)); \n// true because both flags are set\n\nvar_export($exampleFlags-\u003echeckFlag(ExampleFlags::FOO | ExampleFlags::BAZ, false)); \n// true because one of the flags is set (FOO)\n\n// alias of the above method\nvar_export($exampleFlags-\u003echeckAnyFlag(ExampleFlags::FOO | ExampleFlags::BAZ)); \n// true\n\n```\n\n##### Enum usage (optional)\n```php\nuse Reinder83\\BinaryFlags\\BinaryEnumFlags;\nuse Reinder83\\BinaryFlags\\Mask;\n\nenum Permission: int\n{\n    case CanView = Bits::BIT_1;\n    case CanBook = Bits::BIT_2;\n    case CanCancel = Bits::BIT_3;\n}\n\nclass PermissionFlags extends BinaryEnumFlags\n{\n    protected static function getFlagEnumClass(): string\n    {\n        return Permission::class;\n    }\n}\n\n$flags = new PermissionFlags(Permission::CanView);\n$flags-\u003eaddFlag(Permission::CanBook);\n$flags-\u003eaddFlag(Mask::forEnum(Permission::class, Permission::CanCancel));\n\nvar_export($flags-\u003echeckFlag(Permission::CanBook));\n// true\n\nvar_export($flags-\u003egetFlagNames());\n// 'Can View, Can Book, Can Cancel'\n```\n\n##### Migrating from numeric flags to enum flags\n```php\n// Before (numeric PermissionFlags)\nuse Reinder83\\BinaryFlags\\BinaryFlags;\n\nclass PermissionFlags extends BinaryFlags\n{\n    public const CAN_VIEW = Bits::BIT_1;\n    public const CAN_BOOK = Bits::BIT_2;\n}\n\n$flags = new PermissionFlags($storedMask);\n$flags-\u003eaddFlag(PermissionFlags::CAN_VIEW | PermissionFlags::CAN_BOOK);\n$storedMask = $flags-\u003egetMask(); // int\n\n// After (enum PermissionFlags)\nuse Reinder83\\BinaryFlags\\BinaryEnumFlags;\nuse Reinder83\\BinaryFlags\\Mask;\n\nenum Permission: int\n{\n    case CanView = Bits::BIT_1;\n    case CanBook = Bits::BIT_2;\n}\n\nclass PermissionFlags extends BinaryEnumFlags\n{\n    protected static function getFlagEnumClass(): string\n    {\n        return Permission::class;\n    }\n}\n\n$flags = new PermissionFlags(Mask::fromInt($storedMask, Permission::class));\n$flags-\u003eaddFlag(Permission::CanView);\n$flags-\u003eaddFlag(Permission::CanBook);\n\n// Save as integer for storage/interop\n$storedMask = $flags-\u003egetMaskValue();\n```\n\n##### Flag names example\n_By default, the flag names are based on the constant names_\n```php\n$exampleFlags = new ExampleFlags();\n\n$exampleFlags-\u003eaddFlag(ExampleFlags::FOO | ExampleFlags::BAR | ExampleFlags::BAZ);\nvar_export($exampleFlags-\u003egetFlagNames());\n// 'Foo, Bar, Baz'\n\n// null will force current mask\nvar_export($exampleFlags-\u003egetFlagNames(null, true));\n/*\narray (\n  0 =\u003e 'Foo',\n  1 =\u003e 'Bar',\n  2 =\u003e 'Baz',\n)\n*/\n\n// get flag names of given mask\nvar_export($exampleFlags-\u003egetFlagNames(ExampleFlags::FOO | ExampleFlags::BAR));\n// 'Foo, Bar'\n```\n\n##### Custom flag names example\nIf you want custom flag names that are not equal to the constant names, you can override these with `getAllFlags()`\n\n```php\nclass ExampleFlagsWithNames extends BinaryFlags\n{\n    const FOO = Bits::BIT_1;\n    const BAR = Bits::BIT_2;\n    const BAZ = Bits::BIT_3;\n    \n    public static function getAllFlags()\n    {\n        return [\n            static::FOO =\u003e 'My foo description',\n            static::BAR =\u003e 'My bar description',\n            static::BAZ =\u003e 'My baz description',\n        ];\n    }\n}\n\n$exampleFlags = new ExampleFlagsWithNames();\n\n$exampleFlags-\u003eaddFlag(ExampleFlags::FOO | ExampleFlags::BAR | ExampleFlags::BAZ);\n\n// null will force current mask\nvar_export($exampleFlags-\u003egetFlagNames(null, true));\n/*\narray (\n  0 =\u003e 'My foo description',\n  1 =\u003e 'My bar description',\n  2 =\u003e 'My baz description',\n)\n*/\n```\n\n##### Example usage with Eloquent models\n\n```php\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass Test extends Model\n{\n    private $flagsObject;\n\n    /**\n     * Retrieve flags\n     * @return ExampleFlags\n     */\n    public function getFlagsAttribute()\n    {\n        if ($this-\u003eflagsObject === null) {\n            $this-\u003eflagsObject = new ExampleFlags(\n                $this-\u003eattributes['flags'], // set current flags mask\n                function (ExampleFlags $flags) { // set callback function\n                    // update the flags in this model\n                    $this-\u003esetAttribute('flags', $flags-\u003egetMask());\n                }\n            );\n        }\n        return $this-\u003eflagsObject;\n    }\n}\n\n// retrieve object from DB\n$test = Test::find(1);\n\n// do binary operations on the flags class as described earlier\n$test-\u003eflags-\u003echeckFlag(ExampleFlags::FOO);\n```\n\n\n## Support\nFor bugs or feature requests feel free to contact me or submit an issue or pull request. \nOr you can support me by buying me a coffee:\n\n[![Buy me a coffee][buymeacoffee-icon]][buymeacoffee-link]\n\n[buymeacoffee-icon]: https://www.buymeacoffee.com/assets/img/guidelines/download-assets-sm-2.svg\n[buymeacoffee-link]: https://www.buymeacoffee.com/reinder83\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Freinder83%2Fbinary-flags","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Freinder83%2Fbinary-flags","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Freinder83%2Fbinary-flags/lists"}