Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions scripts/deployments/openclaw/update-openclaw.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
#!/bin/bash
set -e

cd /opt/openclaw
git pull origin fork
pnpm install
pnpm build
pnpm ui:build
sudo systemctl restart openclaw-gateway
echo "OpenClaw updated and restarted."
13 changes: 13 additions & 0 deletions terraform/deployments/lab/env/lab/terraform.tfvars
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,19 @@ pve = {
}
vm_disk_datastore_id = "ssd_1641G_thin"
vm_cloudinit_datastore_id = "ssd_1641G_thin"
openclaw = {
name_prefix = "openclaw"
description = "OpenClaw Gateway - Managed by Terraform"
tags = ["openclaw"]
bios = "ovmf"
cpu_cores = 4
memory_mb = 16384
os_disk_size = 50
disk_interface = "virtio0"
network_bridge = "vmbr0"
vlan_id = 200
admin_username = "krkn"
}
pwnbox = {
name_prefix = "pwnbox"
description = "CTF Pwnbox - Managed by Terraform"
Expand Down
35 changes: 35 additions & 0 deletions terraform/deployments/lab/main.tf
Original file line number Diff line number Diff line change
@@ -1,3 +1,38 @@
resource "proxmox_virtual_environment_file" "openclaw_cloudinit" {
provider = pve
content_type = "snippets"
datastore_id = "snippets"
node_name = var.pve.host

source_raw {
data = templatefile("${path.module}/templates/setup-openclaw.yaml.tftpl", {
openclaw_hostname = var.openclaw.name_prefix
admin_username = var.openclaw.admin_username
})
file_name = "setup-${var.openclaw.name_prefix}.yaml"
}
}

module "openclaw" {
source = "git::https://github.com/krakenhavoc/HomeLab.git//terraform/modules/compute/pm-cloudinit-vm?ref=v0.2.0"

vm_name = var.openclaw.name_prefix
vm_node_name = var.pve.host
vm_description = var.openclaw.description
vm_tags = var.openclaw.tags
vm_bios = var.openclaw.bios
clone_vm_id = data.proxmox_virtual_environment_vms.noble_template.vms[0].vm_id
vm_cpu_cores = var.openclaw.cpu_cores
vm_memory_mb = var.openclaw.memory_mb
vm_disk_datastore_id = var.vm_disk_datastore_id
vm_disk_interface = var.openclaw.disk_interface
vm_disk_size = var.openclaw.os_disk_size
vm_cloudinit_datastore_id = var.vm_cloudinit_datastore_id
vm_cloudinit_user_data_file_id = proxmox_virtual_environment_file.openclaw_cloudinit.id
vm_network_bridge = var.openclaw.network_bridge
vm_vlan_id = var.openclaw.vlan_id
}

resource "proxmox_virtual_environment_file" "pwnbox_cloudinit" {
provider = pve
content_type = "snippets"
Expand Down
125 changes: 125 additions & 0 deletions terraform/deployments/lab/templates/setup-openclaw.yaml.tftpl
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
#cloud-config
preserve_hostname: false
hostname: ${openclaw_hostname}
ssh_pwauth: false
package_update: true
package_upgrade: true
packages:
- qemu-guest-agent
- curl
- git
- openssl
- procps

users:
- name: ${admin_username}
gecos: "OpenClaw Admin"
groups: sudo
shell: /bin/bash
sudo: "ALL=(ALL) NOPASSWD:ALL"
ssh_authorized_keys:
- ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAILZzMMk21CqtHkvN3b0euByxFNR042KCcot981yCwUlu

runcmd:
- curl -fsSL https://nodejs.org/dist/v22.12.0/node-v22.12.0-linux-x64.tar.xz -o /tmp/node.tar.xz
- tar -xJf /tmp/node.tar.xz -C /usr/local --strip-components=1
- rm /tmp/node.tar.xz
- npm install -g pnpm@10.23.0
- npm install -g @anthropic-ai/claude-code
- git clone -b fork https://github.com/krakenhavoc/openclaw.git /opt/openclaw
- cd /opt/openclaw && pnpm install
- cd /opt/openclaw && pnpm build
- cd /opt/openclaw && pnpm ui:build
- chown -R ${admin_username}:${admin_username} /opt/openclaw
- printf '#!/bin/bash\nexec /usr/local/bin/node /opt/openclaw/openclaw.mjs "$@"\n' > /usr/local/bin/openclaw
- chmod +x /usr/local/bin/openclaw
- mkdir -p /home/${admin_username}/.openclaw
- |
cat > /home/${admin_username}/.openclaw/openclaw.json <<'JSONEOF'
{
"meta": {
"lastTouchedVersion": "2026.3.3",
"lastTouchedAt": "2026-03-09T00:00:00.000Z"
},
"models": {
"providers": {
"azure-foundry": {
"baseUrl": "https://eus2-foundry.services.ai.azure.com",
"apiKey": "$${AZURE_FOUNDRY_API_KEY}",
"api": "openai-completions",
"models": []
},
"azure-gpt": {
"baseUrl": "https://eus2-foundry.cognitiveservices.azure.com/openai",
"apiKey": "$${AZURE_FOUNDRY_API_KEY}",
"api": "openai-responses",
"models": []
}
}
},
"agents": {
"defaults": {
"model": {
"primary": "azure-gpt/gpt-5.3-chat"
},
"workspace": "/home/${admin_username}/.openclaw/workspace"
}
},
"tools": {
"exec": {
"host": "gateway",
"security": "full",
"ask": "off"
}
},
"commands": {
"native": "auto",
"nativeSkills": "auto",
"restart": true,
"ownerDisplay": "raw"
},
"gateway": {
"mode": "local",
"controlUi": {
"dangerouslyAllowHostHeaderOriginFallback": true,
"allowInsecureAuth": true
}
}
}
JSONEOF
- echo "OPENCLAW_STATE_DIR=/home/${admin_username}/.openclaw" > /home/${admin_username}/.openclaw/.env
- chown -R ${admin_username}:${admin_username} /home/${admin_username}/.openclaw
- |
cat > /etc/systemd/system/openclaw-gateway.service <<EOF
[Unit]
Description=OpenClaw Gateway
After=network-online.target
Wants=network-online.target

[Service]
Type=simple
User=${admin_username}
WorkingDirectory=/opt/openclaw
Environment=HOME=/home/${admin_username}
EnvironmentFile=-/home/${admin_username}/.openclaw/.env
ExecStart=/usr/local/bin/node /opt/openclaw/openclaw.mjs gateway --bind lan --port 18789
Restart=always
RestartSec=5
TimeoutStopSec=30
TimeoutStartSec=30
SuccessExitStatus=0 143
KillMode=control-group

[Install]
WantedBy=multi-user.target
EOF
- systemctl daemon-reload
- systemctl enable openclaw-gateway

power_state:
mode: reboot
message: "Rebooting after cloud-init final stage"
timeout: 30
condition: true

final_message: "${openclaw_hostname} is up. Add API keys to /home/${admin_username}/.openclaw/.env and run: systemctl start openclaw-gateway"
18 changes: 18 additions & 0 deletions terraform/deployments/lab/variables.tf
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,24 @@ variable "vm_cloudinit_datastore_id" {
default = "ssd_1641G_thin"
}

variable "openclaw" {
description = "Object containing the OpenClaw configuration"
type = object({
name_prefix = optional(string, "openclaw")
description = optional(string, "OpenClaw Gateway - Managed by Terraform")
tags = optional(list(string), ["openclaw"])
bios = optional(string, "ovmf")
cpu_cores = optional(number, 4)
memory_mb = optional(number, 16384)
os_disk_size = optional(number, 50)
disk_interface = optional(string, "virtio0")
network_bridge = optional(string, "vmbr0")
vlan_id = optional(number, 200)
admin_username = optional(string, "krkn")
})
default = {}
}

variable "pwnbox" {
description = "Object containing the Pwnbox configuration"
type = object({
Expand Down
Loading