---
title: "VPCs"
description: "Create private networks for Freestyle VMs and attach VM network interfaces to them."
url: "/docs/vms/network/vpcs"
---

VPCs let Freestyle VMs communicate over private IP addresses. Use them when a group of VMs should share an internal network for databases, services, worker pools, or agent environments that should not depend on public VM domains.


## Terms

- A VPC is a private network for your VMs. VMs in the same VPC can talk to each other without using public domains.
- A private IP is an address that only works inside the VPC, like `192.168.10.10`.
- A CIDR is the address range for the VPC. `192.168.10.0/24` means addresses from `192.168.10.1` through `192.168.10.254` are available for VMs.
- A NIC is a network interface on a VM. Attaching a NIC to a VPC is how the VM joins the private network.


## Create A VPC

```ts
import { freestyle } from "freestyle";

const { vpcId, vpc } = await freestyle.vpc.create({
  name: "workspace-network",
  cidr: "192.168.10.0/24",
});

console.log(vpcId);
```

The VPC CIDR is the private address range available to VMs attached to the network. Pick a range that does not overlap with your home, office, or VPN network.


## Attach VMs

Attach a VM by passing a routed network interface in `vms.create`:

```ts
const { vm: apiVm } = await freestyle.vms.create({
  nics: [
    {
      default: true,
      vpc: vpcId,
      mode: "routed",
      ipv4: "192.168.10.10",
    },
  ],
});

const { vm: workerVm } = await freestyle.vms.create({
  nics: [
    {
      default: true,
      vpc: vpcId,
      mode: "routed",
      ipv4: "192.168.10.11",
    },
  ],
});
```

Use `default: true` when the VPC interface should be the VM's default route. Use `mode: "routed"` for VPC networking.


## Test Private Connectivity

VMs in the same VPC can reach each other by private IP:

```ts
const result = await apiVm.exec("ping -c 3 192.168.10.11");
console.log(result.stdout);
```

Run services on `0.0.0.0` inside the destination VM when other VMs should connect to them:

```ts
await workerVm.exec(
  "nohup python3 -m http.server 8080 --bind 0.0.0.0 >/tmp/http.log 2>&1 &",
);
```

Then connect from another VM over the VPC address:

```ts
const response = await apiVm.exec("curl http://192.168.10.11:8080");
console.log(response.stdout);
```


## Connect From Your Computer

Use [VPNs](https://www.freestyle.sh/docs/vms/network/vpns) to create an ephemeral WireGuard connection from your computer into a VPC.


## Current Limits

- VPC VM interfaces use `mode: "routed"`.
- A VM can attach one routed VPC interface.
- Choose a VPC CIDR that does not overlap with networks your VM or VPN client already uses.
