Skip to main content

API Guide

The example code in this document is available in the github.com/whatap/go-api-example repository.

Download

Download the package and the related dependencies.

go get github.com/whatap/go-api

Getting started

init, shutdown

Start the monitoring module by using the trace.Init() function. defer trace.Shutdown() makes sure that the monitoring ends.

Go
import "github.com/whatap/go-api/trace"


func main(){
trace.Init(nil)
//It must be executed before closing the app.
defer trace.Shutdown()

...
}

func Init(m map[string]string)

This can be set in the initial stage of the application by declaring it in the form of map[string]string. Otherwise, more settings can be added in whatap.conf. The performance information can be sent to the WhaTap collection server only when TCP connection to the agent is established normally. It performs TCP communication via 127.0.0.1:6600 using the basic connection information.

To change the connection information, pass the settings to the Init function, or set them in the whatap.conf file and then restart the application.

Go
m := make(map[string]string)
m["net_ipc_host"] = "127.0.0.1"
m["net_ipc_port"] = "6601"

trace.Init(m)
whatap.conf
accesskey={access key}
whatap.server.host={collection server IP}
net_ipc_host=127.0.0.1
net_ipc_host=6600

Context

The agents collect performance data based on the transaction. The transactions are classified based on the context to which whatap context(trace.TraceCtx) belongs. The performance data that is not related to transactions is ignored or collected only as statistical data.

Generating transactions

The whatap context is generated by the Start and StartWithReqest functions of the go-api/trace module. Set the TraceCtx data with the whatap key in the context.

Go
var traceCtx *TraceCtx
traceCtx.Txid = keygen.Next()
ctx = context.WithValue(ctx, "whatap", traceCtx)

In APIs for transactions, SQLs, DBConnections, external HTTP requests, and general function tracing, the Context in which the TraceCtx object exists as the whatap key is required at startup.

Transaction tracing

It traces all transactions from web requests to responses, and traces transactions for normal work units. It consists of the startup and end functions. It is recognized as a single transaction, and you can see the detailed views on the hitmap widget and the statistical metrics such as TPS, response time, and average response time.

You can collect HTTP parameters and HTTP headers through the settings.

Web transaction trace

Go
http.HandleFunc("/index", func(w http.ResponseWriter, r *http.Request) {
ctx, _ := trace.StartWithRequest(r)
defer trace.End(ctx, nil)
}
  • trace.Func(), trace.HandlerFunc()

    • Function that wraps Handle and HandFunc of the net/http

    • Proceed with trace.StartWithRequest and trace.End in the same way.

    • The name of the web transaction is set to RequestURI.

  • trace.Step()

    It provides the function to output the strings delivered by the user to the profile data.

    Go
    http.HandleFunc("/wrapHandleFunc", trace.Func(func(w http.ResponseWriter, r *http.Request) {
    ...
    }))
    Go
    http.Handle("/wrapHandleFunc1", trace.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
    ...
    }))

General transaction trace

Go
func main() {
...

ctx := context.Background()
ctx, _ := trace.Start(ctx, "Custom Transaction")

...

trace.End(ctx, nil)

...
}

API

Go
func Start(ctx context.Context, name string) (context.Context, error)
Go
func End(ctx context.Context, err error) error
Go
func StartWithRequest(r *http.Request) (context.Context, error)
Go
func Step(ctx context.Context, title, message string, elapsed, value int) error
Go
func HandlerFunc(handler func(http.ResponseWriter, *http.Request)) http.HandlerFunc
Go
func Func(handler func(http.ResponseWriter, *http.Request)) func(http.ResponseWriter, *http.Request)

DB connection and SQL tracing

Execution times and errors can be collected by passing parameters for DB connection, SQL syntax, errors, and prepared statements to the API. SQL statements can be collected up to 32 KB. The parameters for SQL prepared statements are collected up to 20 and up to 256 bytes for each.

DB Connection

Go
import (
whatapsql "github.com/whatap/go-api/sql"
)

func main(){
trace.Init(nil)
//It must be executed before closing the app.
defer trace.Shutdown()

ctx, _ := trace.Start(context.Background(), "Trace Open DB")
defer trace.End(ctx, nil)

sqlCtx, _ := whatapsql.StartOpen(ctx, "id@tcp(x.x.x.x:3306)/test")
db, err := sql.Open("mysql", "id:pwd@tcp(x.x.x.x:3306)/test")
whatapsql.End(sqlCtx, err)
defer db.Close()
}
Go
import (
whatapsql "github.com/whatap/go-api/sql"
)

func main(){
trace.Init(nil)
//It must be executed before closing the app.
defer trace.Shutdown()

ctx, _ := trace.Start(context.Background(), "Trace Query")
defer trace.End(ctx, nil)

query = "select id, subject from tbl_faq limit 10"
sqlCtx, _ = whatapsql.Start(ctx, "id:pwd@tcp(x.x.x.x:3306)/test", query)
rows, err := db.QueryContext(ctx, query)
whatapsql.End(sqlCtx, err)
}
Go
import (
whatapsql "github.com/whatap/go-api/sql"
)

func main(){
trace.Init(nil)
//It must be executed before closing the app.
defer trace.Shutdown()

ctx, _ := trace.Start(context.Background(), "Trace Prepared Statement")
defer trace.End(ctx, nil)

// Create Prepared Statement
query = "select id, subject from tbl_faq where id = ? limit ?"
stmt, err := db.Prepare(query)
if err != nil {
return
}
defer stmt.Close()

params := make([]interface{}, 0)
params = append(params, 8)
params = append(params, 1)

sqlCtx, _ := whatapsql.StartWithParamArray(ctx, "id:pwd(x.x.x.x:3306)/test", query, params)
rows, err := stmt.QueryContext(ctx, params...)
whatapsql.End(sqlCtx, err)


sqlCtx, _ = whatapsql.StartWithParam(ctx, "id:pwd(x.x.x.x:3306)/test", query, params...)
rows, err := stmt.QueryContext(ctx, params...)
whatapsql.End(sqlCtx, err)
}

Database/SQL package configuration

Use the whatapsql.OpenContext function instead of the sql.Open function of the database/sql package. It is recommended to use the functions that pass the contexts, such as PrepareContext, QueryContext, and ExecContext. The context to be delivered must have the whatap TraceCtx data through trace.Start().

Go

import (
_ "github.com/go-sql-driver/mysql"
"github.com/whatap/go-api/instrumentation/database/sql/whatapsql"
)

func main() {
config := make(map[string]string)
trace.Init(config)
defer trace.Shutdown()

// The whatap TraceCtx is generated inside whataphttp.Func.
http.HandleFunc("/query", whataphttp.Func(func(w http.ResponseWriter, r *http.Request){
ctx := r.Context()

// Use the WhaTap Driver. It passes the contexts that have TraceCtx.
db, err := whatapsql.OpenContext(ctx, "mysql", dataSource)
if err != nil {
fmt.Println("Error whatapsql.Open ", err)
return
}
defer db.Close()

...
query := "select id, subject from tbl_faq limit 10"

// It passes the contexts that have TraceCtx.
if rows, err := db.QueryContext(ctx, query); err == nil {
...
}
}
...
}

API

Go
func Start(ctx context.Context, dbhost, sql string) (*SqlCtx, error)
Go
func StartOpen(ctx context.Context, dbhost string) (*SqlCtx, error)
Go
func End(sqlCtx *SqlCtx, err error) error
Go
func StartWithParam(ctx context.Context, dbhost, sql, param ...interface{}) (*SqlCtx, error)
Go
func StartWithParamArray(ctx context.Context, dbhost, sql string, param []interface{}) (*SqlCtx, error)
Go
func Trace(ctx context.Context, dbhost, sql, param string, elapsed int, err error) error

Tracing the HTTP requests

Go
import (
"github.com/whatap/go-api/httc"
)

func main(){
trace.Init(nil)
//It must be executed before closing the app.
defer trace.Shutdown()

ctx, _ := trace.Start(context.Background(), "Trace Http Call")
defer trace.End(ctx, nil)

httpcCtx, _ := httpc.Start(ctx, callUrl)
resp, err := http.Get(callUrl)
if err == nil {
httpc.End(httpcCtx, resp.StatusCode, "", nil)
} else {
httpc.End(httpcCtx, 0, "", err)
}
}

http transport RoundTripper

You can set up the RoundTripper.

Go
import (
"github.com/whatap/go-api/instrumentation/net/http/whataphttp"
)
func main() {
config := make(map[string]string)
trace.Init(config)
defer trace.Shutdown()

ctx, _ := trace.Start(context.Background(), "Http call")
defer trace.End(ctx, nil)

callUrl := "http://aaa.com/xxx"
client := http.DefaultClient
// Use WhaTap RoundTripper. It passes the contexts that have TraceCtx.
client.Transport = whataphttp.NewRoundTrip(ctx, http.DefaultTransport)
resp, err := client.Get(callUrl)
if err != nil {
...
}
defer resp.Body.Close()

...

}

API

Go
func Start(ctx context.Context, url string) (*HttpcCtx, error)
Go
func End(httpcCtx *HttpcCtx, status int, reason string, err error) error
Go
func Trace(ctx context.Context, host string, port int, url string, elapsed int, status int, reason string, err error) error

Function tracing

This API measures the execution time of the user function or desired section. API can be set before or after execution of the function.

Go
import (
"github.com/whatap/go-api/method"
)
func main(){
trace.Init(nil)
//It must be executed before closing the app.
defer trace.Shutdown()

ctx, _ := trace.Start(context.Background(), "Trace Method")
defer trace.End(ctx, nil)

getUser(ctx)
}

func getUser(ctx context.Context) {
methodCtx, _ := method.Start(ctx, "getUser")
defer method.End(methodCtx, nil)
time.Sleep(time.Duration(1) * time.Second)
}

API

Go
func Start(ctx context.Context, name string) (*MethodCtx, error)
Go
func End(methodCtx *MethodCtx, err error) error
Go
func Trace(ctx context.Context, name string, elapsed int, err error) error