Back to Checks
aws

Glue job has S3 encryption enabled

glue_etl_jobs_amazon_s3_encryption_enabled
Service: glueSeverity: high
OfficialBuilt-inVerified
Categories:encryption
Resource Type:Other

AWS Glue ETL jobs are validated to use Amazon S3 at-rest encryption (SSE-S3 or SSE-KMS) when writing outputs, either through an attached security configuration or via job arguments. Jobs missing a security configuration or with S3 encryption disabled are identified.

Risk

Storing job outputs in S3 without at-rest encryption weakens confidentiality. Plaintext objects can be exposed via misconfigured bucket policies, compromised credentials, or media reuse, and lack KMS key controls, rotation, and audit trails-hindering incident response and compliance.

Run this check with Prowler

Run in Prowler Cloud
Run
prowler aws --checks glue_etl_jobs_amazon_s3_encryption_enabled

Recommendation

Require S3 encryption for all Glue jobs via security configurations, preferring SSE-KMS. Apply least privilege to KMS keys, restrict key usage and rotate regularly. Enforce defense-in-depth with bucket policies that require encrypted writes, and monitor with key and S3 access logs.

Remediation

Terraform

# Terraform: Attach a Security Configuration with S3 encryption to a Glue job
resource "aws_glue_security_configuration" "sec" {
  name = "<example_resource_name>"

  s3_encryption {
    s3_encryption_mode = "SSE-S3"  # CRITICAL: Enables S3 encryption for Glue outputs
  }
}

resource "aws_glue_job" "job" {
  name     = "<example_resource_name>"
  role_arn = "<example_role_arn>"

  command {
    script_location = "s3://<example_resource_name>/script.py"
  }

  security_configuration = aws_glue_security_configuration.sec.name  # CRITICAL: Applies encrypted security configuration to the job
}

NativeIaC

# CloudFormation: Attach a Security Configuration with S3 encryption to a Glue job
Resources:
  GlueSecurityConfiguration:
    Type: AWS::Glue::SecurityConfiguration
    Properties:
      Name: <example_resource_name>
      EncryptionConfiguration:
        S3Encryptions:
          - S3EncryptionMode: SSE-S3  # CRITICAL: Enables S3 encryption for Glue outputs

  GlueJob:
    Type: AWS::Glue::Job
    Properties:
      Name: <example_resource_name>
      Role: <example_role_arn>
      Command:
        Name: glueetl
        ScriptLocation: s3://<example_resource_name>/script.py
      SecurityConfiguration: !Ref GlueSecurityConfiguration  # CRITICAL: Applies encrypted security configuration to the job

Other

1In the AWS Console, go to AWS Glue > Security configurations > Create security configuration
2Enable S3 encryption and choose SSE-S3 (or SSE-KMS with your key)
3Save the configuration
4Go to AWS Glue > Jobs > select your job > Edit
5Under Job details, set Security configuration to the encrypted configuration you created
6Save the job

Check Code

from prowler.lib.check.models import Check, Check_Report_AWS
from prowler.providers.aws.services.glue.glue_client import glue_client


class glue_etl_jobs_amazon_s3_encryption_enabled(Check):
    def execute(self):
        findings = []
        for job in glue_client.jobs:
            no_sec_configs = True
            report = Check_Report_AWS(metadata=self.metadata(), resource=job)
            for sec_config in glue_client.security_configs:
                if sec_config.name == job.security:
                    no_sec_configs = False
                    report.status = "FAIL"
                    report.status_extended = (
                        f"Glue job {job.name} does not have S3 encryption enabled."
                    )
                    if sec_config.s3_encryption != "DISABLED":
                        report.status = "PASS"
                        report.status_extended = f"Glue job {job.name} has S3 encryption enabled with key {sec_config.s3_key_arn}."
            if no_sec_configs:
                if job.arguments and job.arguments.get("--encryption-type") == "sse-s3":
                    report.status = "PASS"
                    report.status_extended = (
                        f"Glue job {job.name} has S3 encryption enabled."
                    )
                else:
                    report.status = "FAIL"
                    report.status_extended = (
                        f"Glue job {job.name} does not have security configuration."
                    )
            findings.append(report)
        return findings