> For the complete documentation index, see [llms.txt](https://docs.ecotone.tech/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.ecotone.tech/messaging/conversion/conversion/headers-conversion.md).

# Headers Conversion

Ecotone allows for serialization of Message Headers before they go the Message Channel (Queue).

## Scalar Headers

When we are sending Message Headers as simple scalar types like string or integer, then no Conversion is needed. In those situations Message Headers will be passed as they are.

```php
// execution
$commandBus->send(
   $command,
   metadata: [
      'executorId' => '1234'
   ]
)
```

This can be then accessed on the Message Handler level:

```php
#[Asynchronous('async')]
#[CommandHandler]
public function placeOrder(
   PlaceOrderCommand $command,
   #[Header('executorId')] string $executorId
)
{
   // do something
}
```

### Converting Scalars on the Message Endpoint

Even so if Header was sent as scalar, we still can convert it to Application specific object on the Message Handler level.

```php
#[Asynchronous('async')]
#[CommandHandler]
public function placeOrder(
   PlaceOrderCommand $command,
   #[Header('executorId')] ExecutorId $executorId
)
{
   // do something
}
```

For this we do need a Converter, which will state how given Class should be deserialized from **string** to **ExecutorId** object.

```php
class ExampleConverterService
{
    #[Converter] 
    public function convert(string $data) : ExecutorId
    {
        return ExecutorId::fromString($data);
    }
}
```

## Class Headers

We may actually want to pass Headers in more meaningful representation than simple scalars and let Ecotone do serialization when given Message goes to Message Channel (Queue).

```php
$commandBus->send(
   $command,
   metadata: [
      'executorId' => ExecutorId::fromString('1234')
   ]
)
```

For this we need Conversion from ExecutorId to string, for Ecotone to know how to serialize it before it will go to Asynchronous Channel.

```php
class ExampleConverterService
{
    #[Converter] 
    public function convert(ExecutorId $data) : string
    {
        return $data->toString();
    }
}
```

## Dealing with Collections

There may be cases, when simple PHP to PHP Conversion will not be enough.\
This may be for example, when we will be dealing with Collection of Classes.

```php
$commandBus->send(
   $command,
   metadata: [
      'types' => [
         OrderType::fromString('quick-delivery'),
         OrderType::fromString('promotion'),
      ]
   ]
)
```

In those cases Ecotone will fallback to serialize Message Header to JSON. This way we can serialize even most complex Headers.

Then on the receiving side:

```php
/**
* @param OrderType[] $types
*/
#[Asynchronous('async')]
#[CommandHandler]
public function placeOrder(
   PlaceOrderCommand $command,
   #[Header('types')] array $types
)
{
   // do something
}
```

Actually the Docblock is crucial here, as it tell Ecotone what Collection type we are dealing with. This way Ecotone will be able to pass is to your defined [Media Type Converter](/messaging/conversion/conversion.md#media-type-converter) to deserialize it.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.ecotone.tech/messaging/conversion/conversion/headers-conversion.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
