UNPKG

@khulnasoft/cdk

Version:

Define your observability as code using the AWS CDK

99 lines (81 loc) 2.8 kB
import { CfnResource, Stack } from "aws-cdk-lib"; import { Kengine as Config } from "../config"; import { QueryProps, Filter, DeploymentQueryParameters } from "../types/query"; import { AlertProps } from "../types/alert"; import { Alert } from './alert'; function hasDuplicates<T>(array: T[]) { return (new Set(array)).size !== array.length; } function buildShortCalculation(cal: { alias?: string; operation: string; key?: string }) { if (cal.operation === "COUNT") { return cal.operation; } return `${cal.operation}(${cal.key})`; } function getCalculationAlias(cal: { alias?: string; operation: string; key?: string }) { return cal.alias ? cal.alias : buildShortCalculation(cal); } /** * */ export class Query<TKey extends string> extends CfnResource { id: string; props: QueryProps<TKey> constructor(id: string, props: QueryProps<TKey>) { const stack = Stack.of(Config.getConstruct()); const calcs = props.parameters.calculations; const orderByOptions = calcs?.map(cal => getCalculationAlias(cal)); if (calcs?.length && hasDuplicates(calcs.filter(c => c.alias).map(c => c.alias))) { throw Error("Aliases must me unique across all calculations / visualisations.") } if (props.parameters.orderBy && !orderByOptions?.includes(props.parameters.orderBy.value)) { throw Error("The orderBy must be present in the calculations / visualisations.") } const disableStackFilter = props.disableStackFilter || Config.getDisableStackFilter(); if (!disableStackFilter) { props.parameters.filters?.push({ operation: "=", key: "$kengine.stackId", value: stack.stackName }) } const Parameters: DeploymentQueryParameters = { ...props.parameters, datasets: props.parameters.datasets || [], calculations: props.parameters.calculations || [], filters: props.parameters.filters, groupBys: props.parameters.groupBys?.map(groupBy => { return { ...groupBy, type: groupBy?.type || "string" } }), filterCombination: props.parameters.filterCombination || "AND", }; super(Config.getConstruct(), id, { type: "Custom::KengineQuery", properties: { id, ServiceToken: Config.getServiceToken(), KengineApiKey: Config.getApiKey(), Description: props.description, Parameters, Origin: "cdk" }, }); this.id = id; this.props = props; } addAlert(alert: ChangeFields<AlertProps<TKey>, { parameters: Omit<AlertProps<TKey>['parameters'], "query"> }>) { const alertProps = { ...alert, parameters: { ...alert.parameters, query: this } } new Alert(`${this.id}-alert`, alertProps); } addFilters(filters: QueryProps<string>["parameters"]["filters"]) { this.addPropertyOverride('Parameters.filters', [...filters || []]) } }; type ChangeFields<T, R> = Omit<T, keyof R> & R;