> ## Documentation Index
> Fetch the complete documentation index at: https://docs.syntblaze.com/llms.txt
> Use this file to discover all available pages before exploring further.

# PHP Attribute

PHP Attributes (introduced in PHP 8.0) provide a native, structured syntax for embedding machine-readable metadata directly into code declarations. They replace docblock annotations by allowing developers to associate configuration, state, or behavioral directives with classes, methods, properties, parameters, functions, and class constants. This metadata is inert by default and must be explicitly inspected and instantiated at runtime using the PHP Reflection API.

Attributes are declared using the `#[...]` syntax and can accept zero or more arguments, which are passed to the underlying attribute class constructor.

```php theme={"dark"}
#[SimpleAttribute]
#[AttributeWithArguments('value', key: 'value')]
class TargetClass {}
```

## Creating Custom Attributes

Under the hood, an attribute is simply a standard PHP class. To designate a class as a valid attribute, it must be annotated with the built-in `#[Attribute]` attribute. The constructor of this class dictates the signature of the arguments that can be passed when the attribute is applied.

```php theme={"dark"}
#[Attribute]
class SystemMetadata {
    public function __construct(
        public readonly string $identifier,
        public readonly int $version = 1
    ) {}
}
```

## Applying Attributes

Once defined, the attribute can be applied to various structural elements in PHP. Multiple attributes can be applied to the same declaration, either grouped within the same brackets or stacked.

```php theme={"dark"}
#[SystemMetadata(identifier: 'core_module', version: 2)]
class ModuleManager {
    
    #[SystemMetadata('init_flag')]
    #[AnotherAttribute]
    public bool $isInitialized;

    #[SystemMetadata('boot_sequence')]
    public function boot(
        #[SystemMetadata('config_array')] array $config
    ): void {}
}
```

## Restricting Attribute Targets

By default, a custom attribute can be applied to any declaration. You can restrict where an attribute is syntactically valid by passing bitmask flags to the base `#[Attribute]` declaration using predefined constants from the `Attribute` class.

Available target flags include:

* `Attribute::TARGET_CLASS`
* `Attribute::TARGET_FUNCTION`
* `Attribute::TARGET_METHOD`
* `Attribute::TARGET_PROPERTY`
* `Attribute::TARGET_CLASS_CONSTANT`
* `Attribute::TARGET_PARAMETER`
* `Attribute::TARGET_ALL` (Default)

```php theme={"dark"}
#[Attribute(Attribute::TARGET_METHOD | Attribute::TARGET_FUNCTION)]
class ExecutableMetadata {}
```

## Repeatable Attributes

By default, a specific attribute can only be applied to a given declaration once. To allow multiple instances of the same attribute on a single declaration, the `Attribute::IS_REPEATABLE` flag must be combined with the target flags.

```php theme={"dark"}
#[Attribute(Attribute::TARGET_CLASS | Attribute::IS_REPEATABLE)]
class Tag {
    public function __construct(public string $tagName) {}
}

#[Tag('core')]
#[Tag('service')]
class TaggedService {}
```

## Resolving Attributes via Reflection

Attributes do not execute automatically. To read and utilize attribute data, you must use the Reflection API. Reflection classes (e.g., `ReflectionClass`, `ReflectionMethod`, `ReflectionProperty`) provide the `getAttributes()` method, which returns an array of `ReflectionAttribute` objects.

The `ReflectionAttribute` object contains the metadata about the attribute but does not immediately instantiate the underlying attribute class. You must call `newInstance()` to invoke the attribute's constructor and receive the actual class instance.

```php theme={"dark"}
$reflection = new ReflectionClass(ModuleManager::class);

// Retrieve specific attributes by passing the class name
$attributes = $reflection->getAttributes(SystemMetadata::class);

foreach ($attributes as $reflectionAttribute) {
    // $reflectionAttribute->getName() returns the attribute class name
    // $reflectionAttribute->getArguments() returns the raw arguments array
    
    // Instantiate the actual SystemMetadata class
    $metadataInstance = $reflectionAttribute->newInstance();
    
    echo $metadataInstance->identifier; // Outputs: core_module
    echo $metadataInstance->version;    // Outputs: 2
}
```

<div
  style={{ 
display: "flex", 
justifyContent: "space-between", 
alignItems: "center", 
maxWidth: "754px", 
padding: "1rem 0",
marginBottom: "24px"
}}
>
  <span style={{ fontWeight: "bold", fontSize: "1.25rem", color: "var(--tw-prose-headings)", fontFamily: "Inter, ui-sans-serif, system-ui, sans-serif" }}>Tired of Poor PHP Skills? Fix That With Deep Grasping!</span>

  <a
    href="https://syntblaze.com"
    target="_blank"
    style={{ 
  marginLeft: "24px",
  textDecoration: "none", 
  backgroundColor: "#007AFF",
  color: "#ffffff", 
  padding: "6px 16px", 
  borderRadius: "16px",
  fontSize: "0.9rem",
  fontWeight: "600",
  textAlign: "center",
  transition: "background-color 0.2s ease"
}}
  >
    Learn More
  </a>
</div>

<div style={{ display: "flex", gap: "12px", flexWrap: "wrap" }}>
  <img src="https://mintcdn.com/syntblazellc/-L0ums_2lctDSZ1l/images/skill-tracking.png?fit=max&auto=format&n=-L0ums_2lctDSZ1l&q=85&s=b9b0305c93bb501c9e767b5c76c88835" style={{ width: "30%", minWidth: 60 }} width="621" height="1344" data-path="images/skill-tracking.png" />

  <img src="https://mintcdn.com/syntblazellc/23tyuOzaWS88qFlc/images/nuggets.png?fit=max&auto=format&n=23tyuOzaWS88qFlc&q=85&s=c86c80197299762989e9b882419b2109" style={{ width: "30%", minWidth: 60 }} width="621" height="1344" data-path="images/nuggets.png" />

  <img src="https://mintcdn.com/syntblazellc/-L0ums_2lctDSZ1l/images/bite-sized-exercises.png?fit=max&auto=format&n=-L0ums_2lctDSZ1l&q=85&s=a65f9a38c37ff28ab73ed783c53c60e3" style={{ width: "30%", minWidth: 60 }} width="621" height="1344" data-path="images/bite-sized-exercises.png" />
</div>

<div style={{ display: "flex", gap: "12px", flexWrap: "wrap", marginTop: "12px" }}>
  <img src="https://mintcdn.com/syntblazellc/-L0ums_2lctDSZ1l/images/mastery-chain.png?fit=max&auto=format&n=-L0ums_2lctDSZ1l&q=85&s=748a1763454713e679260fbb95f154a2" style={{ width: "30%", minWidth: 60 }} width="621" height="1344" data-path="images/mastery-chain.png" />

  <img src="https://mintcdn.com/syntblazellc/-L0ums_2lctDSZ1l/images/element-previews.png?fit=max&auto=format&n=-L0ums_2lctDSZ1l&q=85&s=242f61448ff5dd6deaaab2dccc13b507" style={{ width: "30%", minWidth: 60 }} width="621" height="1344" data-path="images/element-previews.png" />

  <img src="https://mintcdn.com/syntblazellc/-L0ums_2lctDSZ1l/images/element-explanations.png?fit=max&auto=format&n=-L0ums_2lctDSZ1l&q=85&s=cf0fc1c31f9cd0fc26716781be05fbc9" style={{ width: "30%", minWidth: 60 }} width="621" height="1344" data-path="images/element-explanations.png" />
</div>
