Hello , I am attempting to assign a value to the ‘userData’ attribute while incorporating conditions that determine the specific value to be assigned. I aim to express these conditions in the same line as the assignment statement:
userData: conditional(Op.neq(platform,“windows”),linuxScripts,windowsScripts ) ,
these are my vars :
const windowsScripts= fs.readFileSync(‘…/scripts/user-data.ps1’,‘utf-8’) ;
const linuxScripts=fs.readFileSync(‘…/scripts/user-data.sh’,‘utf-8’) ;
and i got “Type ‘ConditionalExpression’ is not assignable to type ‘string’”.
And in order to solve this i was trying to use addOverride and conditions : instance.addOverride(“user_data”,conditional(Op.neq(platform,“windows”),linuxScripts,windowsScripts )).
And of course non of them works .
Hi @ramzi-af 
You could try to wrap the conditional(...)
in Token.asString()
which would tell CDKTF to treat the result of conditional()
as a string.
– Ansgar
@ansgarm Thank you, but a new error has occurred :
my code :
// Resources
const instance=new Instance(this, "instance", {
ebsOptimized:true,
iamInstanceProfile:iam.outputs["SystemsInstanceProfileName"],
ami :"image",
instanceType: "t2.micro",
keyName:env.outputs["AdminKeyPair"] ,
vpcSecurityGroupIds
:locals.expression["security_groups"] ,
subnetId:Token.asString(conditional(Op.neq(subnet.value,null),subnet.value,locals.expression["subnet"])) ,
rootBlockDevice:{
volumeSize: commonVars.rootVolumeSize.value
},
userData: Token.asString(conditional(Op.neq(platform.value,"linux"),windowsScripts ,linuxScripts)),
tags:generic_tags
}).
Error description
Error: Invalid reference
│
│ on cdk.tf.json line 76, in resource.aws_instance.instance (instance):
│ 76: "subnet_id": "${(var.subnet != undefined) ? var.subnet : undefined}",
│
│ A reference to a resource type must be followed by at least one attribute
│ access, specifying the resource name.
Thank you very much @ansgarm, I appreciate your help.
@ansgarm
It seems like I’m missing something ,
Firstly, when comparing subnet.value with null, it should be compared with Token.asNull(). Secondly, it seems that the datasource is being accessed incorrectly by using env.outputs[“AdminKeyPair”].
The correct version will look like this :
// Resources
const instance = new Instance(this, "instance", {
ebsOptimized: true,
iamInstanceProfile: iam.outputs["SystemsInstanceProfileName"],
ami: "image",
instanceType: "t2.micro",
//"AdminKeyPair"
//How to work with datasources
keyName: Fn.lookup(env.getStringMapAttribute("outputs"), "AdminKeyPair", Token.nullValue()), //is there any thing better than this
vpcSecurityGroupIds: locals.expression["security_groups"],
subnetId: Token.asString(
conditional(
Op.neq(
commonVars.subnet.value,
Token.nullValue()
),
commonVars.subnet.value, env.getStringAttribute("outputs[\"DefaultSubnet\"],")
)
),
rootBlockDevice: {
volumeSize: commonVars.rootVolumeSize.value
},
userData: Token.asString(
conditional(
Op.neq(commonVars.platform.value, "linux"),
Fn.file(powershell.path),
Fn.file(linux.path)
)
),
tags: generic_tags,
})
but is there a more effective way to access data sources than the current method?