def attach_volume()

in cookbooks/aws-parallelcluster-environment/files/default/ec2_udev_rules/manageVolume.py [0:0]


def attach_volume(volume_id, instance_id, ec2):
    # Generate a list of system paths minus the root path
    paths = [adapt_device_name(device) for device in get_all_devices()]

    # List of possible block devices
    block_devices = [
        "/dev/sdb",
        "/dev/sdc",
        "/dev/sdd",
        "/dev/sde",
        "/dev/sdf",
        "/dev/sdg",
        "/dev/sdh",
        "/dev/sdi",
        "/dev/sdj",
        "/dev/sdk",
        "/dev/sdl",
        "/dev/sdm",
        "/dev/sdn",
        "/dev/sdo",
        "/dev/sdp",
        "/dev/sdq",
        "/dev/sdr",
        "/dev/sds",
        "/dev/sdt",
        "/dev/sdu",
        "/dev/sdv",
        "/dev/sdw",
        "/dev/sdx",
        "/dev/sdy",
        "/dev/sdz",
    ]

    # List of available block devices after removing currently used block devices
    available_devices = [a for a in block_devices if a not in paths]

    # Attach the volume
    dev = available_devices[0]
    response = ec2.attach_volume(VolumeId=volume_id, InstanceId=instance_id, Device=dev)

    mapping_file_path = "/dev/disk/by-ebs-volumeid/parallelcluster_dev_id_mapping"
    if os.path.isfile(mapping_file_path):
        with open(mapping_file_path, "r", encoding="utf-8") as mapping_file:
            mapping = json.load(mapping_file)
    else:
        mapping = {}
    mapping[dev] = volume_id
    os.makedirs(os.path.dirname(mapping_file_path), exist_ok=True)
    with open(mapping_file_path, "w", encoding="utf-8") as mapping_file:
        json.dump(mapping, mapping_file)

    # Poll for volume to attach
    state = response.get("State")
    delay = 5  # seconds
    elapsed = 0
    timeout = 300  # seconds
    while state != "attached":
        if elapsed >= timeout:
            print(f"ERROR: Volume {volume_id} failed to mount in {timeout} seconds.")
            sys.exit(1)
        if state in ["busy", "detached"]:
            print(f"ERROR: Volume {volume_id} in bad state {state}")
            sys.exit(1)
        print(f"Volume {volume_id} in state {state} ... waiting to be 'attached'")
        time.sleep(delay)
        elapsed += delay
        try:
            state = ec2.describe_volumes(VolumeIds=[volume_id]).get("Volumes")[0].get("Attachments")[0].get("State")
        except IndexError:
            continue