# Writing Scenarios

[Requires Production Plan](https://www.blackfire.io/pricing)

> **Warning**
>
> **Deprecation notice:** Blackfire-hosted Synthetic Monitoring — including periodic builds, webhook-triggered builds, and native integrations — is deprecated and removed since **May 30, 2026**.
>
> Migrate to [Blackfire Player](synthetic-monitoring)with `--report` to run Synthetic Monitoring from your own infrastructure, with full control over scheduling and secret management.

Blackfire scenarios provide a powerful way to test your application **regularly**, like when you deploy your code on a staging environment or in production, or when you create a pull-request to add a new feature or fix a bug. The idea is to assess the performance of your code and to check its behavior.

## Scenarios

Like [Blackfire tests](../testing-cookbooks/tests), scenarios are defined in the `.blackfire.yaml` file:

```text
scenarios: |
    #!blackfire-player

    scenario
        name 'Visitor'

        visit url('/pricing')
            name 'Pricing page'

        visit url('/docs/introduction')
            name 'Documentation'

    scenario
        name 'Authentication'

        set user_login "my_login"
        set user_password "my_password"

        visit url('/login')
            name 'Login page'

        submit button('Log in')
            name 'Submit log in form'
            param _username user_login
            param _password user_password

        follow
            name 'Login redirection'
            expect current_url() == endpoint ~ '/'
            expect body() matches '/Welcome ' ~ user_login ~ '/'
```

The scenarios are run by the [Blackfire Player](player). It provides a nice DSL to crawl HTTP services, assert responses, and extract data from HTML/XML/JSON responses.

> **Note**
>
> Validate your `.blackfire.yaml` file or test files ending with `.bkf` via the Blackfire [online validator](https://blackfire.io/validator).

- **[Crawling an HTTP application](player#crawling-an-http-application)**

    - **[Making Requests](player#making-requests)**

        - [Visiting a Page with 'visit'](player#visiting-a-page-with-visit)
        - [Clicking on a Link with 'click'](player#clicking-on-a-link-with-click)
        - [Submitting Forms with 'submit'](player#submitting-forms-with-submit)
        - [Following Redirections](player#following-redirections)
        - [Embedding Scenarios with 'include'](player#embedding-scenarios-with-include)
    - **[Configuring the Request](player#configuring-the-request)**

        - [Setting a Header with 'header'](player#setting-a-header-with-header)
        - [Setting a User and Password with 'auth'](player#setting-a-user-and-password-with-auth)
        - [Waiting after sending the request with 'wait'](player#waiting-after-sending-the-request-with-wait)
        - [Sending a JSON Body with 'json'](player#sending-a-json-body-with-json)
        - [Setting Options for all Steps](player#setting-options-for-all-steps)
- [Writing Expectations](player#writing-expectations)
- [Using Variables](player#using-variables)
- [Writing Blackfire Assertions](../integrations/blackfire-player#writing-blackfire-assertions)
- [Scraping Values](player#scraping-values)

> **Note**
>
> Don't forget the `|` (pipe) at the end of the `scenarios: |` line to start a multiline string.
>
> Please also note that the Player script must start with `#!blackfire-player`
