Skip to main content

Pulumi


Installation

AWS

curl "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" -o "awscliv2.zip"
unzip awscliv2.zip
sudo ./aws/install
  • AWS Access Key ID and Access Key: IAM -> 사용자 -> <user> -> 보안 자격 증명 -> 액세스 키 만들기
aws configure --profile <profile>

S3

  • ACL 비활성화됨
  • 모든 퍼블릭 액세스 차단
  • 버킷 버전 관리 비활성화
  • 기본 암호화 활성화

Pulumi

curl -fsSL https://get.pulumi.com | sh
pulumi_config_passphrase
<암호>
export PULUMI_CONFIG_PASSPHRASE_FILE=<path>/pulumi_config_passphrase

또는

export PULUMI_CONFIG_PASSPHRASE=<암호>

Tutorial

Directory structure

test/
├── package.json
├── tsconfig.json
├── Pulumi.yaml
├── Pulumi.test.dev.yaml
└── src/
├── index.ts
├── variable.ts
└── ec2/
├── index.ts
└── ec2.ts

Project file(Pulumi.yaml)

Pulumi.yaml
name: <project>
runtime: nodejs
backend:
url: s3://<bucket>

Package file

package.json
{
"name": "<project>",
"main": "src/index.ts",
"devDependencies": {
"@types/node": "^14"
},
"dependencies": {
"@pulumi/aws": "^5.19.0",
"@pulumi/pulumi": "^3.45.0",
"tsconfig-paths": "^4.1.0"
}
}
tsconfig.json
{
"compilerOptions": {
"strict": true,
"outDir": "bin",
"target": "es2016",
"module": "commonjs",
"moduleResolution": "node",
"sourceMap": true,
"experimentalDecorators": true,
"pretty": true,
"noFallthroughCasesInSwitch": true,
"noImplicitReturns": true,
"forceConsistentCasingInFileNames": true,
"baseUrl": "./src",
"paths": {
"@src/*": ["./*"]
}
},
"files": ["src/index.ts"]
}

Stack Configuration file

pulumi stack init test.dev
Pulumi.test.dev.yaml
encryptionsalt: "*****"
config:
# pulumi.Config("aws")
aws:region: <region>
aws:profile: <profile>

# pulumi.Config()
<project>:cluster: <repo>
info

S3를 사용할 때, backend.url을 공유하는 여러 프로젝트는, stack이름으로 접근이 가능합니다.(pulumi.StackReference) 따라서 stack이름을 지을 때, <project>.<sub-project>.prod 등의 형식으로 짓는 것이 좋습니다.(S3를 backend로 할 때 아직 <organization>/<project>/<stack>을 지원하지 않는 것 같습니다.)

IAC code

src/variable.ts
import * as pulumi from "@pulumi/pulumi";

const stackName = pulumi.getStack();
const clusterName = "eks";

const config = new pulumi.Config();
src/ec2/ec2.ts
import * as aws from "@pulumi/aws";

import * as variable from "@src/variable";

function createEC2(name: string): aws.ec2.Instance {
return new aws.ec2.Instance(name, {
ami: "ami-090717c950a5c34d3",
instanceType: "t3.micro",
tags: {
Name: name,
"loliot.net/stack": variable.stackName,
"loliot.net/cluster": variable.clusterName,
},
});
}

export const appServer = createEC2("app-server");
src/ec2/index.ts
export * as ec2 from "./ec2";
src/index.ts
import { loadConfig, register } from "tsconfig-paths";

const tsConfig = loadConfig(".");
if (tsConfig.resultType === "failed") {
console.log("Could not load tsconfig to map paths, aborting.");
process.exit(1);
}
register({
baseUrl: tsConfig.absoluteBaseUrl,
paths: tsConfig.paths,
});

export * as ec2 from "./ec2";

Execution

pulumi refresh --skip-preview --yes
pulumi up
pulumi stack output
pulumi destroy --skip-preview
pulumi stack rm test.dev