# Railway cloud platform breach exposes customer secrets, leads to $740,000 in fraudulent AI charges (Wiz 'Black October' campaign)

> Between October 18 and 21, 2026, an attacker chained a zero-day filesystem isolation escape in Railway's multi-tenant build infrastructure with an overprivileged build credential, a misconfigured OIDC binding and an on-disk KMS decryption credential to decrypt customer environment variables. Stolen AI provider credentials were abused for roughly $740,000 in unauthorized usage; at most 1.85% of workspaces (~100,000) were potentially affected.

- **Published:** 2026-11-10T22:31:57Z
- **Last reviewed:** 2026-11-10T22:31:57Z
- **Canonical:** https://intel.threadlinqs.com/threat/TL-2026-5687
- **Card image:** https://intel.threadlinqs.com/og/threat/TL-2026-5687.png
- **ID:** TL-2026-5687
- **Severity:** HIGH
- **Category:** DATA_BREACH
- **Status:** ACTIVE
- **Detections:** 9 (1 shown free below) · **IOCs:** 20 (3 shown free below)

## Description

Railway's November 10, 2026 incident report describes a roughly 26-hour intrusion that Railway characterizes as a contest of 'agent speed'. The attacker began creating dummy accounts on October 18 (earlier attempts were blocked by automated systems) and started probing build infrastructure at 06:50 UTC on October 20. At 07:28 UTC a previously unknown vulnerability partially escaped filesystem isolation on a shared build VM, letting the attacker read a build credential intended only for registry pushes.

That build credential was accepted as a trusted client by Railway's internal self-hosted Temporal cluster. Using it, the attacker read the stored histories of 353 builds (including sealed variables) between 13:50 and 15:30 UTC and used build-cache APIs to retrieve a copy of Railway's internal monorepo. Railway's on-call engineer was paged at 13:58 UTC by an alert on anomalous registry API calls; builds were halted at 17:03 and the build credential was revoked and replaced at 17:28 UTC. The attacker reportedly analyzed the source code for further attack paths and probed long-dormant endpoints, using parallel probing with rapid retries and agent fan-outs.

On October 21 at 03:26 UTC the attacker obtained a short-lived cloud credential through a misconfigured OIDC binding, which yielded internal provisioning credentials. Between 04:07 and 05:21 UTC they queried the envelope-encrypted variables database over an internal VPC, filtering by regex on variable names (AI provider keys prioritized, with some queries targeting cloud, database and payment credentials) and favoring environments with many variables. A long-lived KMS-decryption credential found on disk on an orchestration machine (which also held a CD-pushed SSH key and VPC access) was used in windows 04:42-05:14 and 06:36-07:15 UTC to decrypt per-environment keys. Overbroad decryption meant any compromised credential could decrypt many environments' variables. Railway disabled all active cloud credentials and the key-decryption service at 07:14 UTC and fully evicted the attacker at 09:24-09:25 UTC; all user sessions and tokens were invalidated at 20:19 UTC.

Impact: environment variables potentially decrypted for at most 1.85% of workspaces (~100,000; an upper bound at environment level, not a confirmed count of stolen secrets); linked-account tokens (BYOK AI agent keys, GitHub OAuth tokens) for 1,852 users were exposed and reset; about $740,000 in unauthorized AI usage was estimated. Railway found no evidence that customer Git repositories were downloaded or customer databases accessed. Railway believes the attackers sought AI credentials for resale or model distillation. Railway links the incident to the campaign Wiz calls 'Black October', a wave of credential-theft incidents at AI developer platforms (also Northflank, OpenCode, Warp, Lightning AI and others); Wiz states it has not established that every incident is one coordinated campaign and that there is no common vulnerability. No threat actor is named and Railway has not published IOCs (they are being shared privately with law enforcement; an FBI IC3 complaint was filed and an external forensics firm is still investigating). No CVE has been assigned.

## MITRE ATT&CK

- T1585.003 Cloud Accounts
- T1588.007 Artificial Intelligence
- T1595 Active Scanning
- T1611 Escape to Host
- T1552.001 Credentials In Files
- T1078.004 Cloud Accounts
- T1213.003 Code Repositories
- T1119 Automated Collection
- T1021.004 SSH
- T1580 Cloud Infrastructure Discovery
- T1496.004 Cloud Service Hijacking

## Free detection (Splunk SPL, Microsoft KQL, Sigma)

**Black October - Stolen AI Key Abuse Against AWS Bedrock (Railway TL-2026-5687)** (`TL-2026-5687-SPL-001`)

Behaviour-first CloudTrail search for post-theft use of AI provider credentials stolen in the Railway breach (Wiz Black October): one access key that both invokes Bedrock models and enumerates models or quotas (boto3-style ListFoundationModels, GetServiceQuota, PutAccountDataRetention) from a single address, or any Bedrock/quota call from the four Wiz-listed suspected key-validation IPs. Wiz observed a validation InvokeModel call within minutes of credential access, then low-volume daily calls. The Railway incident produced roughly 740,000 USD of unauthorized AI usage. IP IOCs are low confidence, so the behavioural branch is the primary signal.

- **Languages:** Splunk SPL, Microsoft KQL, Sigma
- **ATT&CK:** T1496.004, T1580, T1078.004, T1588.007
- **Data sources:** aws_cloudtrail (index=aws_cloudtrail, sourcetype=aws:cloudtrail), bedrock.amazonaws.com, servicequotas.amazonaws.com
- **Severity:** high
- **Confidence:** medium

### Splunk SPL

```spl
index=aws_cloudtrail sourcetype="aws:cloudtrail" earliest=-24h eventSource IN ("bedrock.amazonaws.com","servicequotas.amazonaws.com","ec2.amazonaws.com") eventName IN ("InvokeModel","InvokeModelWithResponseStream","Converse","ConverseStream","ListFoundationModels","GetFoundationModelAvailability","PutAccountDataRetention","ListServiceQuotas","GetServiceQuota","DescribeInstanceTypeOfferings")
| rename userIdentity.accessKeyId as access_key_id, userIdentity.arn as principal_arn
| eval ioc_ip=if(in(sourceIPAddress,"23.106.46.239","38.246.114.118","104.243.32.50","31.57.201.201"),1,0)
| eval boto_agent=if(match(userAgent,"(?i)boto3|botocore"),1,0)
| eval is_invoke=if(like(eventName,"Invoke%") OR like(eventName,"Converse%"),1,0)
| eval is_enum=if(is_invoke=0,1,0)
| stats count as calls sum(is_invoke) as invoke_calls sum(is_enum) as enum_calls max(ioc_ip) as ioc_ip max(boto_agent) as boto_agent values(eventName) as api_calls values(userAgent) as user_agents min(_time) as first_seen max(_time) as last_seen by access_key_id principal_arn sourceIPAddress
| where ioc_ip=1 OR (invoke_calls>=1 AND enum_calls>=2)
| convert ctime(first_seen) ctime(last_seen)
```

### Microsoft KQL

```kql
let ioc_ips = dynamic(["23.106.46.239","38.246.114.118","104.243.32.50","31.57.201.201"]);
let enum_events = dynamic(["ListFoundationModels","GetFoundationModelAvailability","PutAccountDataRetention","ListServiceQuotas","GetServiceQuota","DescribeInstanceTypeOfferings"]);
let invoke_events = dynamic(["InvokeModel","InvokeModelWithResponseStream","Converse","ConverseStream"]);
AWSCloudTrail
| where TimeGenerated > ago(24h)
| where EventSource in ("bedrock.amazonaws.com","servicequotas.amazonaws.com","ec2.amazonaws.com")
| where EventName in (enum_events) or EventName in (invoke_events)
| extend IsIocIp = SourceIpAddress in (ioc_ips), IsBoto = UserAgent has_any ("Boto3","Botocore"), IsEnum = EventName in (enum_events), IsInvoke = EventName in (invoke_events)
| summarize Calls = count(), EnumCalls = countif(IsEnum), InvokeCalls = countif(IsInvoke), IocIp = max(toint(IsIocIp)), BotoAgent = max(toint(IsBoto)), ApiNames = make_set(EventName, 20), UserAgents = make_set(UserAgent, 5), FirstSeen = min(TimeGenerated), LastSeen = max(TimeGenerated) by UserIdentityAccessKeyId, UserIdentityArn, SourceIpAddress
| where IocIp == 1 or (InvokeCalls >= 1 and EnumCalls >= 2)
| project FirstSeen, LastSeen, UserIdentityAccessKeyId, UserIdentityArn, SourceIpAddress, Calls, InvokeCalls, EnumCalls, IocIp, BotoAgent, ApiNames, UserAgents
```

### Sigma

```yaml
title: Black October Suspected Stolen-Key IP Calling AWS Bedrock or Quota APIs
id: 5c1d7a30-8e42-4b19-9f6a-2d3b71e0a501
status: experimental
description: Detects AWS Bedrock, Service Quotas or EC2 offering API calls originating from IP addresses Wiz lists as suspected stolen AI-key validation infrastructure in the Black October campaign (Railway incident TL-2026-5687). Low-confidence community IOCs, treat as a hunting lead.
references:
    - https://blog.railway.com/p/incident-report-october-security-incident
    - https://www.wiz.io/blog/black-october-for-ai-developer-platforms
author: Threadlinqs Team
date: 2026/11/10
tags:
    - attack.impact
    - attack.t1496.004
    - attack.discovery
    - attack.t1580
    - attack.privilege-escalation
    - attack.t1078.004
logsource:
    product: aws
    service: cloudtrail
detection:
    selection_ip:
        sourceIPAddress:
            - '23.106.46.239'
            - '38.246.114.118'
            - '104.243.32.50'
            - '31.57.201.201'
    selection_api:
        eventSource:
            - 'bedrock.amazonaws.com'
            - 'servicequotas.amazonaws.com'
            - 'ec2.amazonaws.com'
    condition: selection_ip and selection_api
falsepositives:
    - IP reassigned to a legitimate tenant after the campaign window
    - Shared hosting address ranges reused by benign traffic
level: high
```

**Known false positives:**

- Platform or FinOps engineers legitimately running boto3 scripts that list Bedrock models, check quotas and invoke a model
- Shared hosting IPs reused by unrelated benign tenants after the campaign window

**Tuning notes:** Allow-list known automation principals and corporate egress ranges; raise the enum_calls threshold for platform teams; add keys that were ever stored as Railway variables to a watchlist; the IP list is low confidence so keep the behavioural branch enabled when IPs age out. Schedule every 15 minutes over a 24h window.

### 8 more detection rules (Splunk SPL, Microsoft KQL, Sigma), unlock with TL Creds

- Black October - Build Sandbox Escape to Host Namespace (Exploitation) (locked: unlock with TL Creds)
- Black October - Credential File Hunting on Orchestration Host (locked: unlock with TL Creds)
- Black October - Connections to Suspected Stolen-Key IPs (locked: unlock with TL Creds)
- Black October - Boto3 Bedrock and Quota Enumeration (locked: unlock with TL Creds)
- Black October - Bulk Repository Copy (Source Code Theft) (locked: unlock with TL Creds)
- Black October - DNS Lookups for Resale and ARTEX Domains (locked: unlock with TL Creds)
- Black October - OIDC Role Assumption Followed by Bulk KMS Decrypt (locked: unlock with TL Creds)
- Black October - One SSH Key or Source Accepted on Many Hosts (Lateral Movement) (locked: unlock with TL Creds)

Sign up free to unlock the detection rules: https://threadlinqs.com/?modal=signup

## Sample indicators (3 of 20)

Defanged, TLP:CLEAR.

- IP address: `23.106.46[.]239`
- Domain: `llm-routing[.]com`
- IP address: `38.246.114[.]118`

Full set of 20 indicators unlocks with TL Creds: https://threadlinqs.com/tl-creds

## Sources

- [Railway breach leads to $740,000 in fraudulent AI charges](https://www.bleepingcomputer.com/news/apple/railway-breach-leads-to-740-000-in-fraudulent-ai-charges/)
- [Railway Incident Report: October Security Incident](https://blog.railway.com/p/incident-report-october-security-incident)
- [Wiz: "Black October" for AI Developer Platforms](https://www.wiz.io/blog/black-october-for-ai-developer-platforms)
- [Railway warns devs to rotate secrets after potential breach](https://www.bleepingcomputer.com/news/security/railway-warns-devs-to-rotate-secrets-after-potential-breach/)
- [Railway Security Disclosure (October 21st)](https://blog.railway.com/p/security-disclosure-wednesday-october-21st)
- [Railway Preliminary Report: October Security Incident](https://blog.railway.com/p/preliminary-report-october-security-incident)
- [Railway changelog: October 21 security incident](https://railway.com/changelog/2026-10-23-october-21-security-incident)
- [Northflank security breach leads to abuse of customers' AI API keys](https://bleepingcomputer.com/news/security/northflank-security-breach-leads-to-abuse-of-customers-ai-api-keys)

## Full data

The other 8 detection rules (Splunk SPL / Microsoft KQL / Sigma) unlock with TL Creds; a free account includes daily creds: https://threadlinqs.com/?modal=signup
Indicator values unlock with TL Creds, at a lower price on Red and Purple; AI agents can query rules and IOCs through the Threadlinqs MCP server (Purple): https://intel.threadlinqs.com/mcp

Canonical: https://intel.threadlinqs.com/threat/TL-2026-5687
