gifted-terabyte-92288
12/08/2020, 3:51 PM// file 1 - pulumi.ts
import lambdaFn from './lambda.ts';
const bucket = new aws.s3.Bucket('blake-lambda-bucket');
const endpoint = new awsx.apigateway.API('create', {
routes: [
{
path: '/',
method: 'POST',
eventHandler: lambdaFn
}
]
});
export const lambdaUrl = endpoint.url;
export const bucketId = bucket.id
// file 2 - lambda.ts
import { bucketId } from './pulumi.ts';
async function putStuffInBucket() {
// do things
}
export default putStuffInBucket
File 1 depends on the lambda code in file 2. File 2 depends on file 1 for the bucket name. That seems like a circular dependency, no? I've seen some examples where a string relative path is used to point to a file -- is that the preferred pattern? Can that point to a directory? I've also seen environment variables being set for some lambdas from the Pulumi file and those being consumed via lambda code. Just looking for some guidance on best practices / preferred patterns - thanks!brave-planet-10645
12/08/2020, 4:02 PMputStuffInBucket
etc) in one file, have the api gateway code in another, have the lambda code in another and then your index.tx can orchestrate it all together.gifted-terabyte-92288
12/08/2020, 4:08 PMbrave-planet-10645
12/08/2020, 4:34 PMgifted-terabyte-92288
12/08/2020, 4:41 PMfreezing-finland-22895
12/08/2020, 10:47 PMpulumi.Output
wrapped values for results, instead of top-level exports. Makes it much easier to mix & match your resources as needed (and no weird import-order dependencies).gifted-terabyte-92288
12/09/2020, 2:45 PMpulumi.Output
, but if you have a very simple example of a couple files that'd be super helpful and appreciated!brave-planet-10645
12/09/2020, 4:56 PMOutput
you can use apply and get to the value of it. It's because at run time we might not know what the value is (because the resource may not have been created yet) so you can use apply as a callback.freezing-finland-22895
12/09/2020, 5:05 PMapply
on the value of resourcesDomain.fqdn
in order to construct the URL. apply
is only necessary if you need to work with the value, tho. It could just as is easily return fqdn
directly (which would still have type Output<string>
). The key thing is that, by wrapping everything in a function, I control when these resources are created:
export async function createResourcesSite(apexDomain: string, apiDomain: string): Promise<pulumi.Output<string>> {
const zone = await aws.route53.getZone({ name: apexDomain }),
resourcesDomain = new aws.route53.Record(`...`, {
type: "CNAME",
ttl: 30,
zoneId: zone.zoneId,
records: [apiDomain]
})
return resourcesDomain.fqdn.apply((fqdn) => `https://${fqdn}`)
}
Hope that helps!gifted-terabyte-92288
12/09/2020, 5:26 PM// file 1
function x(bucketId) {
return function y(event) {
// connect to bucket
// derive some data for bucket based on event input
// return lambda result
}
}
// file 2
// when creating the gateway, I end up something like:
const gateway = createApiGateway('gateway', [
{
path: '/',
method: 'GET',
eventHandler: x(bucket.id)
}
]);
Do you run into similar scenarios, or are you grouping the creation of things like that inside your functions?freezing-finland-22895
12/09/2020, 6:41 PMOutput
values using the get
method. So if bucket.id
has type Output<string>
, then you could write:
function (bucketId: Output<string>) {
return function y(event) {
const bucket = bucketId.get()
}
}
When the lambda runs (executes the body of y
), then bucketId.get()
will return the ID of the S3 resource.gifted-terabyte-92288
12/09/2020, 6:47 PM