-
Notifications
You must be signed in to change notification settings - Fork 0
Architecture
Recep Samet Yıldız edited this page Sep 1, 2026
·
1 revision
This page describes how UEBPCracker is structured internally, how a tool call flows through the system, and how the commit pipeline works.
User (natural language)
│
▼
MCP-compatible AI Agent
(VS Code Copilot / Claude / Codex / any MCP client)
│
│ JSON-RPC over HTTP (localhost:8000/mcp)
▼
Unreal MCP ─────────────────────────────────────────────────┐
(ModelContextProtocol plugin, bundled with UE 5.8) │
│ │
│ Toolset Registry dispatch │
▼ │
UEBPCracker Toolset │
(UEBPCrackerEditor.UEBPCrackerToolset) │
│ │
├─ 1. Schema validation (USTRUCT request types) │
├─ 2. Security policy (FUEBPSecurityPolicy L0–L3) │
├─ 3. Resource policy (FUEBPResourcePolicy ceilings) │
├─ 4. Mutation lease (FUEBPMutationLease — serial) │
├─ 5. Asset path resolver (FUEBPPathPolicy) │
├─ 6. Preflight / dry-run │
├─ 7. FScopedTransaction (UE Undo system) │
├─ 8. Mutation (service layer) │
├─ 9. Postcondition (structural assertion) │
└─ 10. Commit pipeline ───────────────────────────────────┘
│
├─ Engine compiler (FKismetEditorUtilities::CompileBlueprint)
├─ Data validation (UEditorValidatorSubsystem)
└─ Save (UEditorAssetSubsystem::SaveLoadedAsset)
│
▼
Structured JSON result → AI Agent
Source/
├── UEBPCrackerEditor/ # Core plugin (editor-only)
│ ├── Public/
│ │ ├── UEBPCrackerTypes.h # Error code taxonomy (UEBP.*)
│ │ ├── UEBPCrackerSettings.h # UDeveloperSettings (INI-backed)
│ │ ├── UEBPToolset.h # Toolset UCLASS + tool UFUNCTIONs
│ │ ├── Contracts/ # Request/Result USTRUCTs
│ │ │ ├── UEBPCommitResult.h
│ │ │ └── ...
│ │ ├── Assets/ # Asset path types
│ │ │ └── UEBPAssetPath.h
│ │ ├── Snapshot/ # Fingerprint types
│ │ │ └── UEBPSnapshotTypes.h
│ │ ├── Spec/ # Spec execution plan types
│ │ │ └── UEBPExecutionPlan.h
│ │ ├── Ownership/ # Patch ownership state
│ │ │ └── UEBPOwnershipState.h
│ │ └── Policies/ # Security & resource types
│ │ ├── UEBPSecurityPolicy.h
│ │ ├── UEBPResourcePolicy.h
│ │ └── UEBPFailpoint.h
│ └── Private/
│ ├── Inspector/ # Read-only Blueprint inspection
│ ├── Mutator/ # Blueprint write operations
│ ├── Graph/ # Graph/node/pin services
│ ├── Spec/ # .uebp.json parser/validator/planner/executor
│ ├── Snapshot/ # Fingerprint engine (Blake3)
│ ├── Ownership/ # Patch service, manifest
│ ├── Transaction/ # FScopedTransaction wrapper
│ ├── Recovery/ # Backup/restore service
│ ├── Completion/ # check_completion DoD gate
│ ├── Policies/ # Security/resource enforcement
│ ├── Assets/ # Asset save/validate pipeline
│ └── Versioning/ # Version info, migration
└── UEBPCrackerEditorTests/ # Automation test module
└── Private/
├── Unit/
├── Editor/
├── Persistence/
└── Recovery/
UEBPCracker implements a four-level authorization model:
| Level | Name | Examples | Default |
|---|---|---|---|
| L0 | Read | inspect, snapshot, capabilities, health_check | Always allowed |
| L1 | Create | create_blueprint, add_variable, add_node | Requires bEnableWriteOperations=True
|
| L2 | Patch | plan_blueprint_patch, apply_blueprint_patch | Requires sealed plan hash |
| L3 | Destructive | restore_operation_backup, discard_operation_backup | Requires bEnableDestructiveOperations=True
|
Every write operation that touches a Blueprint asset follows this exact sequence:
1. Schema validation
│ Request USTRUCT field/type/range checks
▼
2. Security policy (FUEBPSecurityPolicy)
│ L0–L3 authorization, path containment, reflection allow-list
▼
3. Resource policy (FUEBPResourcePolicy)
│ Payload size, element count, operation deadline
▼
4. Mutation lease (FUEBPMutationLease::TryAcquire)
│ Serializes concurrent writes; returns OPERATION_BUSY if locked
▼
5. Asset path resolution (FUEBPPathPolicy)
│ Canonical path, existence check, conflict policy
▼
6. Preflight / dry-run
│ Type resolution, pin compatibility, plan generation
▼
7. FScopedTransaction open
│ "UEBPCracker: <operation name>" context
▼
8. Mutation (service layer)
│ Inspector / Mutator / Graph / Node / Pin services
▼
9. Postcondition assertion
│ Structural checks (variable count, node GUID, connection topology)
│ On failure: rollback via Undo loop (≤16 steps) + fingerprint verify
▼
10. Engine compiler
│ FKismetEditorUtilities::CompileBlueprint + FCompilerResultsLog
│ On failure: asset NOT saved; errors returned to AI
▼
11. Data validation
│ UEditorValidatorSubsystem::ValidateAssetsWithSettings
▼
12. Save
│ UEditorAssetSubsystem::SaveLoadedAsset(BP, bOnlyIfIsDirty=true)
▼
13. Structured JSON result
│ success, requestId, operation, assetPath, stage,
│ compileStatus, errors, warnings, saved, transactionId,
│ fingerprint (semantic + layout + full)
If compile fails, the asset is never saved (ADR-006: validate before commit).
| ADR | Decision |
|---|---|
| ADR-001 | Target UE 5.8 — has bundled Unreal MCP and expanded Blueprint API |
| ADR-002 | C++ editor-only plugin — full Blueprint API access, no packaged-game overhead |
| ADR-003 | Two operation modes — direct tool calls (interactive) + .uebp.json spec (reproducible) |
| ADR-004 | No direct .uasset binary production — JSON describes operations, Unreal executes them |
| ADR-005 | Serial mutation — game thread, no concurrent Blueprint writes |
| ADR-006 | Validate before commit — compile failure = no save |
| ADR-007 | Structured error results — typed error codes, never free text |
| ADR-008 | Secure defaults — loopback-only, write gate off, no arbitrary shell/console access |
| ADR-009 | Actor Blueprint first — specialized graph types (AnimBP, UMG, Niagara) require separate adapters |
AI: call inspect_blueprint { "blueprint_path": "/Game/AI/BP_HealthActor" }
│
▼ Schema validation (path string, options)
▼ L0 authorization (always allowed)
▼ Resource policy (result size cap: 8 MiB)
▼ Asset path resolver → UBlueprint* loaded from Asset Registry
▼ FUEBPBlueprintInspector::Inspect()
├─ Variables: FBPVariableDescription[] → typed JSON
├─ Components: USCS_Node tree walk → hierarchy JSON
├─ Graphs: UEdGraph[] → FunctionGraphs + EventGraph + ConstructionScript
│ └─ Nodes: UEdGraphNode[] → kind, position, pins, connections
└─ Fingerprint: semantic + layout + full (Blake3)
▼ Structured JSON result (no mutation, no transaction, no compile)
AI: call apply_blueprint_spec { "file": "BP_HealthActor.uebp.json" }
│
▼ Path policy (relative path, .uebp.json extension, size ≤ 1 MiB)
▼ UTF-8 read + RapidJSON parse (trim trailing whitespace first)
▼ Schema validation (strict additionalProperties=false)
▼ Semantic validation (class exists, variable types resolvable, ≥1 graph)
▼ Deterministic planner → FUEBPExecutionPlan (immutable command list)
▼ L1 authorization (bEnableWriteOperations required)
▼ Target asset must NOT exist (create-only; SPEC_TARGET_ALREADY_EXISTS if so)
▼ FScopedTransaction open ("UEBPCracker: ApplySpec")
▼ Executor runs commands in plan order:
├─ CreateBlueprint
├─ RemoveDefaultEventNodes (clean slate)
├─ AddVariable (×N)
├─ AddComponent (×N)
├─ UseExistingGraph / AddFunctionGraph (×N)
├─ AddNode (×N)
├─ SetPinDefault (×N)
└─ ConnectPins (×N)
▼ Postcondition assertions
▼ Commit pipeline (compile → validate → save)
▼ Structured JSON result with plan summary + fingerprints
All errors follow the pattern UEBP.<CATEGORY>_<DETAIL>.
| Category | Examples |
|---|---|
PATH_* |
PATH_OUTSIDE_ALLOWED_ROOT, PATH_READ_ONLY_ROOT, PATH_TRAVERSAL_DETECTED
|
SECURITY_* |
SECURITY_POLICY_DENIED, OPERATION_NOT_ALLOWED, DESTRUCTIVE_OPERATIONS_DISABLED
|
PLAN_* |
PLAN_HASH_REQUIRED, PLAN_HASH_MISMATCH
|
SPEC_* |
SPEC_TARGET_ALREADY_EXISTS, SPEC_MIGRATION_REQUIRED, SPEC_MIGRATION_LOSSY
|
ASSET_* |
ASSET_SAVE_FAILED, ASSET_NOT_FOUND, ASSET_ALREADY_EXISTS
|
SNAPSHOT_* |
SNAPSHOT_LIMIT_EXCEEDED, SNAPSHOT_NOT_FOUND
|
OPERATION_* |
OPERATION_BUSY, OPERATION_DEADLINE_EXCEEDED, OPERATION_CANCELLED
|
DOMAIN_* |
DOMAIN_NOT_SUPPORTED, DOMAIN_OPERATION_NOT_ALLOWED
|
Full list in Public/UEBPCrackerTypes.h.
- Tool Reference — every tool's parameters and examples
- Security Model — policy configuration in detail
- Transaction and Recovery — undo loop, backup mechanics