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
111 changes: 111 additions & 0 deletions .github/workflows/security.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
name: Security Checks

on:
push:
branches:
- main
pull_request:
branches:
- main

permissions:
contents: read
security-events: write

jobs:
shell-security:
name: Shell Security (ShellCheck)
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Install ShellCheck
run: |
sudo apt-get update
sudo apt-get install -y shellcheck

- name: Run ShellCheck on bash scripts and .envrc
run: |
set -euo pipefail
mapfile -d '' shell_files < <(find . -type f \( -name "*.sh" -o -name "*.bash" \) -not -path "./.git/*" -print0)
mapfile -d '' envrc_files < <(find . -type f -name ".envrc" -not -path "./.git/*" -print0)

if [ "${#shell_files[@]}" -gt 0 ]; then
printf 'Checking shell files:\n'
printf ' - %s\n' "${shell_files[@]}"
shellcheck -x -S error "${shell_files[@]}"
fi

if [ "${#envrc_files[@]}" -gt 0 ]; then
printf 'Checking .envrc files (bash mode):\n'
printf ' - %s\n' "${envrc_files[@]}"
shellcheck -s bash -S error "${envrc_files[@]}"
fi

if [ "${#shell_files[@]}" -eq 0 ] && [ "${#envrc_files[@]}" -eq 0 ]; then
echo "No shell files or .envrc found."
fi

envrc-policy:
name: .envrc Policy Checks
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Validate .envrc policy
run: |
set -euo pipefail
if [ ! -f .envrc ]; then
echo "No .envrc found."
exit 0
fi

# Basic parser sanity check.
bash -n .envrc

# Block common risky patterns in direnv files.
if grep -En '(^|[^[:alnum:]_])(curl|wget)[^\n]*\|[[:space:]]*(bash|sh)\b|\beval[[:space:]]+|\bsource_url\b' .envrc; then
echo "Found unsafe pattern(s) in .envrc."
exit 1
fi

echo ".envrc policy check passed."

terraform-security:
name: Terraform Security (Checkov)
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Run Checkov on Terraform
uses: bridgecrewio/checkov-action@v12
with:
directory: terraform/digitalOcean
framework: terraform
skip_check: CKV_DIO_4
quiet: true
output_format: cli,sarif
output_file_path: console,checkov.sarif

- name: Upload Checkov SARIF
if: always()
uses: github/codeql-action/upload-sarif@v4
with:
sarif_file: checkov.sarif

secrets-scan:
name: Secret Scan (Gitleaks)
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4
with:
fetch-depth: 0

- name: Run Gitleaks
uses: gitleaks/gitleaks-action@v2
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
65 changes: 0 additions & 65 deletions openclaw.json

This file was deleted.

Binary file modified terraform/.DS_Store
Binary file not shown.
4 changes: 2 additions & 2 deletions terraform/digitalOcean/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -28,14 +28,14 @@ resource "digitalocean_firewall" "openclaw" {
inbound_rule {
protocol = "tcp"
port_range = "22"
source_addresses = ["0.0.0.0/0", "::/0"]
source_addresses = var.ssh_allowed_cidrs
}

# OpenClaw gateway
inbound_rule {
protocol = "tcp"
port_range = "18789"
source_addresses = ["0.0.0.0/0", "::/0"]
source_addresses = var.gateway_allowed_cidrs
}


Expand Down
5 changes: 5 additions & 0 deletions terraform/digitalOcean/terraform.tfvars.example
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,11 @@ region = "tor1"
# Sizes: s-1vcpu-1gb ($6/mo), s-1vcpu-2gb ($12/mo), s-2vcpu-2gb ($18/mo), s-2vcpu-4gb ($24/mo)
droplet_size = "s-1vcpu-1gb"

# Restrict ingress to trusted CIDRs.
# Replace with your own public IP/CIDR ranges.
ssh_allowed_cidrs = ["203.0.113.10/32"]
gateway_allowed_cidrs = ["203.0.113.10/32"]

# Swap: 2G (min for 1GB RAM), 3G (recommended), 4G (comfortable)
swap_size = "3G"

Expand Down
12 changes: 12 additions & 0 deletions terraform/digitalOcean/variables.tf
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,18 @@ variable "droplet_size" {
default = "s-1vcpu-1gb"
}

variable "ssh_allowed_cidrs" {
description = "CIDR blocks allowed to SSH to the droplet (recommended: your current public IP as /32)."
type = list(string)
default = ["0.0.0.0/0", "::/0"]
}

variable "gateway_allowed_cidrs" {
description = "CIDR blocks allowed to access OpenClaw gateway on port 18789."
type = list(string)
default = ["0.0.0.0/0", "::/0"]
}

variable "swap_size" {
description = "Swap file size (e.g. 2G, 3G, 4G) — prevents OOM during npm install"
default = "3G"
Expand Down
Loading