aws / aws/aws-cdk

Cyclic reference if CloudWatch Rule and Lambda are in different stacks

Open
#7,744 4 comments 3 reactions 0 assignees View on GitHub
@aws-cdk/aws-cloudwatch bug effort/medium p2
Dominant language
TypeScript
Stars
12.9k
Forks
4.6k
Avg merge
2d 3h
Merged PRs (30d)
83

Description

When creating a CloudWatch Rule in CDK, if the rule is in a different stack from the Lambda, this results in an error. The error can be reproduced by typing `cdk ls`.
`Adding this dependency (${reason}) would create a cyclic reference.`

This is/was a similar issue with API Gateway. The CloudWatch problem was mentioned in the bottom of that issue.
https://github.com/aws/aws-cdk/issues/3000

### Reproduction Steps

```typescript
import { App, Aws, Stack } from '@aws-cdk/core';
import awsIam = require('@aws-cdk/aws-iam');
import awsLambda = require('@aws-cdk/aws-lambda');
import awsEvents = require('@aws-cdk/aws-events');
import awsEventsTargets = require('@aws-cdk/aws-events-targets');

class LambdaStack extends Stack {
lambdaRole: awsIam.Role;
lambdaFunction: awsLambda.Function;

constructor(app: App) {
super(app, 'LambdaStack', {});
this.lambdaRole = this.createLambdaRole();
this.lambdaFunction = this.createLambdaFunction();
}

private createLambdaRole(): awsIam.Role {
const lambdaRole: awsIam.Role = new awsIam.Role(this, 'LambdaRole', {
roleName: 'LambdaRole',
assumedBy: new awsIam.ServicePrincipal('lambda.amazonaws.com'),
})

const policyName = 'LambdaPolicy';
const lambdaPolicy = new awsIam.Policy(this, policyName, {
policyName: policyName,
statements: [
new awsIam.PolicyStatement({
actions: [
'logs:CreateLogStream',
'logs:CreateLogGroup',
'logs:DeleteLogStream',
'logs:DeleteLogGroup',
'logs:PutLogEvents',
],
effect: awsIam.Effect.ALLOW,
resources: [
`arn:aws:logs:${Aws.REGION}:${Aws.ACCOUNT_ID}:log-group:/aws/lambda/LambdaFunction`,
],
}),
],
});
lambdaRole.attachInlinePolicy(lambdaPolicy);

return lambdaRole;
}

private createLambdaFunction(): awsLambda.Function {
const lambdaFunction: awsLambda.Function = new awsLambda.Function(this, 'LambdaFunction', {
runtime: awsLambda.Runtime.PYTHON_3_7,
handler: 'lambda.lambda_handler',
code: awsLambda.AssetCode.fromAsset('lambda.zip'),
functionName: 'LambdaFunction',
role: this.lambdaRole,
});
return lambdaFunction;
}
}

class CloudWatchStack extends Stack {

constructor(app: App, lambdaFunction: awsLambda.Function) {
super(app, 'CloudWatchStack', {});
this.createRule(lambdaFunction);
}

private createRule(lambdaFunction: awsLambda.Function) {

const name = 'CwRule';
const cloudWatchRule: awsEvents.Rule = new awsEvents.Rule(this, name, {
ruleName: name,
schedule: awsEvents.Schedule.expression('cron(0/5 11-23 ? * mon-fri *)'),
enabled: false,
});
/* The addTarget() call will fail because the Lambda and CloudWatch rule are
in separate stacks. */
cloudWatchRule.addTarget(
new awsEventsTargets.LambdaFunction(lambdaFunction, {
event: awsEvents.RuleTargetInput.fromObject({}),
}),
);
}
}

const app = new App();
const lambdaStack = new LambdaStack(app);
new CloudWatchStack(app, lambdaStack.lambdaFunction);
```

### Error Log

```
Error: 'LambdaStack' depends on 'CloudWatchStack' (LambdaStack -> CloudWatchStack/CwRule/Resource.Arn). Adding this dependency (CloudWatchStack -> LambdaStack/LambdaFunction/Resource.Arn) would create a cyclic reference.
```

### Environment

- **CLI Version: 1.32.2**
- **Framework Version: 1.36.0**
- **OS: Mac OS Catalina 10.15.4**
- **Language: TypeScript**

### Other

This is/was a similar issue with API Gateway. The CloudWatch problem was mentioned in the bottom of that issue.
https://github.com/aws/aws-cdk/issues/3000

---

This is :bug: Bug Report

Contributor guide

Open the contributing guide

Research direction

Start by running the provided TypeScript reproduction with `cdk ls` and trace `CloudWatchStack`, `Rule.addTarget()`, and `awsEventsTargets.LambdaFunction` while examining how the two `Stack` instances record dependencies. Compare the behavior with the related API Gateway issue. Done means the example no longer reports a cyclic reference and the two stacks can be synthesized successfully.

Written by the indexing model from the issue text.

Assessment

Tech stack
aws, typescript
Domain
cloud, infrastructure
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Clearly specified
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.