AWS Lambda 토큰 벤딩 머신을 사용하여 Amazon S3에 대한 SaaS 테넌트 격리를 구현합니다. - AWS 권장 가이드

기계 번역으로 제공되는 번역입니다. 제공된 번역과 원본 영어의 내용이 상충하는 경우에는 영어 버전이 우선합니다.

AWS Lambda 토큰 벤딩 머신을 사용하여 Amazon S3에 대한 SaaS 테넌트 격리를 구현합니다.

작성자: Tabby Ward(AWS), Sravan Periyathambi(AWS), Thomas Davis(AWS)

환경: PoC 또는 파일럿

기술: 현대화; SaaS

AWS 서비스: AWS Identity 및 Access Management, AWS Lambda, Amazon S3, AWS STS

요약

멀티테넌트 SaaS 애플리케이션은 테넌트 격리가 유지되도록 시스템을 구현해야 합니다. 동일한 Amazon Web Services(AWS) 리소스에 테넌트 데이터를 저장하는 경우(예: 여러 테넌트가 동일한 Amazon Simple Storage Service(S3) 버킷에 데이터를 저장하는 경우) 테넌트 간 액세스가 발생하지 않도록 해야 합니다. 토큰 자판기(TVM)는 테넌트 데이터 격리를 제공하는 한 가지 방법입니다. 이러한 머신은 토큰 생성 방식의 복잡성을 추상화하는 동시에 토큰을 획득할 수 있는 메커니즘을 제공합니다. 개발자는 토큰 생성 방법에 대한 자세한 지식 없이도 TVM을 사용할 수 있습니다.

이 패턴은 AWS Lambda를 사용하여 TVM을 구현합니다. TVM은 S3 버킷의 단일 SaaS 테넌트 데이터에 대한 액세스를 제한하는 임시 보안 토큰 서비스(STS) 보안 인증 정보로 구성된 토큰을 생성합니다.

TVM과 이 패턴으로 제공되는 코드는 일반적으로 JSON 웹 토큰(JWT)에서 파생된 클레임과 함께 사용되어 AWS 리소스에 대한 요청을 테넌트 범위의 AWS Identity 및 Access Management(IAM) 정책과 연결합니다. 기본적으로 이 패턴의 코드를 사용하여 JWT 토큰에 제공되는 클레임을 기반으로 범위가 지정된 임시 STS 보안 인증 정보를 생성하는 SaaS 애플리케이션을 구현할 수 있습니다.

사전 조건 및 제한 사항

사전 조건 

  • 활성 상태의 AWS 계정.

  • macOS, Linux 또는 Windows에 설치 및 구성된 AWS Command Line Interface(AWS CLI) 버전 1.19.0 이상 또는 AWS CLI 버전 2.1 이상을 사용할 수 있습니다.

제한 사항

  • 이 코드는 Java에서 실행되며 현재 다른 프로그래밍 언어를 지원하지 않습니다. 

  • 샘플 애플리케이션에는 AWS 교차 리전 또는 재해 복구(DR) 지원이 포함되어 있지 않습니다. 

  • 이 패턴은 SaaS 애플리케이션용 Lambda TVM이 범위 지정 테넌트 액세스를 제공하는 방법을 보여줍니다. 프로덕션 환경에서 사용하기 위한 것이 아닙니다.

아키텍처

대상 기술 스택  

  • AWS Lambda

  • Amazon S3

  • IAM

  • AWS Security Token Service (AWS STS)

대상 아키텍처

도구

서비스

  • AWS Command Line Interface(AWS CLI)는 명령줄 쉘에서 명령을 사용하여 AWS 서비스와 상호 작용할 수 있는 오픈 소스 도구입니다.

  • AWS Identity and Access Management(IAM)는 사용자에 대한 인증 및 권한 부여를 제어함으로써 AWS 리소스에 대한 액세스를 안전하게 관리할 수 있습니다.

  • AWS Lambda는 서버를 프로비저닝하거나 관리할 필요 없이 코드를 실행하는 데 도움이 되는 컴퓨팅 서비스입니다. 필요할 때만 코드를 실행하며 자동으로 확장이 가능하므로 사용한 컴퓨팅 시간만큼만 비용을 지불합니다.

  • AWS Security Token Service(AWS STS)를 사용하면 사용자를 위한 제한된 권한의 임시 보안 인증 정보를 요청할 수 있습니다.

  • Amazon Simple Storage Service(S3)는 원하는 양의 데이터를 저장, 보호 및 검색하는 데 도움이 되는 클라우드 기반 객체 스토리지 서비스입니다.

코드

이 패턴의 소스 코드는 첨부 파일로 제공되며 다음과 같은 파일이 포함됩니다.

  • s3UploadSample.jar은 JSON 문서를 S3 버킷에 업로드하는 Lambda 함수의 소스 코드를 제공합니다.

  • tvm-layer.zip(은)는 Lambda 함수가 S3 버킷에 액세스하고 JSON 문서를 업로드할 수 있도록 토큰(STS 임시 보안 인증 정보)을 제공하는 재사용 가능한 Java 라이브러리를 제공합니다.

  • token-vending-machine-sample-app.zip은 이러한 아티팩트와 컴파일 지침을 생성하는 데 사용되는 소스 코드를 제공합니다.

이러한 파일을 사용하려면 다음 섹션의 지침을 따르세요.

에픽

작업설명필요한 기술

변수 값을 결정합니다.

이 패턴의 구현에는 일관되게 사용해야 하는 여러 변수 이름이 포함됩니다. 각 변수에 사용해야 하는 값을 결정하고 이후 단계에서 요청할 경우 해당 값을 제공하세요.

<AWS 계정 ID> ─ 이 패턴을 구현하려는 AWS 계정과 연결된 12자리 계정 ID. AWS 계정 ID를 찾는 방법에 대한 자세한 내용은 IAM 설명서에서 AWS 계정 ID 및 별칭을 참조하세요.

<AWS 리전> ─ 이 패턴을 구현하고 있는 AWS 리전 AWS 리전에 대한 자세한 내용은 AWS 웹사이트의 리전 및 가용 영역을 참조하세요.

< sample-tenant-name > ─ 애플리케이션에서 사용할 테넌트의 이름. 단순화를 위해 이 값에는 영숫자만 사용하는 것이 좋지만 S3 객체 키에는 어떤 유효한 이름이라도 사용할 수 있습니다.

< sample-tvm-role-name > ─ TVM 및 샘플 애플리케이션을 실행하는 Lambda 함수에 연결된 IAM 역할의 이름. 역할 이름은 공백 없이 대문자 및 소문자 영숫자로 구성된 문자열입니다. 밑줄(_), 더하기 기호(+), 등호(=), 쉼표(,), 마침표(.), 골뱅이 기호(@) 및 하이픈(-) 문자를 포함할 수도 있습니다. 역할 이름은 계정 내에서 고유해야 합니다.

< sample-app-role-name > ─ 범위가 지정된 임시 STS 자격 증명을 생성할 때 Lambda 함수가 맡는 IAM 역할의 이름입니다. 역할 이름은 공백 없이 대문자 및 소문자 영숫자로 구성된 문자열입니다. 밑줄(_), 더하기 기호(+), 등호(=), 쉼표(,), 마침표(.), 골뱅이 기호(@) 및 하이픈(-) 문자를 포함할 수도 있습니다. 역할 이름은 계정 내에서 고유해야 합니다.

< sample-app-function-name > ─ Lambda 함수의 이름. 이 문자열은 길이가 최대 64자입니다.

< sample-app-bucket-name > ─ 특정 테넌트로 범위가 지정된 권한으로 액세스해야 하는 S3 버킷의 이름. S3 버킷 이름:

  • 3~63자 이내로 작성합니다.

  • 소문자, 숫자, 마침표(.) 및 하이픈(-)만 포함해야 합니다.

  • 문자나 숫자로 시작하고 끝나야 합니다.

  • IP 주소 형식(예: 192.168.5.4)을 사용할 수 없습니다.

  • 파티션 내에서 고유해야 합니다. 파티션은 리전의 그룹입니다. AWS는 현재 aws  (표준 지역), (중국 지역) 및 aws-cn aws-us-gov (AWS GovCloud [미국] 지역) 이라는 세 개의 파티션을 가지고 있습니다.

클라우드 관리자
작업설명필요한 기술

샘플 애플리케이션을 위한 S3 버킷을 생성합니다.

다음 AWS CLI 명령을 사용하여 S3 버킷을 생성합니다. 코드 스니펫에 < sample-app-bucket-name > 값을 입력하십시오.

aws s3api create-bucket --bucket <sample-app-bucket-name>

Lambda 샘플 애플리케이션은 JSON 파일을 이 버킷에 업로드합니다.

클라우드 관리자
작업설명필요한 기술

TVM 역할을 생성합니다.

다음 AWS CLI 명령 중 하나를 사용하여 IAM 역할을 생성합니다. 명령에 < sample-tvm-role-name > 값을 입력합니다.

macOS 또는 Linux 쉘의 경우:

aws iam create-role \ --role-name <sample-tvm-role-name> \ --assume-role-policy-document '{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "Service": "lambda.amazonaws.com" }, "Action": "sts:AssumeRole" } ]}'

Windows 명령줄의 경우:

aws iam create-role ^ --role-name <sample-tvm-role-name> ^ --assume-role-policy-document "{\"Version\": \"2012-10-17\", \"Statement\": [{\"Effect\": \"Allow\", \"Principal\": {\"Service\": \"lambda.amazonaws.com\"}, \"Action\": \"sts:AssumeRole\"}]}"

Lambda 샘플 애플리케이션은 애플리케이션이 호출될 때 이 역할을 맡습니다. 범위 지정 정책으로 애플리케이션 역할을 맡을 수 있는 기능은 코드에 S3 버킷에 액세스할 수 있는 더 넓은 권한을 부여합니다.

클라우드 관리자

인라인 TVM 역할 정책을 생성합니다.

다음 AWS CLI 명령 중 하나를 사용하여 IAM 정책을 생성합니다. <AWS Account ID>명령에 < sample-tvm-role-name >, 및 < sample-app-role-name > 값을 입력합니다.

macOS 또는 Linux 쉘의 경우:

aws iam put-role-policy \ --role-name <sample-tvm-role-name> \ --policy-name assume-app-role \ --policy-document '{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": "sts:AssumeRole", "Resource": "arn:aws:iam::<AWS Account ID>:role/<sample-app-role-name>" } ]}'

Windows 명령줄의 경우:

aws iam put-role-policy ^ --role-name <sample-tvm-role-name> ^ --policy-name assume-app-role ^ --policy-document "{\"Version\": \"2012-10-17\", \"Statement\": [{\"Effect\": \"Allow\", \"Action\": \"sts:AssumeRole\", \"Resource\": \"arn:aws:iam::<AWS Account ID>:role/<sample-app-role-name>\"}]}"

이 정책은 TVM 역할에 연결되어 있습니다. 이는 코드에 애플리케이션 역할을 맡을 수 있는 권한을 부여하며, 애플리케이션 역할은 S3 버킷에 액세스할 수 있는 더 넓은 권한을 가집니다.

클라우드 관리자

관리형 Lambda 정책을 연결합니다.

다음 AWS CLI 명령을 사용하여 AWSLambdaBasicExecutionRole IAM 정책에 연결합니다. 명령에 < sample-tvm-role-name > 값을 입력합니다.

aws iam attach-role-policy \ --role-name <sample-tvm-role-name> \ --policy-arn arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole

Windows 명령줄의 경우:

aws iam attach-role-policy ^ --role-name <sample-tvm-role-name> ^ --policy-arn arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole

이 관리형 정책은 Lambda가 Amazon에 로그를 전송할 수 있도록 TVM 역할에 연결됩니다. CloudWatch

클라우드 관리자
작업설명필요한 기술

애플리케이션 역할을 생성합니다.

다음 AWS CLI 명령 중 하나를 사용하여 IAM 역할을 생성합니다. <AWS Account ID>명령에 < sample-app-role-name >, 및 < sample-tvm-role-name > 값을 입력합니다.

macOS 또는 Linux 쉘의 경우:

aws iam create-role \ --role-name <sample-app-role-name> \ --assume-role-policy-document '{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": "arn:aws:iam::<AWS Account ID>:role/<sample-tvm-role-name>" }, "Action": "sts:AssumeRole" } ]}'

Windows 명령줄의 경우:

aws iam create-role ^ --role-name <sample-app-role-name> ^ --assume-role-policy-document "{\"Version\": \"2012-10-17\", \"Statement\": [{\"Effect\": \"Allow\",\"Principal\": {\"AWS\": \"arn:aws:iam::<AWS Account ID>:role/<sample-tvm-role-name>\"},\"Action\": \"sts:AssumeRole\"}]}"

Lambda 샘플 애플리케이션은 S3 버킷에 대한 테넌트 기반 액세스를 얻기 위해 범위 지정 정책을 통해 이 역할을 맡습니다.

클라우드 관리자

인라인 애플리케이션 역할 정책을 생성합니다.

다음 AWS CLI 명령 중 하나를 사용하여 IAM 정책을 생성합니다. 명령에 < sample-app-role-name >< sample-app-bucket-name > 값을 입력합니다.

macOS 또는 Linux 쉘의 경우:

aws iam put-role-policy \ --role-name <sample-app-role-name> \ --policy-name s3-bucket-access \ --policy-document '{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "s3:PutObject", "s3:GetObject", "s3:DeleteObject" ], "Resource": "arn:aws:s3:::<sample-app-bucket-name>/*" }, { "Effect": "Allow", "Action": ["s3:ListBucket"], "Resource": "arn:aws:s3:::<sample-app-bucket-name>" } ]}'

Windows 명령줄의 경우:

aws iam put-role-policy ^ --role-name <sample-app-role-name> ^ --policy-name s3-bucket-access ^ --policy-document "{\"Version\": \"2012-10-17\", \"Statement\": [{\"Effect\": \"Allow\", \"Action\": [\"s3:PutObject\", \"s3:GetObject\", \"s3:DeleteObject\"], \"Resource\": \"arn:aws:s3:::<sample-app-bucket-name>/*\"}, {\"Effect\": \"Allow\", \"Action\": [\"s3:ListBucket\"], \"Resource\": \"arn:aws:s3:::<sample-app-bucket-name>\"}]}"

이 정책은 애플리케이션 역할에 연결되어 있습니다. S3 버킷에 있는 객체에 대한 폭넓은 액세스를 제공합니다. 샘플 애플리케이션이 역할을 맡으면 TVM의 동적으로 생성되는 정책에 따라 이러한 권한의 범위가 특정 테넌트로 제한됩니다.

클라우드 관리자
작업설명필요한 기술

컴파일된 소스 파일을 다운로드합니다.

첨부 파일로 포함된 s3UploadSample.jartvm-layer.zip 파일을 다운로드합니다. 이러한 아티팩트를 만드는 데 사용된 소스 코드와 컴파일 지침은 token-vending-machine-sample-app.zip에 제공됩니다.

클라우드 관리자

Lambda 레이어를 생성합니다.

다음 AWS CLI 명령을 사용하여 Lambda 계층을 생성하면 Lambda가 TVM에 액세스할 수 있습니다. 

참고:  tvm-layer.zip을 다운로드한 위치에서 이 명령을 실행하지 않는 경우 --zip-file 파라미터의 tvm-layer.zip에 올바른 경로를 제공하세요. 

aws lambda publish-layer-version \ --layer-name sample-token-vending-machine \ --compatible-runtimes java11 \ --zip-file fileb://tvm-layer.zip

Windows 명령줄의 경우:

aws lambda publish-layer-version ^ --layer-name sample-token-vending-machine ^ --compatible-runtimes java11 ^ --zip-file fileb://tvm-layer.zip

이 명령은 재사용 가능한 TVM 라이브러리를 포함하는 Lambda 계층을 생성합니다.

클라우드 관리자, 앱 개발자

Lambda 함수를 생성합니다.

다음 AWS CLI 명령을 사용하여 Lambda 함수를 생성합니다. <AWS Account ID><AWS Region>명령에 < sample-app-function-name >,, < sample-tvm-role-name >, < sample-app-bucket-name >, < sample-app-role-name > 및 < > 값을 입력합니다. 

참고: s3UploadSample.jar를 다운로드한 위치에서 이 명령을 실행하지 않는 경우 --zip-file 파라미터의 s3UploadSample.jar에 올바른 경로를 입력하세요. 

aws lambda create-function \ --function-name <sample-app-function-name> \ --timeout 30 \ --memory-size 256 \ --runtime java11 \ --role arn:aws:iam::<AWS Account ID>:role/<sample-tvm-role-name> \ --handler com.amazon.aws.s3UploadSample.App \ --zip-file fileb://s3UploadSample.jar \ --layers arn:aws:lambda:<AWS Region>:<AWS Account ID>:layer:sample-token-vending-machine:1 \ --environment "Variables={S3_BUCKET=<sample-app-bucket-name>, ROLE=arn:aws:iam::<AWS Account ID>:role/<sample-app-role-name>}"

Windows 명령줄의 경우:

aws lambda create-function ^ --function-name <sample-app-function-name> ^ --timeout 30 ^ --memory-size 256 ^ --runtime java11 ^ --role arn:aws:iam::<AWS Account ID>:role/<sample-tvm-role-name> ^ --handler com.amazon.aws.s3UploadSample.App ^ --zip-file fileb://s3UploadSample.jar ^ --layers arn:aws:lambda:<AWS Region>:<AWS Account ID>:layer:sample-token-vending-machine:1 ^ --environment "Variables={S3_BUCKET=<sample-app-bucket-name>,ROLE=arn:aws:iam::<AWS Account ID>:role/<sample-app-role-name>}"

이 명령은 샘플 애플리케이션 코드와 TVM 계층이 연결된 Lambda 함수를 생성합니다. 또한 두 개의 환경 변수인 S3_BUCKETROLE을 설정합니다. 샘플 애플리케이션은 이러한 변수를 사용하여 맡을 역할과 JSON 문서를 업로드할 S3 버킷을 결정합니다.

클라우드 관리자, 앱 개발자
작업설명필요한 기술

Lambda 샘플 애플리케이션을 호출합니다.

다음 AWS CLI 명령 중 하나를 사용하여 예상 페이로드로 Lambda 샘플 애플리케이션을 시작합니다. 명령에 < sample-app-function-name >< sample-tenant-name > 값을 입력합니다.

macOS 및 Linux 쉘의 경우:

aws lambda invoke \ --function <sample-app-function-name> \ --invocation-type RequestResponse \ --payload '{"tenant": "<sample-tenant-name>"}' \ --cli-binary-format raw-in-base64-out response.json

Windows 명령줄의 경우:

aws lambda invoke ^ --function <sample-app-function-name> ^ --invocation-type RequestResponse ^ --payload "{\"tenant\": \"<sample-tenant-name>\"}" ^ --cli-binary-format raw-in-base64-out response.json

이 명령은 Lambda 함수를 호출하고 결과를 response.json 문서에 반환합니다. 대부분의 UNIX 기반 시스템에서는 다른 파일을 생성하지 않고도 결과를 쉘에 직접 출력하도록 response.json/dev/stdout으로 변경할 수 있습니다. 

참고: 이후에 이 Lambda 함수를 호출할 때 < sample-tenant-name > 값을 변경하면 JSON 문서의 위치와 토큰이 제공하는 권한이 변경됩니다.

클라우드 관리자, 앱 개발자

S3 버킷을 보면 생성된 객체를 확인할 수 있습니다.

이전에 생성한 S3 버킷 (< sample-app-bucket-name >) 을 찾아보십시오. 이 버킷에는 값이 < sample-tenant-name >인 S3 객체 접두사가 포함되어 있습니다. 이 접두사 아래에는 UUID로 이름이 지정된 JSON 문서가 있습니다. 샘플 애플리케이션을 여러 번 호출하면 더 많은 JSON 문서가 추가됩니다.

클라우드 관리자

샘플 애플리케이션의 Cloudwatch 로그를 볼 수 있습니다.

이름이 < >인 Lambda 함수와 관련된 클라우드워치 로그를 확인하십시오. sample-app-function-name 지침은 AWS Lambda 설명서에서 AWS Lambda의 아마존 CloudWatch 로그에 액세스하기를 참조하십시오. 이 로그에서 TVM이 생성한 테넌트 범위 정책을 확인할 수 있습니다. 이 테넌트 범위 정책은 샘플 애플리케이션에 대한 권한을 Amazon S3 PutObject, GetObjectDeleteObject, 및 ListBucketAPI에 부여하지만 < >와 관련된 객체 접두사에 대해서만 권한을 부여합니다. sample-tenant-name 이후 샘플 애플리케이션을 호출할 때 < sample-tenant-name >를 변경하면 TVM은 호출 페이로드에 제공된 테넌트에 대응하도록 범위 지정 정책을 업데이트합니다. 동적으로 생성되는 이 정책은 SaaS 애플리케이션에서 TVM을 통해 테넌트 범위 액세스를 유지하는 방법을 보여줍니다. 

TVM 기능은 Lambda 계층에서 제공되므로 코드를 복제하지 않고도 애플리케이션에서 사용하는 다른 Lambda 함수에 연결할 수 있습니다.

동적으로 생성되는 정책에 대한 설명은 추가 정보 섹션을 참조하세요.

클라우드 관리자

관련 리소스

추가 정보

다음 Amazon CloudWatch Log는 TVM 코드에 따라 이러한 패턴으로 생성된 동적으로 생성된 정책을 보여줍니다. 이 스크린샷에서 < >는 이고 < sample-app-bucket-name >는 입니다DOC-EXAMPLE-BUCKET. sample-tenant-name test-tenant-1 지정된 이 범위 정책에서 반환된 STS 보안 인증은 객체 키 접두사 test-tenant-1와 연결된 객체를 제외하고 S3 버킷의 객체에 대해 어떠한 작업도 수행할 수 없습니다.

첨부

이 문서와 관련된 추가 콘텐츠에 액세스하려면 attachment.zip 파일의 압축을 풉니다.