WEBVTT

NOTE Created by CaptionSync from Automatic Sync Technologies www.automaticsync.com

00:00:01.036 --> 00:00:03.746 align:middle
Let's profile the Github API endpoint again.

00:00:04.566 --> 00:00:09.386 align:middle
I'll cheat and go directly to
/api/github-organization...

00:00:09.816 --> 00:00:11.466 align:middle
and click to profile this.

00:00:13.176 --> 00:00:20.376 align:middle
I'll call it: [Recording] GitHub Ajax HTTP
requests because we're going to look closer

00:00:20.376 --> 00:00:24.886 align:middle
at the HTTP requests that our
app makes to the GitHub API.

00:00:28.376 --> 00:00:34.236 align:middle
Click to view the call graph:
https://bit.ly/sf-bf-http-requests Oh wow -

00:00:34.236 --> 00:00:40.846 align:middle
this request was super slow - 1.83 seconds
- a lot slower than we've seen before.

00:00:41.706 --> 00:00:47.606 align:middle
We can see that curl_multi_select() is the
problem: this is our code making requests

00:00:47.686 --> 00:00:52.826 align:middle
to the GitHub API, which is apparently
running a bit slow at the moment.

00:00:53.696 --> 00:00:57.596 align:middle
Lucky for us, that's exactly
what I wanted to talk about!

00:00:58.316 --> 00:01:04.316 align:middle
At the top, Blackfire tells me that
this page made two HTTP requests.

00:01:04.486 --> 00:01:08.526 align:middle
And HTTP requests are always
expensive for performance.

00:01:08.526 --> 00:01:15.586 align:middle
If you studied the data from the two API
endpoints that we're using, you would discover

00:01:15.586 --> 00:01:19.656 align:middle
that it's possible - by writing
some clever code -

00:01:19.916 --> 00:01:25.806 align:middle
to get all the info our app
needs with just one HTTP request.

00:01:26.766 --> 00:01:33.616 align:middle
What I'm saying is: our page is making one
more HTTP request than it truly needs to.

00:01:34.426 --> 00:01:35.986 align:middle
If you think about it...

00:01:36.136 --> 00:01:43.846 align:middle
that's kind of a performance "bug": we're
making 2 HTTP requests and we only need 1.

00:01:44.766 --> 00:01:50.356 align:middle
In an ideal world, when we find a bug,
the process for fixing it looks like this.

00:01:50.356 --> 00:01:54.586 align:middle
First, write a test for the expected behavior.

00:01:55.276 --> 00:01:58.216 align:middle
Second, run that test and watch it fail.

00:01:58.756 --> 00:02:02.636 align:middle
And third, fix the bug and
make sure the test passes.

00:02:03.816 --> 00:02:06.366 align:middle
Whelp, when it comes to a performance bug...

00:02:06.666 --> 00:02:09.986 align:middle
we can do the exact same thing!

00:02:10.656 --> 00:02:18.636 align:middle
We can write a functional test that asserts
that this endpoint only makes one HTTP request.

00:02:19.326 --> 00:02:20.996 align:middle
It's... pretty awesome.

00:02:20.996 --> 00:02:27.476 align:middle
Find your editor and open
tests/ ontroller/MainControllerTest.php.

00:02:27.476 --> 00:02:33.246 align:middle
I already set up a functional test that
makes a request to /api/github-organization

00:02:33.606 --> 00:02:36.356 align:middle
and checks some basic data on the response.

00:02:37.346 --> 00:02:39.376 align:middle
Let's makes sure this passes.

00:02:40.036 --> 00:02:43.016 align:middle
Run PHPUnit and point it directly at this class:

00:02:43.016 --> 00:02:50.616 align:middle
php bin/phpunit
tests/Controller/MainControlerTest.php The first

00:02:50.616 --> 00:02:55.166 align:middle
time you run this script, it will probably
download PHPUnit in the background.

00:02:56.316 --> 00:02:57.526 align:middle
When it finishes...

00:02:58.196 --> 00:02:59.296 align:middle
go tests go!

00:02:59.826 --> 00:03:00.796 align:middle
All green.

00:03:01.816 --> 00:03:07.706 align:middle
Here's the idea: in addition to
asserting that this response contains JSON

00:03:07.836 --> 00:03:15.346 align:middle
with an organization key, I also want to
assert that it only made one HTTP request.

00:03:16.196 --> 00:03:22.046 align:middle
To do that, first add a trait
from the SDK: use TestCaseTrait.

00:03:24.236 --> 00:03:29.176 align:middle
Next, in the method, add
$blackfireConfig = new Configuration() -

00:03:30.316 --> 00:03:37.486 align:middle
the one from Blackfire\Profile: the
same Configuration class we used earlier

00:03:37.726 --> 00:03:41.316 align:middle
when we gave our custom-created profile a title.

00:03:42.116 --> 00:03:46.106 align:middle
This time call assert() and
pass it a very special string:

00:03:46.896 --> 00:03:53.296 align:middle
metrics.http.requests.count == 1.

00:03:54.776 --> 00:03:57.016 align:middle
I'll show you where that came from soon.

00:03:57.016 --> 00:04:02.656 align:middle
Finally, below this, call
$this-&gt;assertBlackfire()

00:04:02.806 --> 00:04:06.766 align:middle
and pass this $blackfireConfig
and a callback function.

00:04:07.936 --> 00:04:10.896 align:middle
So... this confused me at first.

00:04:11.476 --> 00:04:16.636 align:middle
When we call $this-&gt;assertBlackfire()
it will execute this callback.

00:04:17.456 --> 00:04:22.626 align:middle
Inside, we will do whatever work
we want - like making the request.

00:04:22.726 --> 00:04:26.256 align:middle
Finally, when the callback finishes,

00:04:26.636 --> 00:04:31.556 align:middle
Blackfire will execute this assertion
against the code that we ran.

00:04:32.426 --> 00:04:35.396 align:middle
To get this to work, we need to use ($client).

00:04:36.236 --> 00:04:37.986 align:middle
If this doesn't make sense yet...

00:04:38.126 --> 00:04:40.836 align:middle
don't worry: we'll dive a bit deeper soon.

00:04:40.836 --> 00:04:42.156 align:middle
But right now...

00:04:42.536 --> 00:04:47.746 align:middle
try it! Run the test again: And...

00:04:48.006 --> 00:04:49.716 align:middle
it fails! Woo!

00:04:49.926 --> 00:04:55.756 align:middle
Failed that metrics.http.requests.count == 1!

00:04:57.076 --> 00:05:03.576 align:middle
Behind the scenes, the Blackfire SDK created
a real Blackfire profile for the request!

00:05:04.446 --> 00:05:08.176 align:middle
You can even copy the profile
URL and go check it out!

00:05:12.876 --> 00:05:15.616 align:middle
This takes us to an "assertions" tab.

00:05:16.796 --> 00:05:20.026 align:middle
We're making 2 requests instead
of the expected one.

00:05:20.616 --> 00:05:23.026 align:middle
We'll talk a lot more about assertions soon.

00:05:23.886 --> 00:05:26.816 align:middle
Ok, but how did this really work?

00:05:27.566 --> 00:05:29.246 align:middle
It's beautifully simple.

00:05:29.766 --> 00:05:34.946 align:middle
When you run the test, it does make a
real Blackfire profile in the background.

00:05:35.476 --> 00:05:40.116 align:middle
However, if you go to your
Blackfire homepage, you won't see it.

00:05:40.846 --> 00:05:45.586 align:middle
Why? Hold Command or Ctrl and
click the assertBlackfire() method.

00:05:46.646 --> 00:05:51.936 align:middle
I love it: this method uses
the SDK - just like we did!

00:05:52.226 --> 00:05:54.186 align:middle
- to create a real profile.

00:05:55.176 --> 00:06:01.676 align:middle
When it does that, it also adds a skip_timeline
option, which simply tells Blackfire

00:06:01.676 --> 00:06:04.196 align:middle
to hide this from our profile page...

00:06:04.516 --> 00:06:08.206 align:middle
so it doesn't get cluttered up
with all these test profiles.

00:06:09.586 --> 00:06:12.166 align:middle
You can totally override that if you wanted...

00:06:12.426 --> 00:06:14.516 align:middle
via the Configuration object.

00:06:15.806 --> 00:06:21.966 align:middle
In reality, the Blackfire PHPUnit
integration is doing the exact same thing

00:06:21.966 --> 00:06:27.846 align:middle
that we just finished doing in our
code: manually creating a new profile.

00:06:28.836 --> 00:06:31.096 align:middle
This is really nothing new...

00:06:31.346 --> 00:06:32.856 align:middle
and I love that!

00:06:34.086 --> 00:06:36.476 align:middle
Except... for this metrics thing.

00:06:37.146 --> 00:06:38.756 align:middle
Where did that string come from?

00:06:39.186 --> 00:06:41.186 align:middle
And what else can we do here?

00:06:42.046 --> 00:06:43.996 align:middle
Let's dive into metrics next.

