diff --git a/API.md b/API.md
index c7360c5c..60c0bb0e 100644
--- a/API.md
+++ b/API.md
@@ -3260,6 +3260,7 @@ const controlPlaneProps: ControlPlaneProps = { ... }
| billing
| IBilling
| The billing provider configuration. |
| disableAPILogging
| boolean
| If true, the API Gateway will not log requests to the CloudWatch Logs. |
| eventManager
| IEventManager
| The event manager instance. |
+| metering
| IMetering
| The metering provider configuration. |
| systemAdminName
| string
| The name of the system admin user. |
| systemAdminRoleName
| string
| The name of the system admin role. |
@@ -3342,6 +3343,18 @@ If not provided, a new instance will be created.
---
+##### `metering`Optional
+
+```typescript
+public readonly metering: IMetering;
+```
+
+- *Type:* IMetering
+
+The metering provider configuration.
+
+---
+
##### `systemAdminName`Optional
```typescript
@@ -4803,10 +4816,10 @@ Encapsulates the list of properties for an IBilling construct.
| **Name** | **Type** | **Description** |
| --- | --- | --- |
-| createCustomerFunction
| aws-cdk-lib.aws_lambda.IFunction \| IFunctionTrigger
| The function to trigger to create a new customer. |
-| deleteCustomerFunction
| aws-cdk-lib.aws_lambda.IFunction \| IFunctionTrigger
| The function to trigger to delete a customer. |
-| createUserFunction
| aws-cdk-lib.aws_lambda.IFunction \| IFunctionTrigger
| The function to trigger to create a new user. |
-| deleteUserFunction
| aws-cdk-lib.aws_lambda.IFunction \| IFunctionTrigger
| The function to trigger to delete a user. |
+| createCustomerFunction
| IFunctionTrigger \| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to create a new customer. |
+| deleteCustomerFunction
| IFunctionTrigger \| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to delete a customer. |
+| createUserFunction
| IFunctionTrigger \| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to create a new user. |
+| deleteUserFunction
| IFunctionTrigger \| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to delete a user. |
| ingestor
| IDataIngestorAggregator
| The IDataIngestorAggregator responsible for accepting and aggregating the raw billing data. |
| putUsageFunction
| aws-cdk-lib.aws_lambda.IFunction \| IFunctionSchedule
| The function responsible for taking the aggregated data and pushing that to the billing provider. |
| webhookFunction
| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger when a webhook request is received. |
@@ -4817,10 +4830,10 @@ Encapsulates the list of properties for an IBilling construct.
##### `createCustomerFunction`Required
```typescript
-public readonly createCustomerFunction: IFunction | IFunctionTrigger;
+public readonly createCustomerFunction: IFunctionTrigger | IFunction;
```
-- *Type:* aws-cdk-lib.aws_lambda.IFunction | IFunctionTrigger
+- *Type:* IFunctionTrigger | aws-cdk-lib.aws_lambda.IFunction
The function to trigger to create a new customer.
@@ -4831,10 +4844,10 @@ The function to trigger to create a new customer.
##### `deleteCustomerFunction`Required
```typescript
-public readonly deleteCustomerFunction: IFunction | IFunctionTrigger;
+public readonly deleteCustomerFunction: IFunctionTrigger | IFunction;
```
-- *Type:* aws-cdk-lib.aws_lambda.IFunction | IFunctionTrigger
+- *Type:* IFunctionTrigger | aws-cdk-lib.aws_lambda.IFunction
The function to trigger to delete a customer.
@@ -4845,10 +4858,10 @@ The function to trigger to delete a customer.
##### `createUserFunction`Optional
```typescript
-public readonly createUserFunction: IFunction | IFunctionTrigger;
+public readonly createUserFunction: IFunctionTrigger | IFunction;
```
-- *Type:* aws-cdk-lib.aws_lambda.IFunction | IFunctionTrigger
+- *Type:* IFunctionTrigger | aws-cdk-lib.aws_lambda.IFunction
The function to trigger to create a new user.
@@ -4859,10 +4872,10 @@ The function to trigger to create a new user.
##### `deleteUserFunction`Optional
```typescript
-public readonly deleteUserFunction: IFunction | IFunctionTrigger;
+public readonly deleteUserFunction: IFunctionTrigger | IFunction;
```
-- *Type:* aws-cdk-lib.aws_lambda.IFunction | IFunctionTrigger
+- *Type:* IFunctionTrigger | aws-cdk-lib.aws_lambda.IFunction
The function to trigger to delete a user.
@@ -5182,6 +5195,176 @@ The detail-type that will trigger the handler function.
---
+### IMetering
+
+- *Implemented By:* IMetering
+
+Encapsulates the list of properties for an IMetering construct.
+
+
+#### Properties
+
+| **Name** | **Type** | **Description** |
+| --- | --- | --- |
+| createMeterFunction
| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to create a meter -- POST /meters Once created, the meter can be used to track and analyze the specific usage metrics for tenants. |
+| fetchUsageFunction
| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to get the usage data that has been recorded for a specific meter. |
+| ingestUsageEventFunction
| IFunctionTrigger \| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to ingest a usage event. |
+| cancelUsageEventsFunction
| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to exclude specific events from being recorded or included in the usage data. |
+| cancelUsageEventsScope
| string
| The scope required to authorize requests for cancelling usage events. |
+| createCustomerFunction
| IFunctionTrigger \| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to create a new customer. (Customer in this context is a tenant.). |
+| createMeterScope
| string
| The scope required to authorize requests for creating a new meter. |
+| deleteCustomerFunction
| IFunctionTrigger \| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to delete a customer. (Customer in this context is a tenant.). |
+| fetchUsageScope
| string
| The scope required to authorize requests for fetching metering usage. |
+| updateMeterFunction
| aws-cdk-lib.aws_lambda.IFunction
| The function to trigger to update a meter -- PUT /meters/meterId. |
+| updateMeterScope
| string
| The scope required to authorize requests for updating a meter. |
+
+---
+
+##### `createMeterFunction`Required
+
+```typescript
+public readonly createMeterFunction: IFunction;
+```
+
+- *Type:* aws-cdk-lib.aws_lambda.IFunction
+
+The function to trigger to create a meter -- POST /meters Once created, the meter can be used to track and analyze the specific usage metrics for tenants.
+
+---
+
+##### `fetchUsageFunction`Required
+
+```typescript
+public readonly fetchUsageFunction: IFunction;
+```
+
+- *Type:* aws-cdk-lib.aws_lambda.IFunction
+
+The function to trigger to get the usage data that has been recorded for a specific meter.
+
+- GET /usage/meterId
+
+---
+
+##### `ingestUsageEventFunction`Required
+
+```typescript
+public readonly ingestUsageEventFunction: IFunctionTrigger | IFunction;
+```
+
+- *Type:* IFunctionTrigger | aws-cdk-lib.aws_lambda.IFunction
+
+The function to trigger to ingest a usage event.
+
+Usage events are used to measure and track the usage metrics associated with the meter.
+
+Default event trigger: INGEST_USAGE
+
+---
+
+##### `cancelUsageEventsFunction`Optional
+
+```typescript
+public readonly cancelUsageEventsFunction: IFunction;
+```
+
+- *Type:* aws-cdk-lib.aws_lambda.IFunction
+
+The function to trigger to exclude specific events from being recorded or included in the usage data.
+
+Used for canceling events that were incorrectly ingested.
+-- DELETE /usage
+
+---
+
+##### `cancelUsageEventsScope`Optional
+
+```typescript
+public readonly cancelUsageEventsScope: string;
+```
+
+- *Type:* string
+
+The scope required to authorize requests for cancelling usage events.
+
+---
+
+##### `createCustomerFunction`Optional
+
+```typescript
+public readonly createCustomerFunction: IFunctionTrigger | IFunction;
+```
+
+- *Type:* IFunctionTrigger | aws-cdk-lib.aws_lambda.IFunction
+
+The function to trigger to create a new customer. (Customer in this context is a tenant.).
+
+Default event trigger: ONBOARDING_REQUEST
+
+---
+
+##### `createMeterScope`Optional
+
+```typescript
+public readonly createMeterScope: string;
+```
+
+- *Type:* string
+
+The scope required to authorize requests for creating a new meter.
+
+---
+
+##### `deleteCustomerFunction`Optional
+
+```typescript
+public readonly deleteCustomerFunction: IFunctionTrigger | IFunction;
+```
+
+- *Type:* IFunctionTrigger | aws-cdk-lib.aws_lambda.IFunction
+
+The function to trigger to delete a customer. (Customer in this context is a tenant.).
+
+Default event trigger: OFFBOARDING_REQUEST
+
+---
+
+##### `fetchUsageScope`Optional
+
+```typescript
+public readonly fetchUsageScope: string;
+```
+
+- *Type:* string
+
+The scope required to authorize requests for fetching metering usage.
+
+---
+
+##### `updateMeterFunction`Optional
+
+```typescript
+public readonly updateMeterFunction: IFunction;
+```
+
+- *Type:* aws-cdk-lib.aws_lambda.IFunction
+
+The function to trigger to update a meter -- PUT /meters/meterId.
+
+---
+
+##### `updateMeterScope`Optional
+
+```typescript
+public readonly updateMeterScope: string;
+```
+
+- *Type:* string
+
+The scope required to authorize requests for updating a meter.
+
+---
+
### IRoute
- *Implemented By:* IRoute
@@ -5306,6 +5489,7 @@ events sent across the EventBus.
| DEACTIVATE_FAILURE
| Event detail type for failed deactivation. |
| TENANT_USER_CREATED
| Event detail type for user creation on the app-plane side. |
| TENANT_USER_DELETED
| Event detail type for user deletion on the app-plane side. |
+| INGEST_USAGE
| Event detail type for ingesting a usage event. |
---
@@ -5454,3 +5638,10 @@ should be emitted by the application plane.
---
+
+##### `INGEST_USAGE`
+
+Event detail type for ingesting a usage event.
+
+---
+
diff --git a/src/control-plane/billing/billing-interface.ts b/src/control-plane/billing/billing-interface.ts
index de16705f..97362471 100644
--- a/src/control-plane/billing/billing-interface.ts
+++ b/src/control-plane/billing/billing-interface.ts
@@ -3,25 +3,9 @@
import { Schedule } from 'aws-cdk-lib/aws-events';
import { IFunction } from 'aws-cdk-lib/aws-lambda';
-import { DetailType } from '../../utils';
+import { IFunctionTrigger } from '../../utils';
import { IDataIngestorAggregator } from '../ingestor-aggregator/ingestor-aggregator-interface';
-/**
- * Optional interface that allows specifying both
- * the function to trigger and the event that will trigger it.
- */
-export interface IFunctionTrigger {
- /**
- * The function definition.
- */
- readonly handler: IFunction;
-
- /**
- * The detail-type that will trigger the handler function.
- */
- readonly trigger: DetailType;
-}
-
/**
* Optional interface that allows specifying both
* the function to trigger and the schedule by which to trigger it.
diff --git a/src/control-plane/billing/billing-provider.ts b/src/control-plane/billing/billing-provider.ts
index 9fb137ee..34af9f3f 100644
--- a/src/control-plane/billing/billing-provider.ts
+++ b/src/control-plane/billing/billing-provider.ts
@@ -6,11 +6,10 @@ import * as apigatewayV2 from 'aws-cdk-lib/aws-apigatewayv2';
import * as apigatewayV2Integrations from 'aws-cdk-lib/aws-apigatewayv2-integrations';
import * as events from 'aws-cdk-lib/aws-events';
import * as targets from 'aws-cdk-lib/aws-events-targets';
-import { IFunction } from 'aws-cdk-lib/aws-lambda';
import { NagSuppressions } from 'cdk-nag';
import { Construct } from 'constructs';
-import { IBilling, IFunctionTrigger } from './billing-interface';
-import { DetailType, IEventManager, addTemplateTag } from '../../utils';
+import { IBilling } from './billing-interface';
+import { DetailType, IEventManager, addTemplateTag, createEventTarget } from '../../utils';
/**
* Encapsulates the list of properties for a BillingProvider.
@@ -57,29 +56,31 @@ export class BillingProvider extends Construct {
super(scope, id);
addTemplateTag(this, 'BillingProvider');
- this.createEventTarget(
- props.eventManager,
- DetailType.ONBOARDING_REQUEST,
- props.billing.createCustomerFunction
- );
-
- this.createEventTarget(
- props.eventManager,
- DetailType.OFFBOARDING_REQUEST,
- props.billing.deleteCustomerFunction
- );
-
- this.createEventTarget(
- props.eventManager,
- DetailType.TENANT_USER_CREATED,
- props.billing.createUserFunction
- );
-
- this.createEventTarget(
- props.eventManager,
- DetailType.TENANT_USER_DELETED,
- props.billing.deleteUserFunction
- );
+ [
+ {
+ defaultFunctionTrigger: DetailType.ONBOARDING_REQUEST,
+ functionDefinition: props.billing.createCustomerFunction,
+ },
+ {
+ defaultFunctionTrigger: DetailType.OFFBOARDING_REQUEST,
+ functionDefinition: props.billing.deleteCustomerFunction,
+ },
+ {
+ defaultFunctionTrigger: DetailType.TENANT_USER_CREATED,
+ functionDefinition: props.billing.createUserFunction,
+ },
+ {
+ defaultFunctionTrigger: DetailType.TENANT_USER_DELETED,
+ functionDefinition: props.billing.deleteUserFunction,
+ },
+ ].forEach((target) => {
+ createEventTarget(
+ this,
+ props.eventManager,
+ target.defaultFunctionTrigger,
+ target.functionDefinition
+ );
+ });
if (props.billing.putUsageFunction) {
const schedule =
@@ -130,26 +131,4 @@ export class BillingProvider extends Construct {
);
}
}
-
- private getFunctionProps(
- fn: IFunction | IFunctionTrigger,
- defaultTrigger: DetailType
- ): IFunctionTrigger {
- return 'handler' in fn
- ? { handler: fn.handler, trigger: fn.trigger }
- : { handler: fn, trigger: defaultTrigger };
- }
-
- private createEventTarget(
- eventManager: IEventManager,
- defaultEvent: DetailType,
- fn?: IFunction | IFunctionTrigger
- ) {
- if (!fn) {
- return;
- }
-
- const { handler, trigger } = this.getFunctionProps(fn, defaultEvent);
- eventManager.addTargetToEvent(this, trigger, new targets.LambdaFunction(handler));
- }
}
diff --git a/src/control-plane/control-plane.ts b/src/control-plane/control-plane.ts
index 495d1947..31a9146b 100644
--- a/src/control-plane/control-plane.ts
+++ b/src/control-plane/control-plane.ts
@@ -9,6 +9,8 @@ import { IAuth } from './auth/auth-interface';
import { CognitoAuth } from './auth/cognito-auth';
import { BillingProvider, IBilling } from './billing';
import { ControlPlaneAPI } from './control-plane-api';
+import { IMetering } from './metering';
+import { MeteringProvider } from './metering/metering-provider';
import { TenantConfigService } from './tenant-config';
import { TenantManagementService } from './tenant-management/tenant-management.service';
import { UserManagementService } from './user-management/user-management.service';
@@ -44,6 +46,11 @@ export interface ControlPlaneProps {
*/
readonly billing?: IBilling;
+ /**
+ * The metering provider configuration.
+ */
+ readonly metering?: IMetering;
+
/**
* The event manager instance. If not provided, a new instance will be created.
*/
@@ -140,6 +147,15 @@ export class ControlPlane extends Construct {
});
}
}
+
+ if (props.metering) {
+ new MeteringProvider(this, 'Metering', {
+ metering: props.metering,
+ api: api,
+ eventManager: eventManager,
+ });
+ }
+
this.eventManager = eventManager;
// defined suppression here to suppress EventsRole Default policy
diff --git a/src/control-plane/index.ts b/src/control-plane/index.ts
index f0510a54..630c63d1 100644
--- a/src/control-plane/index.ts
+++ b/src/control-plane/index.ts
@@ -11,3 +11,4 @@ export * from './ingestor-aggregator/index';
export * from './tenant-config';
export * from './tenant-management';
export * from './user-management';
+export * from './metering';
diff --git a/src/control-plane/metering/index.ts b/src/control-plane/metering/index.ts
new file mode 100644
index 00000000..b062d0c4
--- /dev/null
+++ b/src/control-plane/metering/index.ts
@@ -0,0 +1,4 @@
+// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
+// SPDX-License-Identifier: Apache-2.0
+
+export * from './metering-interface';
diff --git a/src/control-plane/metering/metering-interface.ts b/src/control-plane/metering/metering-interface.ts
index 2d36203b..04a19ed7 100644
--- a/src/control-plane/metering/metering-interface.ts
+++ b/src/control-plane/metering/metering-interface.ts
@@ -2,65 +2,77 @@
// SPDX-License-Identifier: Apache-2.0
import { IFunction } from 'aws-cdk-lib/aws-lambda';
-import { DetailType } from '../../utils';
+import { IFunctionTrigger } from '../../utils';
/**
- * Optional interface that allows specifying both
- * the function to trigger and the event that will trigger it.
+ * Encapsulates the list of properties for an IMetering construct.
*/
-export interface IFunctionTrigger {
+export interface IMetering {
/**
- * The function definition.
+ * The function to trigger to create a meter -- POST /meters
+ * Once created, the meter can be used to track and analyze the specific usage metrics for tenants.
*/
- readonly handler: IFunction;
+ createMeterFunction: IFunction;
/**
- * The detail-type that will trigger the handler function.
+ * The scope required to authorize requests for creating a new meter.
*/
- readonly trigger: DetailType;
-}
+ createMeterScope?: string;
-/**
- * Encapsulates the list of properties for an IMetering construct.
- */
-export interface IMetering {
/**
- * The function to trigger to create a meter.
- * Once created, the meter can be used to track and analyze the specific usage metrics for tenants.
+ * The function to trigger to update a meter -- PUT /meters/meterId
*/
- createMeterFunction: IFunction | IFunctionTrigger;
+ updateMeterFunction?: IFunction;
/**
- * The function to trigger to update a meter.
+ * The scope required to authorize requests for updating a meter.
*/
- updateMeterFunction?: IFunction | IFunctionTrigger;
+ updateMeterScope?: string;
/**
* The function to trigger to ingest a usage event.
* Usage events are used to measure and track the usage metrics associated with the meter.
+ *
+ * Default event trigger: INGEST_USAGE
*/
- ingestFunction: IFunction | IFunctionTrigger;
+ ingestUsageEventFunction: IFunction | IFunctionTrigger;
/**
* The function to trigger to get the usage data that has been recorded for a specific meter.
+ * -- GET /usage/meterId
+ */
+ fetchUsageFunction: IFunction; // use 'fetch*' instead of 'get*' to avoid error JSII5000
+
+ /**
+ * The scope required to authorize requests for fetching metering usage.
*/
- getUsageFunction: IFunction | IFunctionTrigger;
+ fetchUsageScope?: string;
/**
* The function to trigger to exclude specific events from being recorded or included in the usage data.
* Used for canceling events that were incorrectly ingested.
+ * -- DELETE /usage
+ */
+ cancelUsageEventsFunction?: IFunction;
+
+ /**
+ * The scope required to authorize requests for cancelling usage events.
*/
- cancelUsageEventsFunction?: IFunction | IFunctionTrigger;
+ cancelUsageEventsScope?: string;
/**
* The function to trigger to create a new customer.
* (Customer in this context is a tenant.)
+ *
+ * Default event trigger: ONBOARDING_REQUEST
*/
createCustomerFunction?: IFunction | IFunctionTrigger;
/**
* The function to trigger to delete a customer.
* (Customer in this context is a tenant.)
+ *
+ * Default event trigger: OFFBOARDING_REQUEST
*/
deleteCustomerFunction?: IFunction | IFunctionTrigger;
}
diff --git a/src/control-plane/metering/metering-provider.ts b/src/control-plane/metering/metering-provider.ts
new file mode 100644
index 00000000..cf463eb3
--- /dev/null
+++ b/src/control-plane/metering/metering-provider.ts
@@ -0,0 +1,121 @@
+// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
+// SPDX-License-Identifier: Apache-2.0
+
+import * as apigatewayV2 from 'aws-cdk-lib/aws-apigatewayv2';
+import * as apigatewayV2Integrations from 'aws-cdk-lib/aws-apigatewayv2-integrations';
+import { IFunction } from 'aws-cdk-lib/aws-lambda';
+import { Construct } from 'constructs';
+import { IMetering } from './metering-interface';
+import * as utils from '../../utils';
+import { ControlPlaneAPI } from '../control-plane-api';
+
+/**
+ * Encapsulates the list of properties for a MeteringProvider.
+ */
+export interface MeteringProviderProps {
+ /**
+ * An implementation of the IMetering interface.
+ */
+ readonly metering: IMetering;
+
+ /**
+ * An IEventManager object to help coordinate events.
+ */
+ readonly eventManager: utils.IEventManager;
+
+ /**
+ * An API resource to use when setting up API endpoints.
+ */
+ readonly api: ControlPlaneAPI;
+}
+
+/**
+ * Represents a Metering Provider that handles metering-related operations and
+ * connects the concrete IMetering implementation (provided via props.metering)
+ * to the control plane.
+ *
+ * This construct sets up event targets for various metering-related events
+ * and adds API routes for 'usage' and 'meters'.
+ */
+export class MeteringProvider extends Construct {
+ constructor(scope: Construct, id: string, props: MeteringProviderProps) {
+ super(scope, id);
+ utils.addTemplateTag(this, 'MeteringProvider');
+
+ const usagePath = '/usage';
+ const metersPath = '/meters';
+ const functionTriggerMappings: {
+ defaultFunctionTrigger: utils.DetailType;
+ functionDefinition?: IFunction | utils.IFunctionTrigger;
+ }[] = [
+ {
+ defaultFunctionTrigger: utils.DetailType.ONBOARDING_REQUEST,
+ functionDefinition: props.metering.createCustomerFunction,
+ },
+ {
+ defaultFunctionTrigger: utils.DetailType.OFFBOARDING_REQUEST,
+ functionDefinition: props.metering.deleteCustomerFunction,
+ },
+ {
+ defaultFunctionTrigger: utils.DetailType.INGEST_USAGE,
+ functionDefinition: props.metering.ingestUsageEventFunction,
+ },
+ ];
+
+ functionTriggerMappings.forEach((target) => {
+ utils.createEventTarget(
+ this,
+ props.eventManager,
+ target.defaultFunctionTrigger,
+ target.functionDefinition
+ );
+ });
+
+ const routes: utils.IRoute[] = [
+ {
+ path: `${usagePath}/meterId`,
+ method: apigatewayV2.HttpMethod.GET,
+ integration: new apigatewayV2Integrations.HttpLambdaIntegration(
+ 'fetchUsageHttpLambdaIntegration',
+ props.metering.fetchUsageFunction
+ ),
+ scope: props.metering.fetchUsageScope,
+ },
+ {
+ path: metersPath,
+ method: apigatewayV2.HttpMethod.POST,
+ integration: new apigatewayV2Integrations.HttpLambdaIntegration(
+ 'createMeterHttpLambdaIntegration',
+ props.metering.createMeterFunction
+ ),
+ scope: props.metering.createMeterScope,
+ },
+ ];
+
+ if (props.metering.cancelUsageEventsFunction) {
+ routes.push({
+ path: usagePath,
+ method: apigatewayV2.HttpMethod.DELETE,
+ integration: new apigatewayV2Integrations.HttpLambdaIntegration(
+ 'deleteUsageHttpLambdaIntegration',
+ props.metering.cancelUsageEventsFunction
+ ),
+ scope: props.metering.cancelUsageEventsScope,
+ });
+ }
+
+ if (props.metering.updateMeterFunction) {
+ routes.push({
+ path: `${metersPath}/meterId`,
+ method: apigatewayV2.HttpMethod.PUT,
+ integration: new apigatewayV2Integrations.HttpLambdaIntegration(
+ 'updateMeterHttpLambdaIntegration',
+ props.metering.updateMeterFunction
+ ),
+ scope: props.metering.updateMeterScope,
+ });
+ }
+
+ utils.generateRoutes(props.api.api, routes, props.api.jwtAuthorizer);
+ }
+}
diff --git a/src/utils/event-manager.ts b/src/utils/event-manager.ts
index 19fcee5c..e7433a1d 100644
--- a/src/utils/event-manager.ts
+++ b/src/utils/event-manager.ts
@@ -103,6 +103,11 @@ export enum DetailType {
* should be emitted by the application plane.
*/
TENANT_USER_DELETED = 'tenantUserDeleted',
+
+ /**
+ * Event detail type for ingesting a usage event.
+ */
+ INGEST_USAGE = 'ingestUsage',
}
/**
@@ -252,6 +257,7 @@ export class EventManager extends Construct implements IEventManager {
deactivateFailure: this.applicationPlaneEventSource,
tenantUserCreated: this.controlPlaneEventSource,
tenantUserDeleted: this.controlPlaneEventSource,
+ ingestUsage: this.applicationPlaneEventSource,
};
for (const key in this.supportedEvents) {
diff --git a/src/utils/utils.ts b/src/utils/utils.ts
index 413656ea..86a4887a 100644
--- a/src/utils/utils.ts
+++ b/src/utils/utils.ts
@@ -3,7 +3,10 @@
import { Stack } from 'aws-cdk-lib';
import * as apigatewayV2 from 'aws-cdk-lib/aws-apigatewayv2';
+import * as targets from 'aws-cdk-lib/aws-events-targets';
+import { IFunction } from 'aws-cdk-lib/aws-lambda';
import { Construct } from 'constructs';
+import { DetailType, IEventManager } from './event-manager';
export const addTemplateTag = (construct: Construct, tag: string) => {
const stackDesc = Stack.of(construct).templateOptions.description;
@@ -101,3 +104,51 @@ export const generateRoutes = (
});
return allRoutes;
};
+
+/**
+ * Optional interface that allows specifying both
+ * the function to trigger and the event that will trigger it.
+ */
+export interface IFunctionTrigger {
+ /**
+ * The function definition.
+ */
+ readonly handler: IFunction;
+
+ /**
+ * The detail-type that will trigger the handler function.
+ */
+ readonly trigger: DetailType;
+}
+
+/**
+ * Helper function for attaching functions to events.
+ * If an IFunction is passed in as the argument for functionOrFunctionTrigger, then
+ * the defaultEvent is used as the trigger for the IFunction.
+ *
+ * If an IFunctionTrigger is passed in as the argument for functionOrFunctionTrigger, then
+ * the trigger property of the IFunctionTrigger is used as the trigger for the IFunction.
+ *
+ * If the functionOrFunctionTrigger is not passed in, no event is created.
+ */
+export const createEventTarget = (
+ scope: Construct,
+ eventManager: IEventManager,
+ defaultEvent: DetailType,
+ functionOrFunctionTrigger?: IFunction | IFunctionTrigger
+) => {
+ if (!functionOrFunctionTrigger) {
+ return;
+ }
+
+ let handler: IFunction, trigger: DetailType;
+ if ('handler' in functionOrFunctionTrigger) {
+ handler = functionOrFunctionTrigger.handler;
+ trigger = functionOrFunctionTrigger.trigger;
+ } else {
+ handler = functionOrFunctionTrigger;
+ trigger = defaultEvent;
+ }
+
+ eventManager.addTargetToEvent(scope, trigger, new targets.LambdaFunction(handler));
+};