wit-debian-gui/pprof.go

82 lines
1.8 KiB
Go

package main
// run this and then hit:
// http://localhost:6060/debug/pprof/
//
// Also run from the command line:
// go tool pprof 'localhost:6060/debug/pprof/wit_pprof_experiment_thing?debug=1'
//
// https://medium.com/@cep21/creating-custom-go-profiles-with-pprof-b737dfc58e11
import "fmt"
import "log"
import "net/http"
import _ "net/http/pprof" // the _ means only the init() is needed
import "os"
import "runtime/pprof"
import "sync/atomic"
import "time"
var libProfile *pprof.Profile
func init() {
profName := "wit_pprof_experiment_thing" // this ends up in the URL
libProfile = pprof.Lookup(profName)
if libProfile == nil {
libProfile = pprof.NewProfile(profName)
}
}
type someResource struct {
*os.File
}
var fileIndex = int64(0)
func MustResource() *someResource {
f, err := os.Create(fmt.Sprintf("/tmp/%d.txt", atomic.AddInt64(&fileIndex, 1)))
if err != nil {
panic(err)
}
r := &someResource{f}
libProfile.Add(r, 1)
return r
}
func (r *someResource) Close() error {
libProfile.Remove(r)
return r.File.Close()
}
func trackAFunction() {
tracked := new(byte)
libProfile.Add(tracked, 1)
defer libProfile.Remove(tracked)
time.Sleep(time.Second)
}
func usesAResource() {
res := MustResource()
defer res.Close()
for i := 0; i < 10; i++ {
time.Sleep(time.Second)
}
}
func pprofMain() {
http.HandleFunc("/nonblock", func(rw http.ResponseWriter, req *http.Request) {
go usesAResource()
})
http.HandleFunc("/functiontrack", func(rw http.ResponseWriter, req *http.Request) {
trackAFunction()
})
http.HandleFunc("/block", func(rw http.ResponseWriter, req *http.Request) {
usesAResource()
})
log.Println("run this and then hit:")
log.Println("http://localhost:6061/debug/pprof/")
log.Println("")
log.Println("Running!")
log.Println(http.ListenAndServe("localhost:6061", nil))
}