별거 아닌 코드 공유
AWS의 s3 는 *라이프 사이클이 있다.
일정 주기로 오브젝트 들의 스토리지 클래스를 변경하여 비용 효율화 한다.
*s3 라이프 사이클
https://docs.aws.amazon.com/ko_kr/AmazonS3/latest/userguide/object-lifecycle-mgmt.html
하지만 세부 설정은 불가능 하다. 일정 조절이나 스토리지 클래스를 입맛대로 바꾸기 힘들다.
따라서 배치 서비스를 개발 하였다.
저장
1. airflow 에서 스케줄링으로 트리거 시켜줌
2. csv 에서 조건 읽어, 해달경로의 오브젝트들에 cp 명령어를 날려줌
복원
1. 원하는 딥아카이브 파일을 파라미터를 포함하여 실행
2. 복원완료 시 s3 에서 이벤트 트리거를 주어, (슬랙 얼럿 기능을 하는) Lambda 실행
slack alert 을 위해서는 슬랙의 포스트를 위한 웹훅 주소를 일아내야 한다.
https://slack.com/intl/ko-kr/help/articles/115005265063-Slack용-수신-웹후크
아래코드는 *AWS CLI 명령어를 날려주는 파이썬 스크립트이며
* AWS CLI for S3
s3 라이브러리 *boto3 와 pandas 를 활용하였다.
* boto3
https://boto3.amazonaws.com/v1/documentation/api/latest/guide/s3.html
boto3 를 통해 csv 에서 받아온 s3 경로에 실제하는 오브젝트의 키정보를 받아서
각 키들의 날짜를 regex 로 파싱해서 실제하는 날짜 정보 리스트를 만든 후 커맨드를 날리는 로직이다.
스탠다드 -> 딥 아카이브
import os
import boto3
import re
import pandas as pd
from datetime import datetime
from datetime import timedelta
now = datetime.now()
pathData = pd.read_csv("./s3Path.csv")
#pathData = pd.read_csv("./s3PathTest.csv")
date = now.strftime("%Y%m%d")
#print(pathData.iloc[1,3])
pathList = pathData["path"]
cmd = "aws s3 cp "
stClass = " --storage-class DEEP_ARCHIVE"
srcPath = "s3://소스주소"
destPath = "s3://타깃주소"
s3 = boto3.resource('s3')
src_bucket = s3.Bucket('버킷이름')
dateRE = "(19|20)\\d{2}(0[1-9]|1[012])(0[1-9]|[12][0-9]|3[01])"
for row in pathData.itertuples():
prefixPath = re.split('%s', row.path)
#save all of date in s3 object as list
srcDateList = []
try:
for object_summary in src_bucket.objects.filter(Prefix = "S3 경로/"+prefixPath[0]):
try:
#print(object_summary.key)# address
objectDate = re.search(dateRE, object_summary.key).group()
except:
continue
#print(objectDate) # date from address
srcDateList.append(objectDate)
#dropDuplicate
except:
continue
srcDateList = list(set(srcDateList))
#exec copy command
implementTime = datetime.now() - timedelta(days=row.holdTime)
for dateEle in srcDateList:
convertedDate = datetime.strptime(dateEle, "%Y%m%d")
if (implementTime >= convertedDate):
#os.system()
#print(row.path)
cpCmd = cmd + srcPath + row.path +" "+ destPath + row.path
dateCnt = cpCmd.count('%s')
if (dateCnt==2):
os.system (cpCmd % (dateEle, dateEle)) + stClass
elif (dateCnt==4):
os.system (cpCmd % (dateEle, dateEle, dateEle, dateEle)) + stClass
슬랙 얼럿 lambda 코드
import json
import urllib.request
def lambda_handler(event, context):
# TODO implement
records = event["Records"]
objects = records[0]
s3json = objects["s3"]
jsonObject = s3json["object"]
jsonBucket = s3json["bucket"]
print("bucket : " + jsonBucket["name"])
print ("key : " + jsonObject["key"])
message = {
"username": "monitorbot",
"icon_emoji": ":ghost:"
}
msg = jsonBucket["name"] + " " + jsonObject["key"]
print("msg")
message["text"] = urllib.parse.quote(msg)
slack_incoming_url = "https://hooks.slack.com/services/ 슬랙 웹훅 post 주소를 따서 넣어줌"
#message["text"] = urllib.parse.quote(data["message"])
send_text = "payload=" + json.dumps(message)
post_slack(send_text, slack_incoming_url)
def post_slack(data, slack_incoming_url):
request = urllib.request.Request(
slack_incoming_url,
data=data.encode('utf-8'),
method="POST"
)
with urllib.request.urlopen(request) as response:
response_body = response.read().decode('utf-8')
print(response_body)
return {
'statusCode': 200,
'body': json.dumps('Hello from Lambda!')
}
'일 > aws' 카테고리의 다른 글
Amazon EMR 구축 #2 :: 프로비저닝 (0) | 2022.02.01 |
---|---|
Amazon EMR 구축 #1 :: 개념 정리 (0) | 2022.02.01 |
AWS DMS Consistency Checking Application Concept (0) | 2022.01.11 |
AWS Code Deploy + Jenkins + GitLab (0) | 2022.01.04 |
AWS DMS :: from aurora mySQL to S3 (0) | 2021.12.06 |