首页 > 解决方案 > Springboot Kickstart GraphQL - 每个解析器请求数的指标

问题描述

我目前正在 SpringBoot GraphQL kickstart 中尝试跟踪每个解析器方法被调用的次数。更具体地说,我想知道 my 的方法被调用了多少次GraphQLResolver<T>。这将有两个实用程序:

为此,我使用schema directive wiring.

@Component
class ResolverUsageCountInstrumentation(
    private val meterRegistry: MeterRegistry
) : SchemaDirectiveWiring {
    private val callsRecordingMap = ConcurrentHashMap<String, Int>()

    override fun onField(environment: SchemaDirectiveWiringEnvironment<GraphQLFieldDefinition>): GraphQLFieldDefinition {
        val fieldContainer = environment.fieldsContainer
        val fieldDefinition = environment.fieldDefinition

        val currentDF = environment.codeRegistry.getDataFetcher(fieldContainer, fieldDefinition)
        if (currentDF.javaClass.name != "graphql.kickstart.tools.resolver.MethodFieldResolverDataFetcher") {
            return fieldDefinition
        }

        val signature = getMethodSignature(unwrappedDF)
        callsRecordingMap[signature] = 0

        val newDF = DataFetcherFactories.wrapDataFetcher(currentDF) { dfe: DataFetchingEnvironment, value: Any? ->
            callsRecordingMap.computeIfPresent(signature) { _, current: Int -> current + 1 }
            value
        }

        environment.codeRegistry.dataFetcher(fieldContainer, fieldDefinition, newDF)

        return fieldDefinition
    }

    private fun getMethodSignature(currentDF: DataFetcher<*>): String {
        val method = getFieldVal(currentDF, "resolverMethod", true) as Method // nonapi.io.github.classgraph.utils.ReflectionUtils
        return "${method.declaringClass.name}#${method.name}"
    }
}

这种技术可以完成工作,但如果数据获取器被包装,则有一个很大的缺点是无法工作。除此之外,它一点也不干净。我想知道,有没有更好的方法来做到这一点?

谢谢!

标签: spring-bootgraphql-javagraphql-spring-boot

解决方案


推荐阅读