问题
I am trying to use the output of a cloudformation stack in another. I looked at some examoles such as https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/walkthrough-crossstackref.html
but it is very confusing and I could not make it work in my example:
here is what I have: I have a beanstalk.json template and I output the sampleEnvironment I created in resource section:
{
"AWSTemplateFormatVersion": "2010-09-09",
"Resources": {
"sampleApplication": {
"Type": "AWS::ElasticBeanstalk::Application",
"Properties": {
"Description": "AWS Elastic Beanstalk Sample Application",
"ApplicationName": "app-name-test"
}
},
"sampleApplicationVersion": {
"Type": "AWS::ElasticBeanstalk::ApplicationVersion",
"Properties": {
"ApplicationName": {
"Ref": "sampleApplication"
},
"Description": "AWS ElasticBeanstalk Sample Application Version",
"SourceBundle": {
"S3Bucket": "test-war",
"S3Key": "deployment.war"
}
}
},
"sampleConfigurationTemplate": {
"Type": "AWS::ElasticBeanstalk::ConfigurationTemplate",
"Properties": {
"ApplicationName": {
"Ref": "sampleApplication"
},
"Description": "AWS ElasticBeanstalk Sample Configuration Template",
"OptionSettings": [{
"Namespace": "aws:autoscaling:asg",
"OptionName": "MinSize",
"Value": "2"
},
{
"Namespace": "aws:autoscaling:asg",
"OptionName": "MaxSize",
"Value": "3"
},
{
"Namespace": "aws:elasticbeanstalk:environment",
"OptionName": "EnvironmentType",
"Value": "LoadBalanced"
}
],
"SolutionStackName": "64bit Amazon Linux 2017.03 v2.6.1 running Tomcat 8 Java 8"
}
},
"sampleEnvironment": {
"Type": "AWS::ElasticBeanstalk::Environment",
"Properties": {
"ApplicationName": {
"Ref": "sampleApplication"
},
"Description": "AWS ElasticBeanstalk Sample Environment",
"TemplateName": {
"Ref": "sampleConfigurationTemplate"
},
"VersionLabel": {
"Ref": "sampleApplicationVersion"
},
"EnvironmentName": "test-dep-env-name"
}
}
},
"Outputs": {
"applicationName11": {
"Description": "The application chosen by user is :",
"Value": {
"Ref": "sampleEnvironment"
},
"Export" : {
"Name" : {"Ref": "sampleEnvironment"}
}
}
}
Now my problem starts. I need to refer to the name of the sampleEnvironment created in beanstalk.json and assign it to the name of the s3 in resource section in the main template which uses beanstalk.json template. Here is my main tempalte code:
{
"Parameters": {
"appName1": {
"Description": "enter the app name",
"Type": "String",
"Default": "bn-test-jun"
},
"appEnv1": {
"Description": "enter the app name",
"Type": "String",
"Default": "bn-test-jun"
}
},
"Resources": {
"CodeDeployEC2InstancesStack": {
"Type": "AWS::CloudFormation::Stack",
"Properties": {
"TemplateURL": "https://s3.amazonaws.com/url...../beanstalk.json",
"TimeoutInMinutes": "60"
}
},
"myS3": {
"Type": "AWS::S3::Bucket",
"Properties": {
"AccessControl": "PublicRead",
"BucketName": "name of the environment returned as an output sth like Outputs.EnvironmentName"
}
}
}
,
"Outputs":{
"app":{
"Description": "The application chosen by user is :",
"Value": {
"Fn::ImportValue" : "sampleEnvironment"
}
}
}
}
Now you see that in the bucketName section I am stuck. I need to assign the name of the environment created in beanstalk.json to the name of the s3 bucket which is going to be created. How can I do that?
回答1:
I've replied on the CFN course forums
https://acloud.guru/forums/aws-advanced-cloudformation/discussion/-KoAxjlT_ZtSAdrlg1lp/cannot_use_the_output_of_the_i
You dont need to use Export/Import value because you are using nested stacks.
回答2:
The export parameter needs to have an Export property to be accessible to other stacks:
Export (optional)
The name of the resource output to be exported for a cross-stack reference.
Note
The following restrictions apply to cross-stack references:
- For each AWS account, Export names must be unique within a region.
- You can't create cross-stack references across regions.
You can use the intrinsic function Fn::ImportValue to import only values that have been exported within the same region.
For outputs, the value of the Name property of an Export can't use Ref or GetAtt functions that depend on a resource. Similarly, the ImportValue function can't include Ref or GetAtt functions that depend on a resource.
You can't delete a stack if another stack references one of its outputs.
You can't modify or remove an output value that is referenced by another stack.
You can use intrinsic functions to customize the Name value of an export. The following examples use the Fn::Join function.
So add Export property:
"Outputs": {
"applicationName11": {
"Description": "The application chosen by user is :",
"Value": {
"Ref": "sampleEnvironment"
},
"Export" : {
"Name" : {
"Fn::Join" : [ "-", [ { "Ref" : "AWS::StackName" }, {"Ref": "something"} ] ]
}
}
}
}
And then you can import it where necessary via Fn::ImportValue. AWS has a good example.
来源:https://stackoverflow.com/questions/44874005/cannot-use-the-output-of-the-inner-child-template-in-the-parent-template-in-c