1 | ;
|
2 | Object.defineProperty(exports, "__esModule", { value: true });
|
3 | exports.npmInstall = void 0;
|
4 | const archiver = require("archiver");
|
5 | const aws_sdk_1 = require("aws-sdk");
|
6 | const child_process_1 = require("child_process");
|
7 | const fs_extra_1 = require("fs-extra");
|
8 | const os_1 = require("os");
|
9 | const path = require("path");
|
10 | const util_1 = require("util");
|
11 | const shared_1 = require("../shared");
|
12 | async function exec(cmds) {
|
13 | let rv = "";
|
14 | for (const cmd of cmds) {
|
15 | rv += (0, child_process_1.execSync)(cmd).toString();
|
16 | }
|
17 | return rv;
|
18 | }
|
19 | async function npmInstall({ LayerName, packageJsonContents, FunctionName, region, quiet, retentionInDays }) {
|
20 | const log = quiet ? (_) => { } : console.log;
|
21 | log(`*** This faast invocation is an internal lambda call used when the packageJson option is specified to createFunction(). ***`);
|
22 | log(`*** Its purpose is to create a node_modules package and cache it, then combine with user code to form an AWS Lambda code package and upload it to S3 ***`);
|
23 | const buildParentDir = path.join((0, os_1.tmpdir)(), FunctionName);
|
24 | const buildDir = path.join(buildParentDir, "nodejs");
|
25 | await (0, fs_extra_1.ensureDir)(buildDir);
|
26 | await (0, fs_extra_1.writeFile)(path.join(buildDir, "package.json"), packageJsonContents);
|
27 | const awsconfig = { correctClockSkew: true, maxRetries: 6 };
|
28 | let installLog = "";
|
29 | log("Checking cache");
|
30 | log(`Checking faast layers for ${LayerName}`);
|
31 | const lambda = new aws_sdk_1.Lambda({ apiVersion: "2015-03-31", region, ...awsconfig });
|
32 | const cached = await lambda
|
33 | .listLayerVersions({ LayerName, CompatibleRuntime: "nodejs" })
|
34 | .promise()
|
35 | .catch(_ => undefined);
|
36 | const layerVersion = cached?.LayerVersions?.[0];
|
37 | if (layerVersion && !(0, shared_1.hasExpired)(layerVersion.CreatedDate, retentionInDays)) {
|
38 | const layerInfo = {
|
39 | LayerName,
|
40 | Version: layerVersion.Version,
|
41 | LayerVersionArn: layerVersion.LayerVersionArn
|
42 | };
|
43 | log(`CACHED, ${(0, util_1.inspect)(layerInfo)}`);
|
44 | return { installLog, layerInfo };
|
45 | }
|
46 | log("NOT CACHED, running npm install");
|
47 | installLog += await exec([`echo "hello world"`]);
|
48 | installLog += await exec([
|
49 | `export HOME=/tmp; npm install --prefix=${buildDir} --no-package-lock`
|
50 | ]);
|
51 | log(`Running archiver`);
|
52 | const cacheArchive = archiver("zip", { zlib: { level: 8 } });
|
53 | cacheArchive.directory(buildParentDir, false).finalize();
|
54 | log(`Converting archive to buffer`);
|
55 | const ZipFile = await (0, shared_1.streamToBuffer)(cacheArchive);
|
56 | log(`Code ZipFile size: ${ZipFile.length}`);
|
57 | log(`Removing ${buildParentDir}`);
|
58 | const removePromise = (0, fs_extra_1.remove)(buildParentDir);
|
59 | let Content;
|
60 | const Bucket = FunctionName;
|
61 | const s3 = new aws_sdk_1.S3({ region, ...awsconfig });
|
62 | const zipSize = ZipFile.length;
|
63 | try {
|
64 | if (ZipFile.length > 50 * 2 ** 20) {
|
65 | // Try to use S3 to allow for a larger limit
|
66 | log(`Creating s3 bucket ${Bucket}`);
|
67 | await s3
|
68 | .createBucket({ Bucket })
|
69 | .promise()
|
70 | .catch(_ => { });
|
71 | log(`Uploading bucket: ${Bucket}, object: ${LayerName}`);
|
72 | await s3.upload({ Bucket, Key: LayerName, Body: ZipFile }).promise();
|
73 | Content = { S3Bucket: Bucket, S3Key: LayerName };
|
74 | }
|
75 | else {
|
76 | Content = { ZipFile };
|
77 | }
|
78 | log(`Creating lambda layer: ${LayerName}, zip file size: ${ZipFile.length}`);
|
79 | const publishResponse = await lambda
|
80 | .publishLayerVersion({
|
81 | LayerName,
|
82 | Description: `faast packageJson layer with LayerName ${LayerName}`,
|
83 | Content,
|
84 | CompatibleRuntimes: ["nodejs"]
|
85 | })
|
86 | .promise();
|
87 | const { Version } = publishResponse;
|
88 | log(`Created lambda layer: ${LayerName}:${Version}`);
|
89 | log(`DONE`);
|
90 | return {
|
91 | installLog,
|
92 | layerInfo: {
|
93 | LayerName,
|
94 | LayerVersionArn: publishResponse.LayerVersionArn,
|
95 | Version: publishResponse.Version
|
96 | },
|
97 | zipSize
|
98 | };
|
99 | }
|
100 | finally {
|
101 | if (Content?.S3Bucket) {
|
102 | try {
|
103 | await s3.deleteObject({ Bucket, Key: LayerName }).promise();
|
104 | await s3.deleteBucket({ Bucket }).promise();
|
105 | }
|
106 | catch { }
|
107 | }
|
108 | await removePromise;
|
109 | }
|
110 | }
|
111 | exports.npmInstall = npmInstall;
|
112 | //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXdzLW5wbS5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uL3NyYy9hd3MvYXdzLW5wbS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7QUFBQSxxQ0FBcUM7QUFDckMscUNBQXFDO0FBQ3JDLGlEQUF5QztBQUN6Qyx1Q0FBd0Q7QUFDeEQsMkJBQTRCO0FBQzVCLDZCQUE2QjtBQUM3QiwrQkFBK0I7QUFDL0Isc0NBQXVEO0FBRXZELEtBQUssVUFBVSxJQUFJLENBQUMsSUFBYztJQUM5QixJQUFJLEVBQUUsR0FBRyxFQUFFLENBQUM7SUFDWixLQUFLLE1BQU0sR0FBRyxJQUFJLElBQUksRUFBRTtRQUNwQixFQUFFLElBQUksSUFBQSx3QkFBUSxFQUFDLEdBQUcsQ0FBQyxDQUFDLFFBQVEsRUFBRSxDQUFDO0tBQ2xDO0lBQ0QsT0FBTyxFQUFFLENBQUM7QUFDZCxDQUFDO0FBdUJNLEtBQUssVUFBVSxVQUFVLENBQUMsRUFDN0IsU0FBUyxFQUNULG1CQUFtQixFQUNuQixZQUFZLEVBQ1osTUFBTSxFQUNOLEtBQUssRUFDTCxlQUFlLEVBQ0Y7SUFDYixNQUFNLEdBQUcsR0FBRyxLQUFLLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBUyxFQUFFLEVBQUUsR0FBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUM7SUFFcEQsR0FBRyxDQUNDLDZIQUE2SCxDQUNoSSxDQUFDO0lBQ0YsR0FBRyxDQUNDLDBKQUEwSixDQUM3SixDQUFDO0lBRUYsTUFBTSxjQUFjLEdBQUcsSUFBSSxDQUFDLElBQUksQ0FBQyxJQUFBLFdBQU0sR0FBRSxFQUFFLFlBQVksQ0FBQyxDQUFDO0lBQ3pELE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsY0FBYyxFQUFFLFFBQVEsQ0FBQyxDQUFDO0lBQ3JELE1BQU0sSUFBQSxvQkFBUyxFQUFDLFFBQVEsQ0FBQyxDQUFDO0lBQzFCLE1BQU0sSUFBQSxvQkFBUyxFQUFDLElBQUksQ0FB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RUFBRSxNQUFNLEVBQUUsR0FBRyxFQUFFLFNBQVMsRUFBRSxDQUFDLENBQUMsT0FBTyxFQUFFLENBQUM7Z0JBQzVELE1BQU0sRUFBRSxDQUFDLFlBQVksQ0FBQyxFQUFFLE1BQU0sRUFBRSxDQUFDLENBQUMsT0FBTyxFQUFFLENBQUM7YUFDL0M7WUFBQyxNQUFNLEdBQUU7U0FDYjtRQUNELE1BQU0sYUFBYSxDQUFDO0tBQ3ZCO0FBQ0wsQ0FBQztBQTFHRCxnQ0EwR0MiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgKiBhcyBhcmNoaXZlciBmcm9tIFwiYXJjaGl2ZXJcIjtcbmltcG9ydCB7IExhbWJkYSwgUzMgfSBmcm9tIFwiYXdzLXNka1wiO1xuaW1wb3J0IHsgZXhlY1N5bmMgfSBmcm9tIFwiY2hpbGRfcHJvY2Vzc1wiO1xuaW1wb3J0IHsgZW5zdXJlRGlyLCByZW1vdmUsIHdyaXRlRmlsZSB9IGZyb20gXCJmcy1leHRyYVwiO1xuaW1wb3J0IHsgdG1wZGlyIH0gZnJvbSBcIm9zXCI7XG5pbXBvcnQgKiBhcyBwYXRoIGZyb20gXCJwYXRoXCI7XG5pbXBvcnQgeyBpbnNwZWN0IH0gZnJvbSBcInV0aWxcIjtcbmltcG9ydCB7IHN0cmVhbVRvQnVmZmVyLCBoYXNFeHBpcmVkIH0gZnJvbSBcIi4uL3NoYXJlZFwiO1xuXG5hc3luYyBmdW5jdGlvbiBleGVjKGNtZHM6IHN0cmluZ1tdKSB7XG4gICAgbGV0IHJ2ID0gXCJcIjtcbiAgICBmb3IgKGNvbnN0IGNtZCBvZiBjbWRzKSB7XG4gICAgICAgIHJ2ICs9IGV4ZWNTeW5jKGNtZCkudG9TdHJpbmcoKTtcbiAgICB9XG4gICAgcmV0dXJuIHJ2O1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIE5wbUluc3RhbGxBcmdzIHtcbiAgICBwYWNrYWdlSnNvbkNvbnRlbnRzOiBzdHJpbmc7XG4gICAgTGF5ZXJOYW1lOiBzdHJpbmc7XG4gICAgRnVuY3Rpb25OYW1lOiBzdHJpbmc7XG4gICAgcmVnaW9uOiBzdHJpbmc7XG4gICAgcXVpZXQ/OiBib29sZWFuO1xuICAgIHJldGVudGlvbkluRGF5czogbnVtYmVyO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIEF3c0xheWVySW5mbyB7XG4gICAgVmVyc2lvbjogbnVtYmVyO1xuICAgIExheWVyVmVyc2lvbkFybjogc3RyaW5nO1xuICAgIExheWVyTmFtZTogc3RyaW5nO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIE5wbUluc3RhbGxSZXR1cm4ge1xuICAgIGluc3RhbGxMb2c6IHN0cmluZztcbiAgICBsYXllckluZm86IEF3c0xheWVySW5mbztcbiAgICB6aXBTaXplPzogbnVtYmVyO1xufVxuXG5leHBvcnQgYXN5bmMgZnVuY3Rpb24gbnBtSW5zdGFsbCh7XG4gICAgTGF5ZXJOYW1lLFxuICAgIHBhY2thZ2VKc29uQ29udGVudHMsXG4gICAgRnVuY3Rpb25OYW1lLFxuICAgIHJlZ2lvbixcbiAgICBxdWlldCxcbiAgICByZXRlbnRpb25JbkRheXNcbn06IE5wbUluc3RhbGxBcmdzKTogUHJvbWlzZTxOcG1JbnN0YWxsUmV0dXJuPiB7XG4gICAgY29uc3QgbG9nID0gcXVpZXQgPyAoXzogc3RyaW5nKSA9PiB7fSA6IGNvbnNvbGUubG9nO1xuXG4gICAgbG9nKFxuICAgICAgICBgKioqIFRoaXMgZmFhc3QgaW52b2NhdGlvbiBpcyBhbiBpbnRlcm5hbCBsYW1iZGEgY2FsbCB1c2VkIHdoZW4gdGhlIHBhY2thZ2VKc29uIG9wdGlvbiBpcyBzcGVjaWZpZWQgdG8gY3JlYXRlRnVuY3Rpb24oKS4gKioqYFxuICAgICk7XG4gICAgbG9nKFxuICAgICAgICBgKioqIEl0cyBwdXJwb3NlIGlzIHRvIGNyZWF0ZSBhIG5vZGVfbW9kdWxlcyBwYWNrYWdlIGFuZCBjYWNoZSBpdCwgdGhlbiBjb21iaW5lIHdpdGggdXNlciBjb2RlIHRvIGZvcm0gYW4gQVdTIExhbWJkYSBjb2RlIHBhY2thZ2UgYW5kIHVwbG9hZCBpdCB0byBTMyAqKipgXG4gICAgKTtcblxuICAgIGNvbnN0IGJ1aWxkUGFyZW50RGlyID0gcGF0aC5qb2luKHRtcGRpcigpLCBGdW5jdGlvbk5hbWUpO1xuICAgIGNvbnN0IGJ1aWxkRGlyID0gcGF0aC5qb2luKGJ1aWxkUGFyZW50RGlyLCBcIm5vZGVqc1wiKTtcbiAgICBhd2FpdCBlbnN1cmVEaXIoYnVpbGREaXIpO1xuICAgIGF3YWl0IHdyaXRlRmlsZShwYXRoLmpvaW4oYnVpbGREaXIsIFwicGFja2FnZS5qc29uXCIpLCBwYWNrYWdlSnNvbkNvbnRlbnRzKTtcblxuICAgIGNvbnN0IGF3c2NvbmZpZyA9IHsgY29ycmVjdENsb2NrU2tldzogdHJ1ZSwgbWF4UmV0cmllczogNiB9O1xuXG4gICAgbGV0IGluc3RhbGxMb2cgPSBcIlwiO1xuICAgIGxvZyhcIkNoZWNraW5nIGNhY2hlXCIpO1xuICAgIGxvZyhgQ2hlY2tpbmcgZmFhc3QgbGF5ZXJzIGZvciAke0xheWVyTmFtZX1gKTtcbiAgICBjb25zdCBsYW1iZGEgPSBuZXcgTGFtYmRhKHsgYXBpVmVyc2lvbjogXCIyMDE1LTAzLTMxXCIsIHJlZ2lvbiwgLi4uYXdzY29uZmlnIH0pO1xuXG4gICAgY29uc3QgY2FjaGVkID0gYXdhaXQgbGFtYmRhXG4gICAgICAgIC5saXN0TGF5ZXJWZXJzaW9ucyh7IExheWVyTmFtZSwgQ29tcGF0aWJsZVJ1bnRpbWU6IFwibm9kZWpzXCIgfSlcbiAgICAgICAgLnByb21pc2UoKVxuICAgICAgICAuY2F0Y2goXyA9PiB1bmRlZmluZWQpO1xuXG4gICAgY29uc3QgbGF5ZXJWZXJzaW9uID0gY2FjaGVkPy5MYXllclZlcnNpb25zPy5bMF07XG4gICAgaWYgKGxheWVyVmVyc2lvbiAmJiAhaGFzRXhwaXJlZChsYXllclZlcnNpb24uQ3JlYXRlZERhdGUsIHJldGVudGlvbkluRGF5cykpIHtcbiAgICAgICAgY29uc3QgbGF5ZXJJbmZvID0ge1xuICAgICAgICAgICAgTGF5ZXJOYW1lLFxuICAgICAgICAgICAgVmVyc2lvbjogbGF5ZXJWZXJzaW9uLlZlcnNpb24hLFxuICAgICAgICAgICAgTGF5ZXJWZXJzaW9uQXJuOiBsYXllclZlcnNpb24uTGF5ZXJWZXJzaW9uQXJuIVxuICAgICAgICB9O1xuICAgICAgICBsb2coYENBQ0hFRCwgJHtpbnNwZWN0KGxheWVySW5mbyl9YCk7XG4gICAgICAgIHJldHVybiB7IGluc3RhbGxMb2csIGxheWVySW5mbyB9O1xuICAgIH1cblxuICAgIGxvZyhcIk5PVCBDQUNIRUQsIHJ1bm5pbmcgbnBtIGluc3RhbGxcIik7XG4gICAgaW5zdGFsbExvZyArPSBhd2FpdCBleGVjKFtgZWNobyBcImhlbGxvIHdvcmxkXCJgXSk7XG4gICAgaW5zdGFsbExvZyArPSBhd2FpdCBleGVjKFtcbiAgICAgICAgYGV4cG9ydCBIT01FPS90bXA7IG5wbSBpbnN0YWxsIC0tcHJlZml4PSR7YnVpbGREaXJ9IC0tbm8tcGFja2FnZS1sb2NrYFxuICAgIF0pO1xuICAgIGxvZyhgUnVubmluZyBhcmNoaXZlcmApO1xuICAgIGNvbnN0IGNhY2hlQXJjaGl2ZSA9IGFyY2hpdmVyKFwiemlwXCIsIHsgemxpYjogeyBsZXZlbDogOCB9IH0pO1xuICAgIGNhY2hlQXJjaGl2ZS5kaXJlY3RvcnkoYnVpbGRQYXJlbnREaXIsIGZhbHNlKS5maW5hbGl6ZSgpO1xuICAgIGxvZyhgQ29udmVydGluZyBhcmNoaXZlIHRvIGJ1ZmZlcmApO1xuICAgIGNvbnN0IFppcEZpbGUgPSBhd2FpdCBzdHJlYW1Ub0J1ZmZlcihjYWNoZUFyY2hpdmUpO1xuICAgIGxvZyhgQ29kZSBaaXBGaWxlIHNpemU6ICR7WmlwRmlsZS5sZW5ndGh9YCk7XG4gICAgbG9nKGBSZW1vdmluZyAke2J1aWxkUGFyZW50RGlyfWApO1xuICAgIGNvbnN0IHJlbW92ZVByb21pc2UgPSByZW1vdmUoYnVpbGRQYXJlbnREaXIpO1xuICAgIGxldCBDb250ZW50OiBMYW1iZGEuTGF5ZXJWZXJzaW9uQ29udGVudElucHV0IHwgdW5kZWZpbmVkO1xuICAgIGNvbnN0IEJ1Y2tldCA9IEZ1bmN0aW9uTmFtZTtcbiAgICBjb25zdCBzMyA9IG5ldyBTMyh7IHJlZ2lvbiwgLi4uYXdzY29uZmlnIH0pO1xuICAgIGNvbnN0IHppcFNpemUgPSBaaXBGaWxlLmxlbmd0aDtcbiAgICB0cnkge1xuICAgICAgICBpZiAoWmlwRmlsZS5sZW5ndGggPiA1MCAqIDIgKiogMjApIHtcbiAgICAgICAgICAgIC8vIFRyeSB0byB1c2UgUzMgdG8gYWxsb3cgZm9yIGEgbGFyZ2VyIGxpbWl0XG4gICAgICAgICAgICBsb2coYENyZWF0aW5nIHMzIGJ1Y2tldCAke0J1Y2tldH1gKTtcbiAgICAgICAgICAgIGF3YWl0IHMzXG4gICAgICAgICAgICAgICAgLmNyZWF0ZUJ1Y2tldCh7IEJ1Y2tldCB9KVxuICAgICAgICAgICAgICAgIC5wcm9taXNlKClcbiAgICAgICAgICAgICAgICAuY2F0Y2goXyA9PiB7fSk7XG4gICAgICAgICAgICBsb2coYFVwbG9hZGluZyBidWNrZXQ6ICR7QnVja2V0fSwgb2JqZWN0OiAke0xheWVyTmFtZX1gKTtcbiAgICAgICAgICAgIGF3YWl0IHMzLnVwbG9hZCh7IEJ1Y2tldCwgS2V5OiBMYXllck5hbWUsIEJvZHk6IFppcEZpbGUgfSkucHJvbWlzZSgpO1xuICAgICAgICAgICAgQ29udGVudCA9IHsgUzNCdWNrZXQ6IEJ1Y2tldCwgUzNLZXk6IExheWVyTmFtZSB9O1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgQ29udGVudCA9IHsgWmlwRmlsZSB9O1xuICAgICAgICB9XG4gICAgICAgIGxvZyhgQ3JlYXRpbmcgbGFtYmRhIGxheWVyOiAke0xheWVyTmFtZX0sIHppcCBmaWxlIHNpemU6ICR7WmlwRmlsZS5sZW5ndGh9YCk7XG4gICAgICAgIGNvbnN0IHB1Ymxpc2hSZXNwb25zZSA9IGF3YWl0IGxhbWJkYVxuICAgICAgICAgICAgLnB1Ymxpc2hMYXllclZlcnNpb24oe1xuICAgICAgICAgICAgICAgIExheWVyTmFtZSxcbiAgICAgICAgICAgICAgICBEZXNjcmlwdGlvbjogYGZhYXN0IHBhY2thZ2VKc29uIGxheWVyIHdpdGggTGF5ZXJOYW1lICR7TGF5ZXJOYW1lfWAsXG4gICAgICAgICAgICAgICAgQ29udGVudCxcbiAgICAgICAgICAgICAgICBDb21wYXRpYmxlUnVudGltZXM6IFtcIm5vZGVqc1wiXVxuICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIC5wcm9taXNlKCk7XG4gICAgICAgIGNvbnN0IHsgVmVyc2lvbiB9ID0gcHVibGlzaFJlc3BvbnNlO1xuICAgICAgICBsb2coYENyZWF0ZWQgbGFtYmRhIGxheWVyOiAke0xheWVyTmFtZX06JHtWZXJzaW9ufWApO1xuICAgICAgICBsb2coYERPTkVgKTtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICAgIGluc3RhbGxMb2csXG4gICAgICAgICAgICBsYXllckluZm86IHtcbiAgICAgICAgICAgICAgICBMYXllck5hbWUsXG4gICAgICAgICAgICAgICAgTGF5ZXJWZXJzaW9uQXJuOiBwdWJsaXNoUmVzcG9uc2UuTGF5ZXJWZXJzaW9uQXJuISxcbiAgICAgICAgICAgICAgICBWZXJzaW9uOiBwdWJsaXNoUmVzcG9uc2UuVmVyc2lvbiFcbiAgICAgICAgICAgIH0sXG4gICAgICAgICAgICB6aXBTaXplXG4gICAgICAgIH07XG4gICAgfSBmaW5hbGx5IHtcbiAgICAgICAgaWYgKENvbnRlbnQ/LlMzQnVja2V0KSB7XG4gICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgIGF3YWl0IHMzLmRlbGV0ZU9iamVjdCh7IEJ1Y2tldCwgS2V5OiBMYXllck5hbWUgfSkucHJvbWlzZSgpO1xuICAgICAgICAgICAgICAgIGF3YWl0IHMzLmRlbGV0ZUJ1Y2tldCh7IEJ1Y2tldCB9KS5wcm9taXNlKCk7XG4gICAgICAgICAgICB9IGNhdGNoIHt9XG4gICAgICAgIH1cbiAgICAgICAgYXdhaXQgcmVtb3ZlUHJvbWlzZTtcbiAgICB9XG59XG4iXX0= |
\ | No newline at end of file |