Skip to content

Feature: Add S3 bucket access for client VMs #33

Description

@eberrigan

Summary

Add the ability for client VMs to access secure S3 buckets for research data. This addresses feedback from SfN about researchers wanting easy access to secure data storage.

Motivation

"People want easy access to secure data"
"Add S3 buckets to config?"

Currently, client VMs only access data via Git repository cloning (machine.repository in config). Researchers need a way to:

  • Access large datasets that don't fit in Git
  • Share data securely between VMs
  • Store outputs/results persistently (client VMs are ephemeral)

Proposed Configuration

Add a new storage section to config/config.yaml:

storage:
  enabled: true
  buckets:
    - name: "my-research-data"
      access: "read"           # read, write, or read-write
      mount_path: "/data"      # optional: mount point on client VM
      prefix: "project-alpha/" # optional: restrict to prefix
    - name: "my-results-bucket"
      access: "write"
      mount_path: "/results"

Implementation Approach

Key Code Locations

Component File Lines Changes Needed
Config parsing main.tf 29-78 Add local.storage_* variables
Client VM IAM main.tf 123-218 Add S3 policy for client role
Startup script user_data.sh 1-116 Pass bucket config to container
Example configs config/*.example.yaml - Add storage examples

IAM Policy Addition

The allocator already creates IAM roles for client VMs at main.tf:123-218. We need to extend this to include S3 bucket permissions:

# New policy for client VM S3 access
data "aws_iam_policy_document" "client_s3_access" {
  count = local.storage_enabled ? 1 : 0
  
  dynamic "statement" {
    for_each = local.storage_buckets
    content {
      effect = "Allow"
      actions = statement.value.access == "read" ? [
        "s3:GetObject",
        "s3:ListBucket"
      ] : statement.value.access == "write" ? [
        "s3:PutObject",
        "s3:DeleteObject"
      ] : [
        "s3:GetObject",
        "s3:PutObject",
        "s3:DeleteObject",
        "s3:ListBucket"
      ]
      resources = [
        "arn:aws:s3:::${statement.value.name}",
        "arn:aws:s3:::${statement.value.name}/${statement.value.prefix}*"
      ]
    }
  }
}

Client VM Access Methods

Option A: AWS CLI (Recommended for simplicity)

  • Pre-installed on client VMs
  • Uses instance profile credentials automatically
  • Commands: aws s3 cp, aws s3 sync

Option B: s3fs-fuse mount

  • Mount S3 as filesystem at mount_path
  • Transparent file access (like local storage)
  • Higher complexity, potential performance issues

Option C: Both

  • AWS CLI always available
  • Optional mounting via config flag

Design Decisions to Discuss

1. Bucket Management Strategy

Option Pros Cons
A. Reference existing buckets Simple, no Terraform changes to S3 Requires manual bucket creation
B. Create buckets via Terraform Fully automated More complex, bucket naming conflicts
C. Hybrid (default: reference, optional: create) Flexible More config options

Recommendation: Option A initially (reference existing), with Option B as future enhancement.

2. Cross-Account Access

Should client VMs access buckets in different AWS accounts?

  • Yes: Requires bucket policies or assume-role configuration
  • No: Simpler, buckets must be in same account as deployment

Recommendation: Same-account only for v1, with cross-account as future feature.

3. Mount Point Configuration

Option Behavior
No mount_path AWS CLI access only
With mount_path s3fs mount + AWS CLI

4. Encryption Requirements

  • Should we require server-side encryption (SSE-S3, SSE-KMS)?
  • Should we support client-side encryption?

Recommendation: Document best practices, don't enforce in Terraform.

Breaking Changes

Potentially Breaking

  1. Config Schema: New storage section - NOT breaking (optional, defaults to disabled)

  2. Client VM IAM Role: Extended permissions - NOT breaking (additive only)

  3. Allocator Container: Must pass bucket config to client VM provisioning - Requires allocator changes

Non-Breaking Path

If we implement with:

  • storage.enabled: false as default
  • No changes to existing config structure
  • Additive IAM policies only

Then no breaking changes for existing deployments.

Dependencies

  • The allocator service (lablink-client-base-image) needs updates to:
    1. Accept bucket configuration
    2. Configure client VM startup to mount/access buckets
    3. Pass IAM policy to client VM creation

Tasks

  • Add storage section to config schema
  • Add locals for storage config in main.tf
  • Create IAM policy document for client S3 access
  • Update allocator IAM policy to allow passing S3 permissions to clients
  • Update example configs with storage examples
  • Document storage configuration in README
  • Coordinate with allocator service for client-side implementation
  • Add validation for bucket names/access patterns

Related Files

Questions for Discussion

  1. Should we support bucket creation or only reference existing buckets?
  2. Is cross-account access a requirement for v1?
  3. Should mounting (s3fs) be supported or CLI-only access?
  4. What's the priority for encryption enforcement?

Feedback from SfN 2024

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions