# Statement digests

> MySQL 8.0 gives no digest to native prepared statements, which is what Laravel sends by default.

Source: https://boring-observability.dev/sailfish/docs/statement-digests
Section: Using Sailfish — Sailfish documentation
Updated: 2026-10-02

---

MySQL 8.0 gives **no digest** to statements sent through the binary prepared-statement protocol (`COM_STMT_EXECUTE`). They never appear in `events_statements_summary_by_digest`. Laravel's MySQL connection uses native prepared statements by default (`PDO::ATTR_EMULATE_PREPARES => false`), so an application on the defaults only gets digests for the few unprepared statements it sends: `SET NAMES`, `START TRANSACTION`, `COMMIT` and so on.

## What it affects

Only the statement digests. Index and table counters are **not** affected: they see every statement either way, so index status, table scans and every [event](https://boring-observability.dev/sailfish/docs/events) work on the defaults.

## The fix

For digests of your application's queries, enable emulated prepares on the connection:

```php
// config/database.php, connections.mysql: add to whatever `options` it already has
'options' => [
    PDO::ATTR_EMULATE_PREPARES => true,
],
```

PDO then interpolates bindings client-side and sends plain text, which also saves the prepare and close round trips on every query.

Sailfish's own test suite pins this MySQL behaviour, so a MySQL release that changes it will show up there and in these docs.


## Common questions

### Does turning on emulated prepares make Laravel less safe?

No. PDO still escapes every binding, it just does it client-side and sends the finished statement as text. That also saves the prepare and close round trips on every query.
