mirror of
				https://github.com/Unleash/unleash.git
				synced 2025-10-27 11:02:16 +01:00 
			
		
		
		
	feat: add prom metrics (#8980)
This PR adds prometheus metrics that allows us to see whether or not tags and namePrefix is used at all in our cloud offering.
This commit is contained in:
		
							parent
							
								
									b1cced77c2
								
							
						
					
					
						commit
						39ca516823
					
				| @ -23,6 +23,7 @@ import type { OpenApiService } from '../../services/openapi-service'; | |||||||
| import { NONE } from '../../types/permissions'; | import { NONE } from '../../types/permissions'; | ||||||
| import { createResponseSchema } from '../../openapi/util/create-response-schema'; | import { createResponseSchema } from '../../openapi/util/create-response-schema'; | ||||||
| import type { ClientFeaturesQuerySchema } from '../../openapi/spec/client-features-query-schema'; | import type { ClientFeaturesQuerySchema } from '../../openapi/spec/client-features-query-schema'; | ||||||
|  | import type EventEmitter from 'events'; | ||||||
| import { | import { | ||||||
|     clientFeatureSchema, |     clientFeatureSchema, | ||||||
|     type ClientFeatureSchema, |     type ClientFeatureSchema, | ||||||
| @ -33,6 +34,10 @@ import { | |||||||
| } from '../../openapi/spec/client-features-schema'; | } from '../../openapi/spec/client-features-schema'; | ||||||
| import type ConfigurationRevisionService from '../feature-toggle/configuration-revision-service'; | import type ConfigurationRevisionService from '../feature-toggle/configuration-revision-service'; | ||||||
| import type { ClientFeatureToggleService } from './client-feature-toggle-service'; | import type { ClientFeatureToggleService } from './client-feature-toggle-service'; | ||||||
|  | import { | ||||||
|  |     CLIENT_METRICS_NAMEPREFIX, | ||||||
|  |     CLIENT_METRICS_TAGS, | ||||||
|  | } from '../../internals'; | ||||||
| 
 | 
 | ||||||
| const version = 2; | const version = 2; | ||||||
| 
 | 
 | ||||||
| @ -62,6 +67,8 @@ export default class FeatureController extends Controller { | |||||||
| 
 | 
 | ||||||
|     private flagResolver: IFlagResolver; |     private flagResolver: IFlagResolver; | ||||||
| 
 | 
 | ||||||
|  |     private eventBus: EventEmitter; | ||||||
|  | 
 | ||||||
|     private featuresAndSegments: ( |     private featuresAndSegments: ( | ||||||
|         query: IFeatureToggleQuery, |         query: IFeatureToggleQuery, | ||||||
|         etag: string, |         etag: string, | ||||||
| @ -92,6 +99,7 @@ export default class FeatureController extends Controller { | |||||||
|         this.configurationRevisionService = configurationRevisionService; |         this.configurationRevisionService = configurationRevisionService; | ||||||
|         this.featureToggleService = featureToggleService; |         this.featureToggleService = featureToggleService; | ||||||
|         this.flagResolver = config.flagResolver; |         this.flagResolver = config.flagResolver; | ||||||
|  |         this.eventBus = config.eventBus; | ||||||
|         this.logger = config.getLogger('client-api/feature.js'); |         this.logger = config.getLogger('client-api/feature.js'); | ||||||
| 
 | 
 | ||||||
|         this.route({ |         this.route({ | ||||||
| @ -210,6 +218,14 @@ export default class FeatureController extends Controller { | |||||||
|             return {}; |             return {}; | ||||||
|         } |         } | ||||||
| 
 | 
 | ||||||
|  |         if (namePrefix) { | ||||||
|  |             this.eventBus.emit(CLIENT_METRICS_NAMEPREFIX); | ||||||
|  |         } | ||||||
|  | 
 | ||||||
|  |         if (tag) { | ||||||
|  |             this.eventBus.emit(CLIENT_METRICS_TAGS); | ||||||
|  |         } | ||||||
|  | 
 | ||||||
|         const tagQuery = this.paramToArray(tag); |         const tagQuery = this.paramToArray(tag); | ||||||
|         const projectQuery = this.paramToArray(project); |         const projectQuery = this.paramToArray(project); | ||||||
|         const query = await querySchema.validateAsync({ |         const query = await querySchema.validateAsync({ | ||||||
|  | |||||||
| @ -1,4 +1,5 @@ | |||||||
| import type EventEmitter from 'events'; | import type EventEmitter from 'events'; | ||||||
|  | import { CLIENT_METRICS } from './internals'; | ||||||
| 
 | 
 | ||||||
| const REQUEST_TIME = 'request_time'; | const REQUEST_TIME = 'request_time'; | ||||||
| const DB_TIME = 'db_time'; | const DB_TIME = 'db_time'; | ||||||
| @ -14,6 +15,8 @@ const USER_LOGIN = 'user-login' as const; | |||||||
| const EXCEEDS_LIMIT = 'exceeds-limit' as const; | const EXCEEDS_LIMIT = 'exceeds-limit' as const; | ||||||
| const REQUEST_ORIGIN = 'request_origin' as const; | const REQUEST_ORIGIN = 'request_origin' as const; | ||||||
| const ADDON_EVENTS_HANDLED = 'addon-event-handled' as const; | const ADDON_EVENTS_HANDLED = 'addon-event-handled' as const; | ||||||
|  | const CLIENT_METRICS_NAMEPREFIX = 'client-api-nameprefix'; | ||||||
|  | const CLIENT_METRICS_TAGS = 'client-api-tags'; | ||||||
| 
 | 
 | ||||||
| type MetricEvent = | type MetricEvent = | ||||||
|     | typeof REQUEST_TIME |     | typeof REQUEST_TIME | ||||||
| @ -28,7 +31,9 @@ type MetricEvent = | |||||||
|     | typeof STAGE_ENTERED |     | typeof STAGE_ENTERED | ||||||
|     | typeof USER_LOGIN |     | typeof USER_LOGIN | ||||||
|     | typeof EXCEEDS_LIMIT |     | typeof EXCEEDS_LIMIT | ||||||
|     | typeof REQUEST_ORIGIN; |     | typeof REQUEST_ORIGIN | ||||||
|  |     | typeof CLIENT_METRICS_NAMEPREFIX | ||||||
|  |     | typeof CLIENT_METRICS_TAGS; | ||||||
| 
 | 
 | ||||||
| type RequestOriginEventPayload = { | type RequestOriginEventPayload = { | ||||||
|     type: 'UI' | 'API'; |     type: 'UI' | 'API'; | ||||||
| @ -76,6 +81,8 @@ export { | |||||||
|     EXCEEDS_LIMIT, |     EXCEEDS_LIMIT, | ||||||
|     REQUEST_ORIGIN, |     REQUEST_ORIGIN, | ||||||
|     ADDON_EVENTS_HANDLED, |     ADDON_EVENTS_HANDLED, | ||||||
|  |     CLIENT_METRICS_NAMEPREFIX, | ||||||
|  |     CLIENT_METRICS_TAGS, | ||||||
|     type MetricEvent, |     type MetricEvent, | ||||||
|     type MetricEventPayload, |     type MetricEventPayload, | ||||||
|     emitMetricEvent, |     emitMetricEvent, | ||||||
|  | |||||||
| @ -504,6 +504,16 @@ export function registerPrometheusMetrics( | |||||||
|         }) |         }) | ||||||
|         .set(config.rateLimiting.callSignalEndpointMaxPerSecond * 60); |         .set(config.rateLimiting.callSignalEndpointMaxPerSecond * 60); | ||||||
| 
 | 
 | ||||||
|  |     const namePrefixUsed = createCounter({ | ||||||
|  |         name: 'nameprefix_count', | ||||||
|  |         help: 'Count of nameprefix usage in client api', | ||||||
|  |     }); | ||||||
|  | 
 | ||||||
|  |     const tagsUsed = createCounter({ | ||||||
|  |         name: 'tags_count', | ||||||
|  |         help: 'Count of tags usage in client api', | ||||||
|  |     }); | ||||||
|  | 
 | ||||||
|     const featureCreatedByMigration = createCounter({ |     const featureCreatedByMigration = createCounter({ | ||||||
|         name: 'feature_created_by_migration_count', |         name: 'feature_created_by_migration_count', | ||||||
|         help: 'Feature createdBy migration count', |         help: 'Feature createdBy migration count', | ||||||
| @ -734,6 +744,14 @@ export function registerPrometheusMetrics( | |||||||
|         mapFeaturesForClientDuration.observe(duration); |         mapFeaturesForClientDuration.observe(duration); | ||||||
|     }); |     }); | ||||||
| 
 | 
 | ||||||
|  |     eventBus.on(events.CLIENT_METRICS_NAMEPREFIX, () => { | ||||||
|  |         namePrefixUsed.inc(); | ||||||
|  |     }); | ||||||
|  | 
 | ||||||
|  |     eventBus.on(events.CLIENT_METRICS_TAGS, () => { | ||||||
|  |         tagsUsed.inc(); | ||||||
|  |     }); | ||||||
|  | 
 | ||||||
|     events.onMetricEvent( |     events.onMetricEvent( | ||||||
|         eventBus, |         eventBus, | ||||||
|         events.REQUEST_ORIGIN, |         events.REQUEST_ORIGIN, | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user