package cloudflare import ( "context" "fmt" "net/http" "github.com/goccy/go-json" ) // DiagnosticsTracerouteConfiguration is the overarching structure of the // diagnostics traceroute requests. type DiagnosticsTracerouteConfiguration struct { Targets []string `json:"targets"` Colos []string `json:"colos,omitempty"` Options DiagnosticsTracerouteConfigurationOptions `json:"options,omitempty"` } // DiagnosticsTracerouteConfigurationOptions contains the options for performing // traceroutes. type DiagnosticsTracerouteConfigurationOptions struct { PacketsPerTTL int `json:"packets_per_ttl"` PacketType string `json:"packet_type"` MaxTTL int `json:"max_ttl"` WaitTime int `json:"wait_time"` } // DiagnosticsTracerouteResponse is the outer response of the API response. type DiagnosticsTracerouteResponse struct { Response Result []DiagnosticsTracerouteResponseResult `json:"result"` } // DiagnosticsTracerouteResponseResult is the inner API response for the // traceroute request. type DiagnosticsTracerouteResponseResult struct { Target string `json:"target"` Colos []DiagnosticsTracerouteResponseColos `json:"colos"` } // DiagnosticsTracerouteResponseColo contains the Name and City of a colocation. type DiagnosticsTracerouteResponseColo struct { Name string `json:"name"` City string `json:"city"` } // DiagnosticsTracerouteResponseNodes holds a summary of nodes contacted in the // traceroute. type DiagnosticsTracerouteResponseNodes struct { Asn string `json:"asn"` IP string `json:"ip"` Name string `json:"name"` PacketCount int `json:"packet_count"` MeanRttMs float64 `json:"mean_rtt_ms"` StdDevRttMs float64 `json:"std_dev_rtt_ms"` MinRttMs float64 `json:"min_rtt_ms"` MaxRttMs float64 `json:"max_rtt_ms"` } // DiagnosticsTracerouteResponseHops holds packet and node information of the // hops. type DiagnosticsTracerouteResponseHops struct { PacketsTTL int `json:"packets_ttl"` PacketsSent int `json:"packets_sent"` PacketsLost int `json:"packets_lost"` Nodes []DiagnosticsTracerouteResponseNodes `json:"nodes"` } // DiagnosticsTracerouteResponseColos is the summary struct of a colocation test. type DiagnosticsTracerouteResponseColos struct { Error string `json:"error"` Colo DiagnosticsTracerouteResponseColo `json:"colo"` TracerouteTimeMs int `json:"traceroute_time_ms"` TargetSummary DiagnosticsTracerouteResponseNodes `json:"target_summary"` Hops []DiagnosticsTracerouteResponseHops `json:"hops"` } // PerformTraceroute initiates a traceroute from the Cloudflare network to the // requested targets. // // API documentation: https://api.cloudflare.com/#diagnostics-traceroute func (api *API) PerformTraceroute(ctx context.Context, accountID string, targets, colos []string, tracerouteOptions DiagnosticsTracerouteConfigurationOptions) ([]DiagnosticsTracerouteResponseResult, error) { uri := fmt.Sprintf("/accounts/%s/diagnostics/traceroute", accountID) diagnosticsPayload := DiagnosticsTracerouteConfiguration{ Targets: targets, Colos: colos, Options: tracerouteOptions, } res, err := api.makeRequestContext(ctx, http.MethodPost, uri, diagnosticsPayload) if err != nil { return []DiagnosticsTracerouteResponseResult{}, err } var diagnosticsResponse DiagnosticsTracerouteResponse err = json.Unmarshal(res, &diagnosticsResponse) if err != nil { return []DiagnosticsTracerouteResponseResult{}, fmt.Errorf("%s: %w", errUnmarshalError, err) } return diagnosticsResponse.Result, nil }