From 3e1e8fd8f6404366a563b588866321f8971b21f2 Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Mon, 6 May 2024 21:23:22 -0400 Subject: [PATCH 1/8] Iterate on REAMDE --- README.md | 20 +++++++++++++------- 1 file changed, 13 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 99be61c..69fb9ec 100644 --- a/README.md +++ b/README.md @@ -16,7 +16,7 @@ Then run `npm install -g speedscope` ## Usage -Simplest is calling with a block: +The simplest way is to wrap your code with a block ```ruby flamegraph { @@ -30,7 +30,7 @@ Flamegraphs are saved for later review to `Singed.output_directory`, which is `t Singed.output_directory = "tmp/slowness-exploration" ``` -### Blockage +#### Block form If you are calling it in a loop, or with different variations, you can include a label on the filename: ```ruby @@ -39,7 +39,7 @@ flamegraph("rspec") { } ``` -You can also skip opening speedscope automatically: +You can also skip opening speedscope in a browser automatically: ```ruby flamegraph(open: false) { @@ -47,7 +47,7 @@ flamegraph(open: false) { } ``` -### RSpec +#### RSpec If you are using RSpec, you can use the `flamegraph` metadata to capture it for you. @@ -62,7 +62,7 @@ RSpec.describe YourClass do end ``` -### Controllers +#### Controllers If you want to capture a flamegraph of a controller action, you can call it like: @@ -78,7 +78,7 @@ end This won't catch the entire request though, just once it's been routed to controller and a response has been served (ie no middleware). -### Rack/Rails requests +#### Rack/Rails requests To capture the whole request, there is a middleware which checks for the `X-Singed` header to be 'true'. With curl, you can do this like: @@ -90,7 +90,7 @@ PROTIP: use Chrome Developer Tools to record network activity, and copy requests This can also be enabled to always run by setting `SINGED_MIDDLEWARE_ALWAYS_CAPTURE=1` in the environment. -### Command Line +#### Command Line There is a `singed` command line you can use that will record a flamegraph from the entirety of a command run: @@ -101,6 +101,12 @@ $ bundle exec singed -- bin/rails runner 'Model.all.to_a' The flamegraph is opened afterwards. +## How to read a flamegraph + +You've generated a flamegraph, now what? That's a great question. Here's some resources for getting started: + +- [technicalpickles/flamegraph-lighting-talk](https://github.com/technicalpickles/flamegraph-lighting-talk) +- [Pairin' with Aaron: Flamegraphs and App Performance - YouTube](https://www.youtube.com/watch?v=9nvX3OHykGQ) ## Limitations From 4c7fb2a830d8f1e6f5fafb5f26a18fa8c595f391 Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Mon, 6 May 2024 21:35:46 -0400 Subject: [PATCH 2/8] Add options. adjust header levels --- README.md | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 69fb9ec..e603242 100644 --- a/README.md +++ b/README.md @@ -30,7 +30,7 @@ Flamegraphs are saved for later review to `Singed.output_directory`, which is `t Singed.output_directory = "tmp/slowness-exploration" ``` -#### Block form +### Block form If you are calling it in a loop, or with different variations, you can include a label on the filename: ```ruby @@ -47,9 +47,22 @@ flamegraph(open: false) { } ``` +##### Options + +`flamegraph` takes some of the options that [stackprof]() does: + +- `ignore_gc: true`: if your profiled code is very memory heavy, the garbage collection can make it harder to read. ignoring gc can make it more readable, but it's also a sign to use [memory_profiler](https://github.com/SamSaffron/memory_profiler). +- `interval: 1000` (in ms): how frequently to sample. for very small + +Plus some of its own: + +- `label: "your-description"`: a label to include in the filename +- `open: false`: don't try to `open` the flamegraph in a browser +- `io: File.open("your-output")` where to write the output, defaults to `$stdout` + #### RSpec -If you are using RSpec, you can use the `flamegraph` metadata to capture it for you. +If you are using RSpec, you can use the `flamegraph` metadata to capture it for you. This [RSpec::Core::Hooks#around](https://rubydoc.info/gems/rspec-core/RSpec%2FCore%2FHooks:around), so focuses only on code inside the example block. ```ruby # make sure this is required at somepoint, like in a spec/support file! @@ -76,7 +89,7 @@ class EmployeesController < ApplicationController end ``` -This won't catch the entire request though, just once it's been routed to controller and a response has been served (ie no middleware). +This won't catch the entire request though, _just once it's been routed to controller and a response has been served_ (ie no middleware). #### Rack/Rails requests From 485cb495bc46a5f30fa4e0cda8292008277a4986 Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Mon, 6 May 2024 21:38:06 -0400 Subject: [PATCH 3/8] Add badges --- README.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/README.md b/README.md index e603242..fc853a2 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,9 @@ # Singed + +[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/build.yml/badge.svg?event=push) + + Singed makes it easy to get a flamegraph anywhere in your code base. It wraps profiling your code with [stackprof](https://github.com/tmm1/stackprof) or [rbspy](https://github.com/rbspy/rbspy), and then launching [speedscope](https://github.com/jlfwong/speedscope) to view it. ## Installation From e8cdcfc36f2d8c4b0092bc44d7cd9d0dd4eb30fa Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Tue, 7 May 2024 09:40:36 -0400 Subject: [PATCH 4/8] add a note about why --- README.md | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/README.md b/README.md index fc853a2..812d942 100644 --- a/README.md +++ b/README.md @@ -6,6 +6,11 @@ Singed makes it easy to get a flamegraph anywhere in your code base. It wraps profiling your code with [stackprof](https://github.com/tmm1/stackprof) or [rbspy](https://github.com/rbspy/rbspy), and then launching [speedscope](https://github.com/jlfwong/speedscope) to view it. +But why would you want to do this? At least a couple of reasons: + +- you have code that you either feel, think, or KNOW is slow +- you are curious about how some code actually runs + ## Installation Add to `Gemfile`: From 13d4d19b027130f4dde4f24f9a07fd46bd510587 Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Tue, 7 May 2024 09:41:38 -0400 Subject: [PATCH 5/8] Add standard --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 812d942..94ebdc7 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Singed -[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/build.yml/badge.svg?event=push) +[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/build.yml/badge.svg?event=push) | ![Standard](https://github.com/rubyatscale/singed/actions/workflows/standardrb.yml/badge.svg?event=push) Singed makes it easy to get a flamegraph anywhere in your code base. It wraps profiling your code with [stackprof](https://github.com/tmm1/stackprof) or [rbspy](https://github.com/rbspy/rbspy), and then launching [speedscope](https://github.com/jlfwong/speedscope) to view it. From b428d100c084afa306f87e609aecec0381ce1fe7 Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Tue, 7 May 2024 09:44:17 -0400 Subject: [PATCH 6/8] fix badge --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 94ebdc7..067a05c 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Singed -[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/build.yml/badge.svg?event=push) | ![Standard](https://github.com/rubyatscale/singed/actions/workflows/standardrb.yml/badge.svg?event=push) +[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/build.yml/badge.svg?event=push) | ![Standard](https://github.com/rubyatscale/singed/actions/workflows/standardrb.yaml/badge.svg?event=push) Singed makes it easy to get a flamegraph anywhere in your code base. It wraps profiling your code with [stackprof](https://github.com/tmm1/stackprof) or [rbspy](https://github.com/rbspy/rbspy), and then launching [speedscope](https://github.com/jlfwong/speedscope) to view it. From c9eda57f2810e2a2eb49c71d53db4772436f9063 Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Tue, 7 May 2024 09:48:37 -0400 Subject: [PATCH 7/8] Rename workflow files, set name, etc --- .github/workflows/{build.yml => specs.yaml} | 2 +- .github/workflows/{standardrb.yaml => standard.yaml} | 0 README.md | 2 +- 3 files changed, 2 insertions(+), 2 deletions(-) rename .github/workflows/{build.yml => specs.yaml} (98%) rename .github/workflows/{standardrb.yaml => standard.yaml} (100%) diff --git a/.github/workflows/build.yml b/.github/workflows/specs.yaml similarity index 98% rename from .github/workflows/build.yml rename to .github/workflows/specs.yaml index 6c409d7..a359244 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/specs.yaml @@ -1,4 +1,4 @@ -name: CI Test +name: Specs on: [ push ] jobs: build: diff --git a/.github/workflows/standardrb.yaml b/.github/workflows/standard.yaml similarity index 100% rename from .github/workflows/standardrb.yaml rename to .github/workflows/standard.yaml diff --git a/README.md b/README.md index 067a05c..9e2ad67 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Singed -[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/build.yml/badge.svg?event=push) | ![Standard](https://github.com/rubyatscale/singed/actions/workflows/standardrb.yaml/badge.svg?event=push) +[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/specs.yaml/badge.svg?event=push) | ![Lint](https://github.com/rubyatscale/singed/actions/workflows/standard.yaml/badge.svg?event=push) Singed makes it easy to get a flamegraph anywhere in your code base. It wraps profiling your code with [stackprof](https://github.com/tmm1/stackprof) or [rbspy](https://github.com/rbspy/rbspy), and then launching [speedscope](https://github.com/jlfwong/speedscope) to view it. From e5b681a34eed837d2eb07d0cb7c083e1097bffba Mon Sep 17 00:00:00 2001 From: Josh Nichols Date: Tue, 7 May 2024 09:51:33 -0400 Subject: [PATCH 8/8] remove pipe --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 9e2ad67..8440bbc 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Singed -[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) | ![CI](https://github.com/rubyatscale/singed/actions/workflows/specs.yaml/badge.svg?event=push) | ![Lint](https://github.com/rubyatscale/singed/actions/workflows/standard.yaml/badge.svg?event=push) +[![Gem Version](https://badge.fury.io/rb/singed.svg)](https://badge.fury.io/rb/singed) ![CI](https://github.com/rubyatscale/singed/actions/workflows/specs.yaml/badge.svg?event=push) ![Lint](https://github.com/rubyatscale/singed/actions/workflows/standard.yaml/badge.svg?event=push) Singed makes it easy to get a flamegraph anywhere in your code base. It wraps profiling your code with [stackprof](https://github.com/tmm1/stackprof) or [rbspy](https://github.com/rbspy/rbspy), and then launching [speedscope](https://github.com/jlfwong/speedscope) to view it.