5. blackfire.io @blackfireio # blackfireio
Understanding the overhead
● Instrumentation
● Tools ready for production vs tools made for
development only
● Instrumenting all requests vs specific requests
6. blackfire.io @blackfireio # blackfireio
Profiling is about measuring how much
resources your code is consuming
Wall time I/O CPU
Memory Network SQLHTTP Time
https://blackfire.io/docs/24-days/07-time-flavors
7. blackfire.io @blackfireio # blackfireio
Time is volatile
● Time is not a stable metric. External factors such as machine load can
have significant impacts on wall time between two profiles of identical
code.
● Time is just a consequence of what happened in the code
● Use time to identify the slow parts in your code and then:
○ iterate and compare
○ write assertions on the root cause
● Profiling is about understanding how code works at runtime
https://blackfire.io/docs/24-days/12-tests-best-pratices
8. blackfire.io @blackfireio # blackfireio
Callgraphs, timelines and more
● Find the function calls that
consume the most resources
● Know where to stop optimizing
● Trade-off time vs memory and
performance vs code complexity
● Profiling should not always be a
lonely activity
15. blackfire.io @blackfireio # blackfireio
The main issues
● SQL Queries
● Network
● CPU Time
● Memory
● I/O Wait
● External HTTP requests
● PHP & Bad PHP code
16. blackfire.io @blackfireio # blackfireio
SQL Queries
● Use indexes and correct types.
● Limit the number of results you need.
● Avoid SQL requests…
● If you can’t avoid them, cache the output or
use LocalStorage/CacheStorage if insensitive information.
● Use Magento Repositories.
SQL Requests are the main issue.
18. blackfire.io @blackfireio # blackfireio
CPU Time
● Avoid consuming operations: loops, events…
● Use Magento Repositories.
● KISS : Keep It Simple Stupid.
19. blackfire.io @blackfireio # blackfireio
Memory
● Use the MagentoFrameworkModelResourceModelIterator for your
loops.
● Use PHP! Avoid creating so many objects when you can do the
operation with one function call.
● Use the Magento Dependency Injection.
● Use Magento Repositories.
20. blackfire.io @blackfireio # blackfireio
I/O Wait
● Use php://memory and php://temp. Because Memory is always faster
than I/O.
● Optimize composer: composer dump-autoload --optimize --no-dev
21. blackfire.io @blackfireio # blackfireio
External HTTP Requests
● Don’t do that.
● If you really have to: use RabbitMQ.
● And if you really have no choice: use asynchronous?
● And if you really really have no choice: use a small timeout and deal with
the errors properly.
23. blackfire.io @blackfireio # blackfireio
PHP & Bad PHP code
● Upgrade to the latest version of PHP.
● Prefer a PHP core function to a lot of objects and methods.
●
25. blackfire.io @blackfireio # blackfireio
The metrics
● Is Magento 2 installed? CE or EE?
● Is the cache enabled?
● Cache manipulation.
● Product loads.
● Interceptors measurement.
● Mode detector: production/developer/default.
● …
26. blackfire.io @blackfireio # blackfireio
The metrics
magento2.all.cache.full_page.builtin.hit:
label: "Hit full page cache using builtin"
matching_calls:
php:
- callee: "=Magento[…]BuiltinPlugin::addDebugHeader"
caller: "=Magento[…]BuiltinPlugin::aroundDispatch"
27. blackfire.io @blackfireio # blackfireio
The metrics
mymetrics.image.operation:
matching_calls:
php:
- callee: "/.*image.*/"
Will match imagecreate, getimagesize etc.
28. blackfire.io @blackfireio # blackfireio
The recommendations
'The Magento 2 Full Page Cache should be enabled':
assertions:
- 'metrics.magento2.[…]full_page.builtin.hit.count == 1'
exclude:
- '.*/checkout.*'
- '.*/customer/section/load'
- '.*/catalogsearch'
[…]
29. blackfire.io @blackfireio # blackfireio
The recommendations
'Do not make any image operation':
assertions:
- 'metrics.mymetrics.image.operation.count == 0'
30. blackfire.io @blackfireio # blackfireio
Put some limits: .blackfire.yml
tests:
Pages should be fast enough:
path: /.*
assertions:
- main.wall_time < 850ms
- main.io < 500ms
- main.cpu_time < 500ms
Pages should not consume too much memory:
path: /.*
assertions:
- main.memory < 50M
- main.peak_memory < 75M
Homepage should not do too many SQL queries:
path: /
assertions:
- metrics.sql.queries.count <= 12
Checkout pages should be light:
path: /checkout/.*
assertions:
- metrics.output.network_out < 100KB