GitHub Security Advisory: GHSA-7r9j-r86q-7g45
Package: @budibase/backend-core (NPM)
Severity: CRITICAL (CVSS 9.6)
CWE: CWE-918: Server-Side Request Forgery (SSRF), CWE-1188: Initialization of a Resource with an Insecure Default
Vulnerable versions: < 3.33.4
Patched in: 3.33.4

Summary: Budibase: Server-Side Request Forgery via REST Connector with Empty Default Blacklist

Details:
## 1. Summary

| Field | Value |
|-------|-------|
| **Title** | SSRF via REST Connector with Empty Default Blacklist Leading to Full Internal Data Exfiltration |
| **Product** | Budibase |
| **Version** | 3.30.6 (latest stable as of 2026-02-25) |
| **Component** | REST Datasource Integration + Backend-Core Blacklist Module |
| **Severity** | Critical |
| **Attack Vector** | Network |
| **Privileges Required** | Low (Builder role, or QUERY WRITE for execution of pre-existing queries) |
| **User Interaction** | None |
| **Affected Deployments** | All self-hosted instances without explicit `BLACKLIST_IPS` configuration (believed to be the vast majority) |

---

## 2. Description

A critical Server-Side Request Forgery (SSRF) vulnerability exists in Budibase's REST datasource connector. The platform's SSRF protection mechanism (IP blacklist) is rendered completely ineffective because the `BLACKLIST_IPS` environment variable is **not set by default** in any of the official deployment configurations. When this variable is empty, the blacklist function unconditionally returns `false`, allowing all requests through without restriction.

This allows any user with `Builder` privileges (or `QUERY WRITE` permission on an existing query) to create REST datasources pointing to arbitrary internal network services, execute queries against them, and fully exfiltrate the responses — including credentials, database contents, and internal service metadata.

The vulnerability is particularly severe because:
1. The CouchDB backend stores all user credentials (bcrypt hashes), platform configurations, and application data
2. CouchDB credentials are embedded in the environment variables visible to the application container
3. A successful exploit grants full read/write access to the entire Budibase data layer

---

## 3. Root Cause Analysis

### 3.1 Blacklist Implementation

**File**: `packages/backend-core/src/blacklist/blacklist.ts`

```typescript
// Line 23-37: Blacklist refresh reads from environment variable
export async function refreshBlacklist() {
  const blacklist = env.BLACKLIST_IPS           // ← reads BLACKLIST_IPS
  const list = blacklist?.split(",") || []       // ← empty array if unset
  let final: string[] = []
  for (let addr of list) {
    // ... resolves domains to IPs
  }
  blackListArray = final                         // ← empty array
}

// Line 39-54: Blacklist check
export async function isBlacklisted(address: string): Promise<boolean> {
  if (!blackListArray) {
    await refreshBlacklist()
  }
  if (blackListArray?.length === 0) {
    return false                                 // ← ALWAYS returns false when empty
  }
  // ... rest of check never executes
}
```

**Problem**: When `BLACKLIST_IPS` is not set (the default), `blackListArray` is initialized as an empty array, and `isBlacklisted()` unconditionally returns `false` for every URL.

### 3.2 Default Configuration Missing BLACKLIST_IPS

**File**: `hosting/.env` (official Docker Compose dep