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

# Import existing Gcore infrastructure into Terraform

Terraform is not limited to resources it creates. Infrastructure that already exists — whether created manually in the [Gcore Customer Portal](https://portal.gcore.com), through the API, or by another Terraform configuration — can be brought under Terraform management without being recreated. This process is called `import` and is commonly used when teams migrate existing environments to infrastructure-as-code, recover from lost state files, or reorganize infrastructure between configurations.

## Import process

Without import, Terraform does not know about resources outside its state file, so `terraform plan` shows them as `+ create` — meaning it would create duplicates. Import solves this:

1. Terraform reads the resource's current state from the Gcore API using the resource ID.
2. It writes that state into `terraform.tfstate`.
3. From that point, `terraform plan` compares the configuration against the recorded state and reports only the actual differences.

## Prepare for import

Every import requires a resource type and a resource ID; find both in the **Import** section of each resource's page on the [Terraform Registry](https://registry.terraform.io/providers/G-Core/gcore/latest/docs).

| What                                               | Example                                                      |
| -------------------------------------------------- | ------------------------------------------------------------ |
| The resource type as used in Terraform             | `gcore_cloud_project`, `gcore_cloud_network`                 |
| The resource ID in the format the provider expects | `1186668` for a project, `1186668/76/abc-uuid` for a network |

Terraform offers two import methods — choose based on scope and team workflow:

|                                         | `terraform import`         | `import` block                |
| --------------------------------------- | -------------------------- | ----------------------------- |
| **Availability**                        | All Terraform CLI versions | Terraform CLI 1.5+            |
| **Modifies `.tf` files**                | No                         | No (but can generate config)  |
| **Visible in `terraform plan`**         | No                         | Yes                           |
| **Can be committed to version control** | No                         | Yes                           |
| **Best for**                            | Quick one-off imports      | Team workflows, IaC pipelines |

## Run an import command

The `terraform import` command binds an existing resource to a resource block in the configuration and writes its state immediately. It works with all Terraform CLI versions and requires no changes to `.tf` files beyond adding the resource block.

### Step 1. Write a resource block

Create a resource block in the `.tf` configuration with at minimum the required fields, listed in the resource's schema on Terraform Registry.

For a Gcore project:

```hcl theme={null}
resource "gcore_cloud_project" "default" {
  name = "Default"
}
```

### Step 2. Run terraform import

The import command format is:

```bash theme={null}
terraform import <resource_address> '<resource_id>'
```

Where `<resource_address>` is `<resource_type>.<local_name>` — matching the resource block written in Step 1.

```bash theme={null}
terraform import gcore_cloud_project.default '1186668'
```

Expected output:

```
gcore_cloud_project.default: Importing from ID "1186668"...
gcore_cloud_project.default: Import prepared!
  Prepared gcore_cloud_project for import
gcore_cloud_project.default: Refreshing state... [name=Default]

Import successful!

The resources that were imported are shown above. These resources are now in
your Terraform state and will henceforth be managed by Terraform.
```

### Step 3. Run terraform plan after import

Run plan to verify there is no attribute drift between the configuration and the imported state:

```bash theme={null}
terraform plan
```

```
gcore_cloud_project.default: Refreshing state... [name=Default]

No changes. Your infrastructure matches the configuration.

Terraform has compared your real infrastructure against your configuration
and found no differences, so no changes are needed.
```

If `terraform plan` still shows changes, the resource block in `.tf` has attributes that do not match the imported state. Update the configuration until `terraform plan` reports no changes.

## Add an import block to configuration

The `import` block is the recommended approach for team environments. It makes the import operation visible in `terraform plan`, so the intent is reviewable before state is modified.

### Step 1. Write an import block

Add an `import` block to any `.tf` file alongside the target resource block:

```hcl theme={null}
resource "gcore_cloud_project" "default" {
  name = "Default"
}

import {
  id = "1186668"
  to = gcore_cloud_project.default
}
```

The `to` field must match the `<resource_type>.<local_name>` of the resource block.

### Step 2. Run terraform plan

Run plan to preview the full resource state before the import is applied:

```bash theme={null}
terraform plan
```

```
gcore_cloud_project.default: Preparing import... [id=1186668]
gcore_cloud_project.default: Refreshing state... [name=Default]

Terraform will perform the following actions:

  # gcore_cloud_project.default will be imported
    resource "gcore_cloud_project" "default" {
        client_id   = 1000503
        created_at  = "2026-04-17T12:43:36Z"
        description = "Default project"
        id          = 1186668
        is_default  = true
        name        = "Default"
        state       = "ACTIVE"
    }

Plan: 1 to import, 0 to add, 0 to change, 0 to destroy.
```

The plan shows the full resource state that will be written to the state file.

### Step 3. Apply

After reviewing the plan, apply to write the resource into state:

```bash theme={null}
terraform apply
```

```
gcore_cloud_project.default: Importing... [id=1186668]
gcore_cloud_project.default: Import complete [id=1186668]

Apply complete! Resources: 1 imported, 0 added, 0 changed, 0 destroyed.
```

After a successful import, remove the `import` block from the configuration — it is no longer needed and will cause an error if left in place after the resource is already in state.

## Generate configuration automatically

When importing a resource that has many attributes, writing the resource block manually is time-consuming. Use the `-generate-config-out` flag to generate the block automatically.

### Step 1. Write only the import block (no resource block)

Add only an `import` block — no resource block. Terraform generates it automatically in the next step:

```hcl theme={null}
import {
  id = "1186668"
  to = gcore_cloud_project.default
}
```

### Step 2. Run terraform plan with -generate-config-out

Pass the flag to specify the output file name. Terraform generates the resource block and writes it to that file:

<Tabs>
  <Tab title="PowerShell">
    ```powershell theme={null}
    terraform plan "-generate-config-out=generated.tf"
    ```
  </Tab>

  <Tab title="Bash / Zsh">
    ```bash theme={null}
    terraform plan -generate-config-out=generated.tf
    ```
  </Tab>
</Tabs>

```
gcore_cloud_project.default: Preparing import... [id=1186668]
gcore_cloud_project.default: Refreshing state... [name=Default]

Terraform will perform the following actions:

  # gcore_cloud_project.default will be imported
  # (config will be generated)
    resource "gcore_cloud_project" "default" {
        ...
    }

Plan: 1 to import, 0 to add, 0 to change, 0 to destroy.

Warning: Config generation is experimental

Terraform has generated configuration and written it to generated.tf. Please
review the configuration and edit it as necessary before adding it to version
control.
```

### Step 3. Review and prune generated.tf

Terraform writes the full resource schema to `generated.tf`:

```hcl theme={null}
# __generated__ by Terraform
# Please review these resources and move them into your main configuration files.

# __generated__ by Terraform from "1186668"
resource "gcore_cloud_project" "default" {
  description = "Default project"
  name        = "Default"
}
```

Remove read-only and default-value attributes from `generated.tf`, then move the pruned configuration into the main `.tf` files and delete `generated.tf`.

<Info>
  Config generation is marked experimental. The generated output may include read-only attributes that Terraform does not accept as input. Remove any attribute that the provider schema marks as read-only (`client_id`, `created_at`, `id`, `is_default`, `state` in this example) before running `terraform apply`.
</Info>

## Import ID reference

The import ID format varies by resource. Common Gcore resources:

| Resource                     | Import ID format                         | Example               |
| ---------------------------- | ---------------------------------------- | --------------------- |
| `gcore_cloud_project`        | `<project_id>`                           | `1186668`             |
| `gcore_cloud_network`        | `<project_id>/<region_id>/<network_id>`  | `1186668/76/abc-uuid` |
| `gcore_cloud_network_subnet` | `<project_id>/<region_id>/<subnet_id>`   | `1186668/76/xyz-uuid` |
| `gcore_cloud_instance`       | `<project_id>/<region_id>/<instance_id>` | `1186668/76/def-uuid` |
| `gcore_cloud_volume`         | `<project_id>/<region_id>/<volume_id>`   | `1186668/76/ghi-uuid` |
| `gcore_cloud_k8s_cluster`    | `<project_id>/<region_id>/<cluster_id>`  | `1186668/76/jkl-uuid` |
| `gcore_cloud_load_balancer`  | `<project_id>/<region_id>/<lb_id>`       | `1186668/76/mno-uuid` |
| `gcore_dns_zone`             | `<zone_name>`                            | `example.com`         |

Find project and region IDs in the [Gcore Customer Portal](https://portal.gcore.com) or via the `data "gcore_cloud_project"` and `data "gcore_cloud_region"` data sources; resource UUIDs appear in the portal URL and in Gcore API responses. Check the **Import** section of the specific resource page on Terraform Registry for the exact format.

## Inspect and manage state

After import, use `terraform state` subcommands to inspect what is recorded:

```bash theme={null}
# List all resources in state
terraform state list
```

```
gcore_cloud_project.default
```

```bash theme={null}
# Show full details of a resource in state
terraform state show gcore_cloud_project.default
```

```
# gcore_cloud_project.default:
resource "gcore_cloud_project" "default" {
    client_id   = 1000503
    created_at  = "2026-04-17T12:43:36Z"
    description = "Default project"
    id          = 1186668
    is_default  = true
    name        = "Default"
    state       = "ACTIVE"
}
```

```bash theme={null}
# Remove a resource from state without destroying it
terraform state rm gcore_cloud_project.default
```

```
Removed gcore_cloud_project.default
Successfully removed 1 resource instance(s).
```

<Warning>
  `terraform state rm` removes the resource from Terraform's tracking only. The actual Gcore resource is not deleted. Use it to stop managing a resource with Terraform without destroying it.
</Warning>
