Skip to content
This repository has been archived by the owner on Jun 20, 2024. It is now read-only.

Commit

Permalink
feat: allow passing a custom prometheus registry to the graph gateway…
Browse files Browse the repository at this point in the history
… backend, and at the library level stop using the global default registry by default
  • Loading branch information
aschmahmann committed Jul 24, 2023
1 parent c44aa68 commit 2c1b4b7
Show file tree
Hide file tree
Showing 2 changed files with 27 additions and 14 deletions.
2 changes: 1 addition & 1 deletion handlers.go
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ func makeGatewayHandler(bs bstore.Blockstore, kuboRPC []string, port int, blockC
return nil, err
}

gwAPI, err = lib.NewGraphGatewayBackend(bs.(lib.CarFetcher), exch, lib.WithValueStore(routing), lib.WithBlockstore(cacheBlockStore))
gwAPI, err = lib.NewGraphGatewayBackend(bs.(lib.CarFetcher), exch, lib.WithValueStore(routing), lib.WithBlockstore(cacheBlockStore), lib.WithPrometheusRegistry(prometheus.DefaultRegisterer))

Check warning on line 106 in handlers.go

View check run for this annotation

Codecov / codecov/patch

handlers.go#L106

Added line #L106 was not covered by tests
if err != nil {
return nil, err
}
Expand Down
39 changes: 26 additions & 13 deletions lib/graph_gateway.go
Original file line number Diff line number Diff line change
Expand Up @@ -66,9 +66,10 @@ type CarFetcher interface {
}

type gwOptions struct {
ns namesys.NameSystem
vs routing.ValueStore
bs blockstore.Blockstore
ns namesys.NameSystem
vs routing.ValueStore
bs blockstore.Blockstore
promRegistry prometheus.Registerer
}

// WithNameSystem sets the name system to use for the gateway. If not set it will use a default DNSLink resolver
Expand Down Expand Up @@ -96,6 +97,14 @@ func WithBlockstore(bs blockstore.Blockstore) GraphGatewayOption {
}
}

// WithPrometheusRegistry sets the registry to use for metrics collection
func WithPrometheusRegistry(reg prometheus.Registerer) GraphGatewayOption {
return func(opts *gwOptions) error {
opts.promRegistry = reg
return nil
}

Check warning on line 105 in lib/graph_gateway.go

View check run for this annotation

Codecov / codecov/patch

lib/graph_gateway.go#L101-L105

Added lines #L101 - L105 were not covered by tests
}

type GraphGatewayOption func(gwOptions *gwOptions) error

type GraphGateway struct {
Expand Down Expand Up @@ -162,14 +171,19 @@ func NewGraphGatewayBackend(f CarFetcher, blockFetcher exchange.Fetcher, opts ..
bs = cbs
}

var promReg prometheus.Registerer = prometheus.NewRegistry()
if compiledOptions.promRegistry != nil {
promReg = compiledOptions.promRegistry
}

Check warning on line 177 in lib/graph_gateway.go

View check run for this annotation

Codecov / codecov/patch

lib/graph_gateway.go#L176-L177

Added lines #L176 - L177 were not covered by tests

return &GraphGateway{
fetcher: f,
blockFetcher: blockFetcher,
routing: vs,
namesys: ns,
bstore: bs,
notifiers: sync.Map{},
metrics: registerGraphGatewayMetrics(),
metrics: registerGraphGatewayMetrics(promReg),
pc: dagpb.AddSupportToChooser(func(lnk ipld.Link, lnkCtx ipld.LinkContext) (ipld.NodePrototype, error) {
if tlnkNd, ok := lnkCtx.LinkNode.(schema.TypedLinkNode); ok {
return tlnkNd.LinkTargetNodePrototype(), nil
Expand All @@ -179,8 +193,7 @@ func NewGraphGatewayBackend(f CarFetcher, blockFetcher exchange.Fetcher, opts ..
}, nil
}

func registerGraphGatewayMetrics() *GraphGatewayMetrics {

func registerGraphGatewayMetrics(registerer prometheus.Registerer) *GraphGatewayMetrics {
// How many CAR Fetch attempts we had? Need this to calculate % of various graph request types.
// We only count attempts here, because success/failure with/without retries are provided by caboose:
// - ipfs_caboose_fetch_duration_car_success_count
Expand All @@ -193,15 +206,15 @@ func registerGraphGatewayMetrics() *GraphGatewayMetrics {
Name: "car_fetch_attempts",
Help: "The number of times a CAR fetch was attempted by IPFSBackend.",
})
prometheus.MustRegister(carFetchAttemptMetric)
registerer.MustRegister(carFetchAttemptMetric)

contextAlreadyCancelledMetric := prometheus.NewCounter(prometheus.CounterOpts{
Namespace: "ipfs",
Subsystem: "gw_graph_backend",
Name: "car_fetch_context_already_cancelled",
Help: "The number of times context is already cancelled when a CAR fetch was attempted by IPFSBackend.",
})
prometheus.MustRegister(contextAlreadyCancelledMetric)
registerer.MustRegister(contextAlreadyCancelledMetric)

// How many blocks were read via CARs?
// Need this as a baseline to reason about error ratio vs raw_block_recovery_attempts.
Expand All @@ -211,7 +224,7 @@ func registerGraphGatewayMetrics() *GraphGatewayMetrics {
Name: "car_blocks_fetched",
Help: "The number of blocks successfully read via CAR fetch.",
})
prometheus.MustRegister(carBlocksFetchedMetric)
registerer.MustRegister(carBlocksFetchedMetric)

// How many times CAR response was not enough or just failed, and we had to read a block via ?format=raw
// We only count attempts here, because success/failure with/without retries are provided by caboose:
Expand All @@ -225,15 +238,15 @@ func registerGraphGatewayMetrics() *GraphGatewayMetrics {
Name: "raw_block_recovery_attempts",
Help: "The number of ?format=raw block fetch attempts due to GraphGateway failure (CAR fetch error, missing block in CAR response, or a block evicted from cache too soon).",
})
prometheus.MustRegister(blockRecoveryAttemptMetric)
registerer.MustRegister(blockRecoveryAttemptMetric)

carParamsMetric := prometheus.NewCounterVec(prometheus.CounterOpts{
Namespace: "ipfs",
Subsystem: "gw_graph_backend",
Name: "car_fetch_params",
Help: "How many times specific CAR parameter was used during CAR data fetch.",
}, []string{"dagScope", "entityRanges"}) // we use 'ranges' instead of 'bytes' here because we only count the number of ranges present
prometheus.MustRegister(carParamsMetric)
registerer.MustRegister(carParamsMetric)

bytesRangeStartMetric := prometheus.NewHistogram(prometheus.HistogramOpts{
Namespace: "ipfs",
Expand All @@ -242,7 +255,7 @@ func registerGraphGatewayMetrics() *GraphGatewayMetrics {
Help: "Tracks where did the range request start.",
Buckets: prometheus.ExponentialBuckets(1024, 2, 24), // 1024 bytes to 8 GiB
})
prometheus.MustRegister(bytesRangeStartMetric)
registerer.MustRegister(bytesRangeStartMetric)

bytesRangeSizeMetric := prometheus.NewHistogram(prometheus.HistogramOpts{
Namespace: "ipfs",
Expand All @@ -251,7 +264,7 @@ func registerGraphGatewayMetrics() *GraphGatewayMetrics {
Help: "Tracks the size of range requests.",
Buckets: prometheus.ExponentialBuckets(256*1024, 2, 10), // From 256KiB to 100MiB
})
prometheus.MustRegister(bytesRangeSizeMetric)
registerer.MustRegister(bytesRangeSizeMetric)

return &GraphGatewayMetrics{
contextAlreadyCancelledMetric,
Expand Down

0 comments on commit 2c1b4b7

Please sign in to comment.