> ## Documentation Index
> Fetch the complete documentation index at: https://cloudanix.com/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Sagemaker notebook data encrypted remediation

### Triage and Remediation

<Tabs>
  <Tab title="Remediation">
    ### Remediation

    <AccordionGroup>
      <Accordion title="Using Console" defaultOpen="true">
        For DynamoDB, “notebook data” translates to DynamoDB table data needing encryption at rest.

        DynamoDB already encrypts all table data at rest by default with an AWS-owned KMS key. If your requirement is stricter (e.g., must use a customer-managed KMS key), follow these steps in the AWS Console:

        ***

        ### 1. Confirm Encryption Status of the Table

        1. Sign in to the **AWS Management Console**.
        2. Go to **DynamoDB**.
        3. In the left menu, click **Tables**.
        4. Click the specific table.
        5. Choose the **Additional settings** or **Overview** tab (depending on UI version).
        6. Look for **Encryption at rest**:
           * It should show something like:
             * **Encryption type**: AWS owned key\
               or
             * **KMS key**: alias/aws/dynamodb\
               or
             * **KMS key**: `alias/your-cmk-alias`

        If encryption is already enabled (it always is), you only need remediation if your policy requires a **customer-managed KMS key (CMK)**.

        ***

        ### 2. (If Required) Create a Customer-Managed KMS Key

        1. In the console, open **Key Management Service (KMS)**.
        2. Click **Customer managed keys** → **Create key**.
        3. Key type: **Symmetric**.
        4. Key usage: **Encrypt and decrypt**.
        5. Set **Alias** (e.g., `alias/dynamodb-notebook-data`).
        6. Configure **Key administrators** and **Key users**:
           * Ensure the IAM roles/services that use DynamoDB have permission to use this key.
        7. Finish key creation.

        ***

        ### 3. Update DynamoDB Table to Use the Customer-Managed KMS Key

        > Note: DynamoDB encryption with AWS-owned/AWS-managed key is default; using a **customer-managed key** is an optional enhancement. UI labels may differ slightly between regions/UI versions but the flow is similar.

        1. Go back to **DynamoDB → Tables**.
        2. Select the table.
        3. Go to **Additional settings** or **Table details**.
        4. Find the **Encryption at rest** section.
        5. Click **Edit** (or **Manage encryption**).
        6. Change encryption from **AWS owned key** or default key to **Customer managed key**.
        7. From the dropdown, choose your new KMS key alias (e.g., `alias/dynamodb-notebook-data`).
        8. Save/Apply the change.

        DynamoDB will handle re-encryption transparently; no application changes are needed.

        ***

        ### 4. Validate Compliance

        1. Re-open the table **Details/Additional settings**.
        2. Confirm:
           * **Encryption at rest** is **Enabled**.
           * **KMS key** now references your customer-managed CMK alias.
        3. Optionally, in **KMS → Customer managed keys**, open the key and check **Key usage** / **CloudTrail** to see DynamoDB using the key.

        ***

        If your policy only says “must be encrypted,” DynamoDB’s default (AWS-owned key) already satisfies that; the remediation is primarily confirming and documenting that encryption at rest is enabled and enforced for all DynamoDB tables storing notebook data.
      </Accordion>

      <Accordion title="Using CLI">
        Below are the minimal, step‑by‑step AWS CLI steps to ensure DynamoDB “Notebook Data” is encrypted at rest.

        ***

        ### 1. Identify the DynamoDB table(s)

        If you already know the table name, skip to step 2.

        ```bash theme={null}
        aws dynamodb list-tables
        ```

        Assume your table is called `notebook-data-table` (replace with your actual name).

        ***

        ### 2. Check current encryption status

        ```bash theme={null}
        aws dynamodb describe-table \
          --table-name notebook-data-table \
          --query "Table.SSEDescription"
        ```

        Look at:

        * `Status` (ENABLED, ENABLING, DISABLED)
        * `SSEType` (KMS)
        * `KMSMasterKeyArn` (if using a CMK)

        If `Status` is `DISABLED` or not present, encryption is not enabled.

        ***

        ### 3. (Optional) Choose or create a KMS key

        If you want to use an AWS-managed key for DynamoDB (simplest), skip to step 4.

        To create a customer-managed KMS key:

        ```bash theme={null}
        aws kms create-key \
          --description "CMK for DynamoDB Notebook Data Encryption" \
          --query "KeyMetadata.KeyId" \
          --output text
        ```

        Note the returned `KeyId` or ARN.\
        Ensure the key policy allows DynamoDB and relevant IAM principals to use it.

        ***

        ### 4. Enable encryption on the table

        #### Option A – Use AWS-owned key (default encryption)

        ```bash theme={null}
        aws dynamodb update-table \
          --table-name notebook-data-table \
          --sse-specification Enabled=true
        ```

        #### Option B – Use AWS-managed KMS key for DynamoDB

        ```bash theme={null}
        aws dynamodb update-table \
          --table-name notebook-data-table \
          --sse-specification Enabled=true,SSEType=KMS
        ```

        #### Option C – Use your own customer-managed KMS key

        Replace `<kms-key-arn-or-id>` with your key:

        ```bash theme={null}
        aws dynamodb update-table \
          --table-name notebook-data-table \
          --sse-specification Enabled=true,SSEType=KMS,KMSMasterKeyId=<kms-key-arn-or-id>
        ```

        ***

        ### 5. Confirm encryption is enabled

        Run again:

        ```bash theme={null}
        aws dynamodb describe-table \
          --table-name notebook-data-table \
          --query "Table.SSEDescription"
        ```

        You should see:

        * `Status`: `ENABLED`
        * `SSEType`: `KMS`
        * `KMSMasterKeyArn`: set (if using KMS)

        Once done, the DynamoDB table storing notebook data is encrypted at rest.
      </Accordion>

      <Accordion title="Using Python">
        To encrypt DynamoDB “notebook data” at rest, you need to ensure the DynamoDB table has Server-Side Encryption (SSE) enabled, preferably with a customer-managed KMS key. Below are step-by-step instructions using Python (boto3).

        ***

        ## 1. Prerequisites

        * `boto3` installed:
          ```bash theme={null}
          pip install boto3
          ```
        * AWS credentials configured (via `aws configure`, environment variables, or an IAM role).
        * IAM permissions for:
          * `dynamodb:DescribeTable`
          * `dynamodb:UpdateTable`
          * `kms:CreateKey` (if you’ll create a new CMK)
          * `kms:DescribeKey`
          * `kms:EnableKeyRotation`
          * `kms:PutKeyPolicy` (as needed)

        ***

        ## 2. (Optional) Create a customer-managed KMS key for DynamoDB

        If you want to use your own CMK instead of the AWS-owned key:

        ```python theme={null}
        import boto3

        kms = boto3.client('kms', region_name='us-east-1')  # choose your region

        response = kms.create_key(
            Description='CMK for encrypting DynamoDB notebook data',
            KeyUsage='ENCRYPT_DECRYPT',
            Origin='AWS_KMS'
        )

        cmk_arn = response['KeyMetadata']['Arn']
        print("Created KMS CMK:", cmk_arn)

        # (Optional but recommended) enable key rotation
        kms.enable_key_rotation(KeyId=cmk_arn)
        ```

        Keep `cmk_arn` – you’ll use it in the DynamoDB SSE config.

        ***

        ## 3. Check current encryption status of the DynamoDB table

        ```python theme={null}
        import boto3

        dynamodb = boto3.client('dynamodb', region_name='us-east-1')  # choose your region
        table_name = 'your-notebook-data-table'

        desc = dynamodb.describe_table(TableName=table_name)
        print(desc['Table'].get('SSEDescription', 'No SSEDescription found'))
        ```

        Look at:

        * `SSEDescription['Status']` (e.g., `ENABLED`, `ENABLING`, `DISABLED`)
        * `SSEDescription['SSEType']` (e.g., `KMS`)
        * `SSEDescription['KMSMasterKeyArn']` (if using CMK)

        ***

        ## 4. Enable or update server-side encryption on the table

        ### Option A – Use AWS owned key (simpler)

        ```python theme={null}
        dynamodb.update_table(
            TableName=table_name,
            SSESpecification={
                'Enabled': True,
                'SSEType': 'KMS'  # with no KMSMasterKeyId, DynamoDB uses the AWS owned key
            }
        )
        ```

        ### Option B – Use customer-managed CMK (more control)

        Use the `cmk_arn` from step 2:

        ```python theme={null}
        cmk_arn = 'arn:aws:kms:us-east-1:123456789012:key/your-key-id-or-arn'

        dynamodb.update_table(
            TableName=table_name,
            SSESpecification={
                'Enabled': True,
                'SSEType': 'KMS',
                'KMSMasterKeyId': cmk_arn
            }
        )
        ```

        ***

        ## 5. Wait for encryption to finish and verify

        ```python theme={null}
        import time

        while True:
            desc = dynamodb.describe_table(TableName=table_name)
            sse = desc['Table'].get('SSEDescription', {})
            status = sse.get('Status')
            print("SSE Status:", status)

            if status in ['ENABLED', 'UPDATING']:
                break
            time.sleep(5)

        print("Final SSEDescription:", sse)
        ```

        Ensure:

        * `Status` is `ENABLED`
        * `SSEType` is `KMS`
        * `KMSMasterKeyArn` is set (if using CMK)

        ***

        ## 6. Enforce encryption via IaC / policy (optional but recommended)

        To prevent future unencrypted tables:

        * Use IaC (CloudFormation/Terraform) with `SSESpecification` always set.
        * Add AWS Config rule `dynamodb-table-encryption-enabled` and remediate non-compliant tables with an automation script similar to the above.

        This ensures that all “notebook data” stored in DynamoDB is encrypted at rest.
      </Accordion>

      <Accordion title="Using Terraform">
        ```hcl theme={null}
        resource "aws_kms_key" "SAGEMAKER_ENCRYPTION_KEY" {
          description         = "KMS key for SageMaker notebook volume encryption"
          enable_key_rotation = true

          # Optional: scope down key policy as required for your org
        }

        resource "aws_sagemaker_notebook_instance" "SAGEMAKER_NOTEBOOK" {
          # Substitute:
          # - NOTEBOOK_NAME with the desired SageMaker notebook instance name
          # - INSTANCE_TYPE with the SageMaker instance type (e.g., "ml.t3.medium")
          # - IAM_ROLE_ARN with the ARN of the SageMaker execution role that has KMS permissions
          name          = "NOTEBOOK_NAME"
          instance_type = "INSTANCE_TYPE"
          role_arn      = "IAM_ROLE_ARN"

          # This is the critical setting: enables encryption of the notebook's EBS volume
          kms_key_id = aws_kms_key.SAGEMAKER_ENCRYPTION_KEY.arn

          # Optionally mirror any existing networking configuration:
          # subnet_id         = "SUBNET_ID"
          # security_group_ids = ["SECURITY_GROUP_ID_1", "SECURITY_GROUP_ID_2"]
        }
        ```

        Changing `kms_key_id` on an existing `aws_sagemaker_notebook_instance` forces resource replacement: Terraform will destroy the current unencrypted notebook instance and create a new, encrypted one. This is destructive and irreversible, and any data on the original notebook’s volume must be backed up and restored manually to the new instance.

        To verify, `terraform plan` should show the current unencrypted `aws_sagemaker_notebook_instance` scheduled for `-/+` replacement, with the new resource including `kms_key_id = aws_kms_key.SAGEMAKER_ENCRYPTION_KEY.arn`.
      </Accordion>
    </AccordionGroup>
  </Tab>
</Tabs>
