Flag of Ukraine
SymfonyCasts stands united with the people of Ukraine

Lucky you! You found an early release chapter - it will be fully polished and published shortly!

API Debugging with the Profiler

This Chapter isn't
quite ready...

Rest assured, the gnomes are hard at work
completing this video!

Browse Tutorials

We're going to be doing some seriously cool and complex stuff with API platform. So before we get there, I want to make sure we have a really awesome debugging setup. Because... sometimes debugging APIs can be a pain! Ever made an Ajax request from JavaScript... and the endpoint explodes in a 500 error full of HTML? Yea, not super helpful.

Installing the Profiler

One of the best features of Symfony is its Web Debug Toolbar. But if we're building an API... there's not going to be a Web Debug Toolbar on the bottom of these JSON responses. So should we even bother installing that package? The answer is: absolutely!

Spin over to the terminal and run:

composer require debug

This is another Symfony Flex pack that installs symfony/debug-pack. If you pop over to your composer.json file, this installed a bunch of good stuff: a logger... then down in require-dev, it also added MakerBundle, DebugBundle, and WebProfilerBundle, which is the most important thing for what we'll talk about.

AJAX Requests in the Web Debug Toolbar

Head back to our documentation homepage and refresh. Sweet! We get the Web Debug Toolbar down on the bottom! Though... that doesn't really help us because... all of this info is literally for the documentation page itself. Not particularly useful.

What we really want is all of this profiler info for any API request we make. And that's super possible. Use the GET collection endpoint. Hit "Try it out" and then watch closely down here on the Web Debug Toolbar. When I hit "Execute"... boom! Because that made an AJAX request the AJAX icon on the Web Debug Toolbar showed up! Want to see all the deep profiler info for that request? Just click the little link on that panel. Yup, as you can see here, we're now looking at the profiler for the GET /api/dragon_treasures API call.

API Platform & Serializer in the Profiler

And there's lots of cool stuff in here. Obviously, there's the Performance section and all the normal goodies. But one of my favorite parts is the "Exception" tab. If you have an API endpoint and that API endpoint explodes with an error - it happens - you can open this part of the profiler to see the full beautiful HTML exception: including the stack trace in all its glory. So handy.

I have two other favorite spots when working on an API. The first, no surprise, is the "API Platform" tab. This gives us info about the configuration for all of our API resources. We're going to talk more about this config, but this shows you the current and possible options that you could put inside of this ApiResource attribute. That's pretty cool. For example, this shows a description option... and we already have that!

The other really useful section in the profiler is relatively new: it's for the "Serializer". We're going to be talking a lot about Symfony's serializer and this tool will help us get a look at what's going on internally.

Finding the Profiler for an API Request

So the big takeaway is that every API request actually has a profiler! And there are a few ways to find it. We just say the first: if you're making an AJAX request - even if it's via your own JavaScript - then you can use the web debug toolbar.

And, if you look down here a bit, these are the response headers our API returned. One is called X-Debug-Token-Link which offers us a second way to find the profiler for any API request. This is exactly the URL we were just at.

The last way is... maybe the simplest. Suppose we go directly to /api/dragon_treasure.json. From here, there's no easy way to get to the profiler. But now, open up a new tab and manually go to /_profiler. Yup! This shows us a list of the latest request to our app... include the GET request we just made! If you click the little token link... boom! We're inside that profiler.

You can click this "Last 10" at any point to get back to that list... and find whichever request you need.

Sweet debugging tools, check! Next: let's talk about the concept of "operations" in API platform, which represent these six endpoints. How can we configure these? Or disable one? Or add more? Let's find out!

Leave a comment!

0
Login or Register to join the conversation
Cat in space

"Houston: no signs of life"
Start the conversation!

What PHP libraries does this tutorial use?

// composer.json
{
    "require": {
        "php": ">=8.1",
        "ext-ctype": "*",
        "ext-iconv": "*",
        "api-platform/core": "^3.0", // v3.0.8
        "doctrine/annotations": "^1.0", // 1.14.2
        "doctrine/doctrine-bundle": "^2.8", // 2.8.0
        "doctrine/doctrine-migrations-bundle": "^3.2", // 3.2.2
        "doctrine/orm": "^2.14", // 2.14.0
        "nelmio/cors-bundle": "^2.2", // 2.2.0
        "nesbot/carbon": "^2.64", // 2.64.1
        "phpdocumentor/reflection-docblock": "^5.3", // 5.3.0
        "phpstan/phpdoc-parser": "^1.15", // 1.15.3
        "symfony/asset": "6.2.*", // v6.2.0
        "symfony/console": "6.2.*", // v6.2.3
        "symfony/dotenv": "6.2.*", // v6.2.0
        "symfony/expression-language": "6.2.*", // v6.2.2
        "symfony/flex": "^2", // v2.2.4
        "symfony/framework-bundle": "6.2.*", // v6.2.3
        "symfony/property-access": "6.2.*", // v6.2.3
        "symfony/property-info": "6.2.*", // v6.2.3
        "symfony/runtime": "6.2.*", // v6.2.0
        "symfony/security-bundle": "6.2.*", // v6.2.3
        "symfony/serializer": "6.2.*", // v6.2.3
        "symfony/twig-bundle": "6.2.*", // v6.2.3
        "symfony/ux-react": "^2.6", // v2.6.1
        "symfony/validator": "6.2.*", // v6.2.3
        "symfony/webpack-encore-bundle": "^1.16", // v1.16.0
        "symfony/yaml": "6.2.*" // v6.2.2
    },
    "require-dev": {
        "doctrine/doctrine-fixtures-bundle": "^3.4", // 3.4.2
        "symfony/debug-bundle": "6.2.*", // v6.2.1
        "symfony/maker-bundle": "^1.48", // v1.48.0
        "symfony/monolog-bundle": "^3.0", // v3.8.0
        "symfony/stopwatch": "6.2.*", // v6.2.0
        "symfony/web-profiler-bundle": "6.2.*", // v6.2.4
        "zenstruck/foundry": "^1.26" // v1.26.0
    }
}