floci-io/floci · error · AwsException

AlreadyExists

AlreadyExists

Error message

Launch configuration '{name}' already exists.

What it means

Thrown by the Auto Scaling emulator when CreateLaunchConfiguration uses a name that already exists in the given region. AWS Auto Scaling launch configuration names are region-unique; the real service returns AlreadyExists (HTTP 400 in this emulator) on duplicates.

Source

Thrown at src/main/java/io/github/hectorvent/floci/services/autoscaling/AutoScalingService.java:80

        this.activities = storageBacked("autoscaling-activities.json", new TypeReference<Map<String, ScalingActivity>>() {});
        this.instanceRefreshes = storageBacked("autoscaling-instance-refreshes.json", new TypeReference<Map<String, InstanceRefresh>>() {});
    }

    private <V> Map<String, V> storageBacked(String fileName, TypeReference<Map<String, V>> typeReference)
    {
        return new StorageBackedMap<>(storageFactory.create("autoscaling", fileName, typeReference));
    }

    // ── Launch Configurations ──────────────────────────────────────────────────

    public LaunchConfiguration createLaunchConfiguration(String region, String name, String instanceId,
                                                          String imageId, String instanceType, String keyName,
                                                          List<String> securityGroups, String userData,
                                                          String iamInstanceProfile,
                                                          Boolean associatePublicIpAddress) {
        String key = lcKey(region, name);
        if (launchConfigs.containsKey(key)) {
            throw new AwsException("AlreadyExists",
                    "Launch configuration '" + name + "' already exists.", 400);
        }
        if (isBlank(instanceId) && (isBlank(imageId) || isBlank(instanceType))) {
            throw new AwsException("ValidationError", INVALID_LAUNCH_CONFIGURATION_PARAMETERS_MESSAGE, 400);
        }
        if (notBlank(instanceId) && ec2Service != null) {
            List<Instance> sourceInstances = ec2Service.describeInstances(region, List.of(instanceId), Map.of())
                    .stream()
                    .flatMap(reservation -> reservation.getInstances().stream())
                    .collect(Collectors.toList());
            if (!sourceInstances.isEmpty()) {
                Instance source = sourceInstances.getFirst();
                if (isBlank(imageId)) {
                    imageId = source.getImageId();
                }
                if (isBlank(instanceType)) {
                    instanceType = source.getInstanceType();
                }

View on GitHub (pinned to 62ff490619)

Solutions

  1. Check describeLaunchConfigurations for the name first and skip creation if present (or delete-then-create for updates).
  2. Use unique names per run (timestamp/UUID suffix) in tests.
  3. Remember launch configurations are immutable in AWS — to change one, create a new name and update the ASG.
  4. Clear persistent emulator storage between test sessions if fixtures are assumed fresh.

Example fix

# before
aws autoscaling create-launch-configuration \
  --launch-configuration-name web --image-id ami-123 --instance-type t3.micro

# after
aws autoscaling delete-launch-configuration --launch-configuration-name web || true
aws autoscaling create-launch-configuration \
  --launch-configuration-name web --image-id ami-123 --instance-type t3.micro
Defensive patterns

Strategy: validation

Validate before calling

boolean exists = autoScalingClient.describeLaunchConfigurations(
        r -> r.launchConfigurationNames(name)).launchConfigurations().stream()
        .anyMatch(lc -> name.equals(lc.launchConfigurationName()));
if (!exists) autoScalingClient.createLaunchConfiguration(req);

Try / catch

try {
    autoScalingClient.createLaunchConfiguration(req);
} catch (AutoScalingException e) {
    if ("AlreadyExists".equals(e.awsErrorDetails().errorCode())) return; // idempotent
    throw e;
}

Prevention

When it happens

Trigger: Calling createLaunchConfiguration twice with the same name in the same region; re-running a provisioning script; integration tests against persistent emulator storage where launch configs survived the previous run.

Common situations: Non-idempotent bootstrap scripts; emulator persistence mode keeping state across restarts; parallel CI jobs sharing one emulator instance.

Related errors


AI-assisted analysis of floci-io/floci@62ff490619 (2026-08-14). Data as JSON: /api/errors/1d78840ff9a6b479. Report an issue: GitHub.