áááºá¹ááá¬ááá»ááºážáá« áá°áááºáá»ááºážááá¯á·á ááŸá¯ááºážááŒáá·áº á
á®ážáááºážááŸá¯á¡áá
áºáá
áºáᯠá
áááºááẠáá»áŸá±á¬áºááá·áºáá«áááºá
á¡ááŒá±áá¶á¡áá±á¬ááºá¡áŠáá¯áẠ(Infrastructure as Code) á¡ááœáẠPulumi ááŸáá·áº áá±áá¯áá»áááºááœááºáá»áẠáááá¯ááááºáá¬áá¬á
áá¬ážáá»á¬ážááᯠá¡áá¯á¶ážááŒá¯ááŒááºážááẠá¡á¬ážáá¬áá»ááºáá»á¬ážá
áœá¬ááᯠáá±ážáá±á¬ááºáááº- áá»áœááºážáá»ááºááŸá¯ááŸáá·áº á¡ááááá¬áááŸáááá¯ááºááŸá¯á abstraction ááŸáááá·áº áá¯ááºá¡ááœááºážááŸá boilerplate áááºááŸá¬ážáá±ážá IDEs ááŸáá·áº linters áá²á·ááá¯á·áá±á¬ ááá·áºá¡ááœá²á·ááŸáá·áºáááºážááŸá®ážáá±á¬ áááááá¬áá»á¬ážá á€áá±á¬á·ááºáá²ááºá¡ááºáá»ááºáá®áᬠáááááá¬áá»á¬ážá¡á¬ážáá¯á¶ážááẠáá»áœááºá¯ááºááá¯á·ááᯠááá¯ááá¯á¡áá»áá¯ážááŒá
áºááœááºážá
á±áá¯á¶áá¬áá áá»áœááºá¯ááºááá¯á·ááá¯ááºá¡áááºá¡ááœá±ážááá¯áááºáž ááŒáŸáá·áºáááºáá±ážáá«áááºá ááá¯á·ááŒá±á¬áá·áºá áá±áá°áá»áááºááœááºáá»ááºááŒáá·áº áááá¯ááááºážáááºážáá¬áá¬á
áá¬ážáá»á¬ážááá¯á¡áá¯á¶ážááŒá¯ááŒááºážááẠáá»áœááºá¯ááºááá¯á·á¡á¬áž á¡áá±ážááŒá®ážáá±á¬áá±á¬á·ááºáá²ááºááœá¶á·ááŒáá¯ážááá¯ážáááºáá±ážá¡áá±á·á¡áá»áá·áºááᯠááááºáááºáá±ážááá¯ááºá
á±áááºááŸá¬ ááá¬ááá»áá«áááºá á
ááºážáááºááŒááºáž.
á€áá±á¬ááºážáá«ážááœááºá Pulumi ááẠáá»áœááºá¯ááºááá¯á·á¡á¬áž áá»áœááºá¯ááºááá¯á·á á¡ááŒá±áá¶á¡áá±á¬ááºá¡áŠ-á¡ááŒá áº-áá¯ááºááᯠá ááºážáááºááẠáááºááá¯á·áá°áá®áá±ážáááºááᯠááŒáá·áºááŸá¯áá«áááºá
á¡ááŒá±áá¶á¡áá±á¬ááºá¡á¡á¯á¶ááᯠáá¬ááŒá±á¬áá·áº á ááºážáááºáá¬áá²á
á¡áá±ážá áááºááá±á·áá¬áá®á âáá¬ááŒá±á¬áá·áº á¡ááŒá±áá¶á¡áá±á¬ááºá¡á¡á¯á¶ááᯠá ááºážáááºáá¬áá²â ááá¯áá²á· áá±ážááœááºážááᯠáá±ážááá·áºáááºá áááºážá¡ááœáẠá¡ááŒá±á¬ááºážáááºážáá»á¬ážá áœá¬ááŸáááŒá®áž á€á¡áá¬áá»á¬ážáá²á០á¡áá»áá¯á·ááŸá¬-
- ááá·áºáááá¯ááááºáá¯áá¹áááá±áá áá áºáá®ážáá¯áá¹áááá¯ááºáá±á¬ááºáá»ááºáá»á¬áž ááá¯á·ááá¯áẠá¡ááá¯ááºážá¡á áá»á¬ážááᯠá ááºážáááºááŒááºážá
- á¡áá»áá¯á·áá±á¬ ááá·áºáááºáá»ááºáá»á¬ážááᯠááá·áºáá»ááºá á¡ááŒá±áá¶á¡áá±á¬ááºá¡á¡á¯á¶á á¡ááá¯ááŸááá±á¬ á¡ááŒá±á¡áá±á¡á¬áž á¡áááºááŒá¯áááºá
- ááá¯ááŸá±á¬ááºááŸá¯áá¯á¶ážá áá¯ááºáá¯ááºáááŸáááŒááºáž ááá¯á·ááá¯áẠá¡áá¬á¡ááœááºáááŸáááŒááºážáá²á·ááá¯á·áá±á¬ áá¯á¶á¡ááŸá¬ážá¡ááœááºážáá»á¬ážááᯠáá±á¬ááºááŸááºážááŒááºážááẠá¡ááºáá¬áááºá០á¡áá¯á¡áá±á¬ááºá ááºáá»á¬ážááá¯á· ááœáá·áºáááºáá±á¬ááºááŒááºáž ááŒá áºáááºá
- á¡ááŒá±áá¶á¡áá±á¬ááºá¡á¡á¯á¶áá»á¬áž áá»áá¬ážáá±áž á¡áá±á¬ááºá¡áááºáá±á¬áºááŸá¯ááᯠá á áºáá±ážááŒááºážá
- á á®áá¶áá±á¬ááºááœááºáá±ážááŒá®ážáá±á¬áẠáá¯ááºáá±á¬ááºááá¯ááºá áœááºážááᯠá á áºáá±ážáááºá¡ááœáẠáááºá "áááá¯ááááºááá·áºááœááºážáá¬ážáá±á¬" á¡ááŒá±áá¶á¡áá±á¬ááºá¡á¡á¯á¶á¡ááœááºáž áá¯ááºáá±á¬ááºáá±ááá·áº á¡ááºááºáá±á¬á·áá»á áºá á¡ááŒá±ážá¡áá»áááºááᯠá ááºážáááºááŒááºážá
- áá»áœááºá¯ááºááá¯á·ááŒááºááá¯ááºáááºá¡ááá¯ááºážá á¡ááŒá±áá¶á¡áá±á¬ááºá¡á¡á¯á¶á ááºážáááºááŒááºážááœá±ážáá»ááºá áá¬áá»á¬ážáá»ááºááŒáá·áºá áœá¬ááŸááááºá Polumi ááœáẠဠspectrum áá±á«áºááŸá á¡áá»ááºááá¯ááºážááœáẠá ááºážáááºááẠááá¹ááá¬ážáá»á¬áž ááŸááááºá á áááºááŒá®áž áááºááá¯á¡áá¯ááºáá¯ááºáá² ááŒáá·áºáá¡á±á¬ááºá
áá°áá áºá ááºážáááºááŒááºážá
Pulumi áááá¯ááááºáá»á¬ážááᯠJavaScriptá Pythoná TypeScript ááá¯á·ááá¯áẠGo áá²á·ááá¯á·áá±á¬ áá±áá¯áá»áááºááœááºáá»áẠáááá¯ááááºážáááºážáá¬áá¬á áá¬ážáá»á¬ážááŒáá·áº áá±ážáá¬ážáá¬ážáááºá ááá¯á·ááŒá±á¬áá·áºá á ááºážáááºááŸá¯áá±á¬ááºáá»á¬ážá¡áá«á¡ááẠáááºážááá¯á·ááááááá¬áá»á¬ážááŸáá·áº á á¬ááŒáá·áºááá¯ááºáá»á¬áž á¡áá«á¡ááẠá€áá¬áá¬á áá¬ážáá»á¬ážá á áœááºážá¡á¬ážá¡ááŒáá·áºááᯠáááºážááá¯á·á¡ááœáẠáááŸáááá¯ááºáá«áááºá Pulumi ááẠMulti-cloud ááŒá áºáááºá ááá¯ááá¯áááºááŸá¬ áááºážááᯠáááºááá·áº cloud áááºáá±á¬ááºááŸá¯áá±ážáá°áá¶ááŸáááᯠá ááºážáááºáááºá¡ááœáẠá¡áá¯á¶ážááŒá¯ááá¯ááºáááºá
(á€áá±á¬ááºážáá«ážááœááºá áá¬áá¬á
áá¬ážáá±á«ááºážá
á¯á¶ááŸáá·áº multicloud ááŒá
áºááá·áºáá
á¬ážá áá»áœááºá¯ááºááá¯á·ááẠJavaScript ááŸáá·áº Mocha ááá¯á¡áá¯á¶ážááŒá¯ááŒá®áž AWS ááá¯á¡á¬áá¯á¶á
áá¯ááºáá«á áááºááẠPython ááá¯áá¯á¶ážááá¯ááºáááºá unittest
á
ááºážáááºááŸá¯áá±á¬ááºááᯠááœá¬ážáá«á ááá¯á·ááá¯áẠáááºááŸá
áºáááºááá·áº á¡ááŒá¬ážá
ááºážáááºááŸá¯áá±á¬ááºááᯠááœá¬ážáá«á Pulumi ááẠAzureá Google Cloudá Kubernetes ááá¯á·ááŸáá·áº áá±á¬ááºážááœááºá
áœá¬á¡áá¯ááºáá¯ááºáá«áááºá)
áá»áœááºá¯ááºááá¯á·ááœá±á·ááŒááºáááá·áºá¡ááá¯ááºážá áááºááẠáááºáá¡ááŒá±áá¶á¡áá±á¬ááºá¡á¡á¯á¶áá¯ááºááᯠá
ááºážáááºááá¯ááá·áº á¡ááŒá±á¬ááºážáááºážáá»á¬ážá
áœá¬ááŸááá«áááºá áááºážááá¯á·áá²ááŸáá
áºáá¯ááŸá¬ ááá¬ážááá¯ážáá» áá°áá
áºá
ááºážáááºááŒááºáž ááŒá
áºáááºá ááá·áºáá¯ááºááœáẠáá¯ááºáá±á¬ááºáá»ááºáá»á¬áž ááŸáááá¯ááºáá±á¬ááŒá±á¬áá·áº - á¥ááá¬á CIDR ááᯠááœááºáá»ááºáááºá ááá¯ááºážááá
áºááŒáá·áº ááœááºáá»ááºáá±á¬ á¡áááºáá»á¬ážá áááºáá»á¬áž á
áááºááŒáá·áºá - áááºáá°ááá¯á·ááᯠá
ááºážáááºáá»ááºáá±áááá·áºáááºá áááºážááẠáááºááŸá
áºáááºáá±á¬ áááá¯ááááºážáááºážáá¬áá¬á
áá¬ážááŒáá·áº á¡ááºááºáá®áá±ážááŸááºážáá»á¬ážá¡ááœáẠáá¯á¶ááŸááºáá°áá
áºá
á
áºáá±ážááŸá¯áá»á¬ážááᯠáá±ážáá¬ážááŒááºážááŸáá·áº á¡áá°áá°áááºááŒá
áºáá«áááºá
á¡áááºážáááºááá¯ááá¯ááŸá¯ááºááœá±ážá
á±áááºá ááá·áºáááá¯ááááºááẠá¡áááºážá¡ááŒá
áºáá»á¬ážááᯠáááºááá¯á·ááœá²áá±áá±ážáááºááᯠá
á
áºáá±ážááá¯ááºáá«áááºá á¥ááá¬á¡áá±ááŒáá·áºá áá»áœááºá¯ááºááá¯á·ááẠááá¯ážááŸááºážáá±á¬ EC2 áá¬áá¬ááᯠáááºáá®ážááẠááá¯á¡ááºááŒá®áž á¡á±á¬ááºáá«ááá¯á·ááᯠáá±áá»á¬á
á±ááá¯áá«áááº-
- áá¬áááá»á¬ážááœáẠtag áá
áºáá¯ááŸááááºá
Name
. - á¥ááá¬áá»á¬ážááẠinline script ááá¯ááá¯á¶ážááá·áºáá«á
userData
- áá»áœááºá¯ááºááá¯á·ááẠAMI (áá¯á¶) ááá¯áá¯á¶ážááá«áááºá - SSH ááẠá¡ááºáá¬áááºááŸáá·áº áááááœá±á·ááá·áºáá«á
á€á¥ááá¬ááá¯á¡ááŒá±áá¶áááºá
index.js-
"use strict";
let aws = require("@pulumi/aws");
let group = new aws.ec2.SecurityGroup("web-secgrp", {
ingress: [
{ protocol: "tcp", fromPort: 22, toPort: 22, cidrBlocks: ["0.0.0.0/0"] },
{ protocol: "tcp", fromPort: 80, toPort: 80, cidrBlocks: ["0.0.0.0/0"] },
],
});
let userData =
`#!/bin/bash
echo "Hello, World!" > index.html
nohup python -m SimpleHTTPServer 80 &`;
let server = new aws.ec2.Instance("web-server-www", {
instanceType: "t2.micro",
securityGroups: [ group.name ], // reference the group object above
ami: "ami-c55673a0" // AMI for us-east-2 (Ohio),
userData: userData // start a simple web server
});
exports.group = group;
exports.server = server;
exports.publicIp = server.publicIp;
exports.publicHostName = server.publicDns;
áááºážááẠá¡ááŒá±áᶠPulumi áááá¯ááááºááŒá áºáááº- áááºážááẠEC2 áá¯á¶ááŒá¯á¶áá±ážá¡ááœá²á·ááŸáá·áº á¥ááá¬áá áºáá¯ááᯠááœá²áá±áá±ážáááºá ááá¯á·áá±á¬áº á€áá±áá¬ááœáẠáá»áœááºá¯ááºááá¯á·ááẠá¡áááºáá±á¬áºááŒáá« á ááºážáááºážáá»áẠáá¯á¶ážáá¯áá¯á¶ážááᯠáá»áá¯ážáá±á¬ááºáá±ááŒá±á¬ááºáž áááááŒá¯ááá·áºáááºá á á¬áá±ážááœá²ááœá± áá±ážááŒáá¡á±á¬ááºá
á á¬áá±ážá á¬áá±ážááœá²áá»á¬áž
áá»áœááºá¯ááºááá¯á·áá á áºáá±ážááŸá¯áá»á¬ážá áá±áá°áá»ááœá²á·á ááºážáá¯á¶ááẠáá¯á¶ááŸáẠMocha á ááºážáááºááŸá¯áá»á¬ážááŸáá·áºáá°áááá·áºáááº-
ec2tests.js
test.js:
let assert = require("assert");
let mocha = require("mocha");
let pulumi = require("@pulumi/pulumi");
let infra = require("./index");
describe("Infrastructure", function() {
let server = infra.server;
describe("#server", function() {
// TODO(check 1): ÐПлжеМ бÑÑÑ ÑÑг Name.
// TODO(check 2): Ðе ЎПлжМП бÑÑÑ inline-ÑкÑОпÑа userData.
});
let group = infra.group;
describe("#group", function() {
// TODO(check 3): Ðе ЎПлжМП бÑÑÑ SSH, ПÑкÑÑÑПгП в ÐÐœÑеÑМеÑ.
});
});
ááᯠáá»áœááºá¯ááºááá¯á·á ááááá¯á¶ážá
ááºážáááºááŸá¯ááᯠáá±ážááŒáá«á
áá¯á·- á¥ááá¬áá»á¬ážááœáẠtag áá«ááŸáááŒá±á¬ááºáž áá±áá»á¬áá«á
á±á Name
. áááºážááá¯á
á
áºáá±ážáááºá¡ááœáẠáá»áœááºá¯ááºááá¯á·ááẠEC2 instance object ááá¯ááá°ááŒá®áž áááºááá¯ááºáá¬ááá¯ááºááá¯ááºááŸá¯ááá¯á
á
áºáá±ážáá«á tags
:
// check 1: ÐПлжеМ бÑÑÑ ÑÑг Name.
it("must have a name tag", function(done) {
pulumi.all([server.urn, server.tags]).apply(([urn, tags]) => {
if (!tags || !tags["Name"]) {
done(new Error(`Missing a name tag on server ${urn}`));
} else {
done();
}
});
});
áááºážááẠáá¯á¶ááŸááºá ááºážáááºááŸá¯áá áºáá¯ááŸáá·áº áá°áá±á¬áºáááºáž ááŸááºáá¬ážááá¯ááºááá·áº á¡ááºá¹áá«áááºá¡áá»áá¯á·ááŒáá·áº-
- ááŒáá·áºáá»ááºááŒááºážáááŒá¯áá® á¡áááºážá¡ááŒá áºáá áºáá¯áá¡ááŒá±á¡áá±ááᯠáá»áœááºá¯ááºááá¯á·áá±ážááŒááºážáá±á¬ááŒá±á¬áá·áºá áá»áœááºá¯ááºááá¯á·áá ááºážáááºááŸá¯áá»á¬ážááᯠ"á¡á á®á¡á á¥áº" (ááá¯á·ááá¯áẠ"á¡á ááºážááŒáá·áºááŸá¯ááŒááºáž") áá¯ááºááœáẠá¡ááŒá²áá¯ááºáá±á¬ááºáá«áááºá ááá¯á·ááŒá±á¬áá·áºá áááºááá¯ážáá»á¬ážááᯠááá¯ážááá¯ážááŸááºážááŸááºáž ááŒááºáá°áááºááá¯áẠááá¯á·ááá¯áẠáááºááŸááºáááºááá¯ááºááá·áº áá¯ááºááá¹áááá»á¬ážá áœá¬ááŸááá«áááºá áááºážááœáẠáááºá cloud áááºáá±á¬ááºááŸá¯áá±ážáá°á០ááœááºáá»ááºáá¬ážáá±á¬ á¡ááœááºáá¯ááºááá¹áááá»á¬áž áá«áááºáááºá áááºážááẠáá»áœááºá¯ááºááá¯á·áá á áºáá±ážááŸá¯áá»á¬ážá¡ááœáẠáá¯á¶ááŸááºááŒá áºááẠ- áá»áœááºá¯ááºááá¯á·ááẠááá·áºááœááºážááŸá¯áá±áá¬ááá¯áᬠá á áºáá±ážáá«áááºá áá±á«ááºážá ááºážááŒááºážááá¯ááºáᬠá ááºážáááºááŸá¯áá»á¬ážááŸáá·áº áááºáááºáá¬áá»áŸáẠáá±á¬ááºááá¯ááºážááœáẠá€ááŒá¿áá¬ááᯠááŒááºááœá¬ážáá«áááºá
- Pulumi á¡áááºážá¡ááŒá
áºáá¯ááºááá¹áááá»á¬áž á¡á¬ážáá¯á¶ážááẠá¡ááœááºáá»á¬ážááŒá
áºááŒá®áž áááºážááá¯á·áá²á០á¡áá»á¬ážá¡ááŒá¬ážááᯠá¡áá»áááºáááœá±áž á¡áá²ááŒááºááŒááºážááŒá
áºáá±á¬ááŒá±á¬áá·áº áááºááá¯ážáá»á¬ážááᯠáááºáá±á¬ááºááŒáá·áºááŸá¯ááẠá¡áá¯á¶ážáá»áááºážáááºážááᯠá¡áá¯á¶ážááŒá¯ááẠááá¯á¡ááºáá«áááºá áááºážááẠááááá»á¬ážááŸáá·áº áá¯ááºáá±á¬ááºáá»ááºáá»á¬ážááŸáá·áº á¡ááœááºáááºáá°áááºá
then
. - áá»áœááºá¯ááºááá¯á·ááẠerror message ááœáẠá¡áááºážá¡ááŒá
ẠURN ááá¯ááŒáááẠáá¯ááºááá¹áááá»á¬ážá
áœá¬ááᯠá¡áá¯á¶ážááŒá¯áá±áá±á¬ááŒá±á¬áá·áºá áá»áœááºá¯ááºááá¯á·ááẠáá¯ááºáá±á¬ááºáá»ááºááᯠá¡áá¯á¶ážááŒá¯áááºááá¯á¡ááºáá«áááºá
pulumi.all
áá°ááá¯á·ááá¯áá±á«ááºážá ááºááá¯á·á - áá±á¬ááºáá¯á¶ážááœááºá á€áááºááá¯ážáá»á¬ážááᯠáááŒáá¯ááºáááºáááºáž ááœááºáá»ááºáá¬ážáá±á¬ááŒá±á¬áá·áº Mocha á built-in async callback áá¯ááºáá±á¬ááºáá»ááºááᯠá¡áá¯á¶ážááŒá¯ááẠááá¯á¡ááºáá«áááºá
done
áá«ááŸááá¯áẠááááá áºáá¯ááŒááºáá±ážáááºá
á¡áá¬á¡á¬ážáá¯á¶ážááᯠáááºááŸááºááŒá®ážáááºááŸáá·áºá áá»áœááºá¯ááºááá¯á·ááẠááá¯ážááŸááºážáá±á¬ JavaScript áááºááá¯ážáá»á¬ážá¡ááŒá
Ạááá·áºááœááºážááŸá¯áá»á¬ážááᯠáááºáá±á¬ááºááŒáá·áºááŸá¯ááá¯ááºáááºááŒá
áºáááºá áá
á¹á
ááºážá¥á
á¹á
ᬠtags
ááŒá±áá¯á¶ (associative array) ááŒá
áºáááºá ááá¯á·ááŒá±á¬áá·áº áááºážááẠ(á) á¡ááŸá¬ážááá¯ááºááŒá±á¬ááºážá (á) á¡ááœáẠáá±á¬á·áá
áºáᯠááŸááááºá Name
. áááºážááẠá¡ááœááºááá¯ážááŸááºážááŒá®áž ááᯠáá»áœááºá¯ááºááá¯á·ááẠáááºááá·áºá¡áá¬ááá¯áááᯠá
ááºážáááºááá¯ááºááŒá®ááŒá
áºáááºá
ááᯠáá»áœááºá¯ááºááá¯á·á áá¯áááá á áºáá±ážááŸá¯ááᯠáá±ážááŒáá«á áá¯á·á ááá¯áá±á¬áẠááá¯ážááŸááºážáá«áááº-
// check 2: Ðе ЎПлжМП бÑÑÑ inline-ÑкÑОпÑа userData.
it("must not use userData (use an AMI instead)", function(done) {
pulumi.all([server.urn, server.userData]).apply(([urn, userData]) => {
if (userData) {
done(new Error(`Illegal use of userData on server ${urn}`));
} else {
done();
}
});
});
áá±á¬ááºáá¯á¶ážáá±á¬á· ááááá¡á ááºážáá±ážááŒáá·áºáá¡á±á¬ááºá áá¯á¶ááŒá¯á¶áá±ážá¡ááœá²á·ááŸáá·áº áááºá ááºáá±á¬ á¡áá±á¬áá·áºáááºááŒááºážááá¯ááºáᬠá ááºážáá»ááºážáá»á¬ážááᯠáá»áœááºá¯ááºááá¯á· ááŸá¬ááœá±áá±áá±á¬ááŒá±á¬áá·áº áááºážááŸá¬ á¡áááºážááẠááá¯ááá¯ááŸá¯ááºááœá±ážááœá¬ážáááºááŒá áºááŒá®áž áááºážááá¯á·ááœáẠáá»á¬ážá áœá¬ááŸáááá¯ááºááá·áºá¡ááŒáẠá¡ááá¯áá«á ááºážáá»ááºážáá»á¬ážááœáẠCIDR á¡ááá¯ááºážá¡ááŒá¬ážáá»á¬ážáááºáž áá»á¬ážá áœá¬ááŸáááá¯ááºáá«áááºá ááá¯á·áá±á¬áº áá»áœááºá¯ááºááá¯á· á á®áá¶áá²á·áááº-
// check 3: Ðе ЎПлжМП бÑÑÑ SSH, ПÑкÑÑÑПгП в ÐÐœÑеÑМеÑ.
it("must not open port 22 (SSH) to the Internet", function(done) {
pulumi.all([ group.urn, group.ingress ]).apply(([ urn, ingress ]) => {
if (ingress.find(rule =>
rule.fromPort == 22 && rule.cidrBlocks.find(block =>
block === "0.0.0.0/0"))) {
done(new Error(`Illegal SSH port 22 open to the Internet (CIDR 0.0.0.0/0) on group ${urn}`));
} else {
done();
}
});
});
áá«áá«áá²á áá² á á¬áá±ážááœá²ááœá± á ááá¯ááºáá¡á±á¬ááºá
á¡ááŒá±ážá ááºážáááºááŸá¯áá»á¬áž
á¡ááŒá±á¡áá±á¡áá»á¬ážá
á¯ááœááºá áááºááœá±ážáá»ááºáá¬ážáá±á¬ á
ááºážáááºááŸá¯áá±á¬ááºááᯠá¡áá¯á¶ážááŒá¯á áá¯á¶ááŸááºáááºážáááºážááŒáá·áº á
á¬áá±ážááœá²áá»á¬ážááᯠáá¯ááºáá±á¬ááºááá¯ááºáááºá ááá¯á·áá±á¬áº áááááŒá¯áááá·áºá¡áá»ááºááŸá¬ Pulumi á áá°ážááŒá¬ážáá»ááºáá
áºáá¯ááŸááááºá
áá¯á¶ááŸááºá¡á¬ážááŒáá·áº Pulumi áááá¯ááááºáá»á¬ážááᯠrun áááºá¡ááœáẠpulimi CLI (Command Line interface) ááᯠá¡áá¯á¶ážááŒá¯ááŒá®áž language runtime ááᯠconfigure áá¯ááºáᬠPulumi engine á áá
áºááœáŸááºááŸá¯ááᯠááááºážáá»á¯ááºáᬠá¡áááºážá¡ááŒá
áºáá»á¬ážááŸáá·áºá¡áá° áá¯ááºáá±á¬ááºááŸá¯áá»á¬ážááᯠááŸááºáááºážáááºááŒá®áž á¡á
á®á¡á
ááºááœáẠááá·áºááœááºážááá¯ááºá
á±áááºá á
áááºááá¯á·ááᯠá¡áá¯á¶ážááŒá¯áá«áááºá ááá¯á·áá±á¬áº ááŒá¿áá¬áá
áºáá¯áá±á¬á· ááŸááá«áááºá áááºáá
ááºážáááºááŸá¯áá±á¬ááºáááááºážáá»á¯ááºááŸá¯á¡á±á¬ááºááœááºá¡áá¯ááºáá¯ááºáá±á¬á¡áá«á CLI ááŸáá·áº Pulumi á¡ááºáá»ááºá¡ááŒá¬ážáááºááœááºááŸá¯ááŸááá¬áááºááá¯ááºáá«á
á€ááŒá¿áá¬ááá¯ááŒá±ááŸááºážáááºá áá»áœááºá¯ááºááá¯á·ááẠá¡á±á¬ááºáá«ááá¯á·ááᯠáááºááŸááºááẠááá¯á¡ááºáá«áááºá
- ááá±á¬áá»ááºá¡áááºá áááºáááºážáá»áẠááááºážááŸááºááœááºáá«ááŸááááºá
PULUMI_NODEJS_PROJECT
(ááá¯á·ááá¯ááºá áá±áá¯áá»á¡á¬ážááŒáá·áºáPULUMI__PROJECT ÐŽÐ»Ñ ÐŽÑÑÐ³ÐžÑ ÑзÑкПв).
Environment variable ááœáẠáááºááŸááºáá¬ážáá±á¬ stack á á¡áááºPULUMI_NODEJS_STACK
(ááá¯á·ááá¯ááºá áá±áá¯áá»á¡á¬ážááŒáá·áºáPULUMI__ STACK).
áááºá stack configuration variables áááºážááá¯á·ááᯠEnvironment variable ááŒáá·áº ááá°ááá¯ááºáááºáPULUMI_CONFIG
áááºážááá¯á·ááá±á¬áºáááºááẠáá±á¬á·/áááºááá¯ážá¡ááœá²áá»á¬ážáá«ááŸááá±á¬ JSON ááŒá±áá¯á¶ááŒá áºáááºááááá¯ááááºááẠáá¯ááºáá±á¬ááºáá±á ááºá¡ááœááºáž CLI/á¡ááºáá»ááºááŸáá·áº áá»áááºáááºááŸá¯ ááááŸáááá¯ááºááŒá±á¬ááºáž ááœáŸááºááŒáá±á¬ ááááá±ážáá»ááºáá»á¬áž áá¯ááºááŒááºáá«áááºá ááá·áºáááá¯ááááºááẠá¡ááŸááºááááºááœáẠáááºááá·áºá¡áá¬ááá¯áá»áŸ ááŒáá·áºáá»ááºáá¯ááºáá±á¬ááºáááºááá¯ááºáá±á¬ááŒá±á¬áá·áº áááºážááẠá¡áá±ážááŒá®ážáá±á¬ááŒá±á¬áá·áº áááºážááẠáááºáááºááœááºáá¬ážááá·áºá¡áá¬ááá¯ááºáá«á á¡á¶á·á¡á¬ážááá·áºá áá¬ááŒá áºáá¬ááá¯ááºáááºá Pulumi ááẠáááºááá¯á¡ááºááá·áºá¡áá¬ááŒá áºáááºááᯠá¡ááá¡áá»ááŒá±á¬ááŒáááºá áááºááẠááá·áºááœááºážááá¯ááºáááºá
PULUMI_TEST_MODE
вtrue
.ááá±á¬áá»ááºá¡áááºááᯠáááºááŸááºááẠááá¯á¡ááºáááºáᯠááŒááºáá±á¬ááºááŒáá·áºáá«á
my-ws
, stack á¡áááºdev
ááŸáá·áº AWS áá±áus-west-2
. Mocha á ááºážáááºááŸá¯áá»á¬áž áá¯ááºáá±á¬ááºáááºá¡ááœáẠá¡áááá·áºáá±ážá á¬ááŒá±á¬ááºážááẠá€áá²á·ááá¯á· ááŒá áºáá±áááá·áºáááº-$ PULUMI_TEST_MODE=true PULUMI_NODEJS_STACK="my-ws" PULUMI_NODEJS_PROJECT="dev" PULUMI_CONFIG='{ "aws:region": "us-west-2" }' mocha tests.js
áá»áŸá±á¬áºááá·áºáá¬ážááá·áºá¡ááá¯ááºáž á€ááá¯á·áá¯ááºáá±á¬ááºááŒááºážááŒáá·áº áá»áœááºá¯ááºááá¯á·ááœáẠáá»ááŸá¯á¶ážáá±á¬ á ááºážáááºááŸá¯ áá¯á¶ážáá¯ááŸáááŒá±á¬ááºáž ááŒááá«áááá·áºáááºá
Infrastructure #server 1) must have a name tag 2) must not use userData (use an AMI instead) #group 3) must not open port 22 (SSH) to the Internet 0 passing (17ms) 3 failing 1) Infrastructure #server must have a name tag: Error: Missing a name tag on server urn:pulumi:my-ws::my-dev::aws:ec2/instance:Instance::web-server-www 2) Infrastructure #server must not use userData (use an AMI instead): Error: Illegal use of userData on server urn:pulumi:my-ws::my-dev::aws:ec2/instance:Instance::web-server-www 3) Infrastructure #group must not open port 22 (SSH) to the Internet: Error: Illegal SSH port 22 open to the Internet (CIDR 0.0.0.0/0) on group
áá»áœááºá¯ááºááá¯á·ááááá¯ááááºááᯠááŒá¯ááŒááºááŒáá«á áá¯á·á
"use strict"; let aws = require("@pulumi/aws"); let group = new aws.ec2.SecurityGroup("web-secgrp", { ingress: [ { protocol: "tcp", fromPort: 80, toPort: 80, cidrBlocks: ["0.0.0.0/0"] }, ], }); let server = new aws.ec2.Instance("web-server-www", { tags: { "Name": "web-server-www" }, instanceType: "t2.micro", securityGroups: [ group.name ], // reference the group object above ami: "ami-c55673a0" // AMI for us-east-2 (Ohio), }); exports.group = group; exports.server = server; exports.publicIp = server.publicIp; exports.publicHostName = server.publicDns;
ááá¯á·áá±á¬áẠá ááºážáááºááŸá¯áá»á¬ážááᯠáááºáá¶áá¯ááºáá±á¬ááºáá«-
Infrastructure #server â must have a name tag â must not use userData (use an AMI instead) #group â must not open port 22 (SSH) to the Internet 3 passing (16ms)
á¡á¬ážáá¯á¶ážá¡áááºááŒá±ááœá¬ážáá«ááŒá®... áá¬áž! âââ
áá®áá±á·á¡ááœáẠáá®áá±á¬ááºáá«áá²á áá«áá±ááá·áº áá¬áá¬ááŒááºááŒááºážáá²á· áá¯áááá¡ááá¯ááºážááŸá¬ ááŒáá·áºáá»ááºá ááºážáááºááŒááºážá¡ááŒá±á¬ááºáž ááŒá±á¬ááŒáá«ááẠð
source: www.habr.com