feat: Adds AI skills to migrate from RunUO (#2366)

## Summary

Adds comprehensive RunUO → ModernUO migration documentation and Claude AI skills to help shard owners and script authors convert RunUO 2.7 code to ModernUO.

- **10 migration skills** (`dev-docs/claude-skills/migrate-from-runuo/`) — system-by-system conversion guides (foundation, serialization, timers, gumps, packets, property lists, commands/events, persistence, items/mobiles, systems/engines)
- **12 reference docs** (`dev-docs/runuo-migration-docs/`) — deep-reference with before/after examples, API mapping tables, edge cases, and gotchas
- **Updated existing skills** — `modernuo-timers`, `modernuo-serialization`, and `modernuo-threading` now document that `Serialize()` runs on background threads and timers are not thread-safe
- **Updated `CLAUDE.md`** — added migration skill lookup table

### Key migration patterns covered
- Manual `Serialize()`/`Deserialize()` → source-generated `[SerializableField]`
- `Packet` class hierarchy → static `SpanWriter`/`SpanReader` methods
- `Timer` subclasses → `TimerExecutionToken` fire-and-forget
- `Gump` → `StaticGump<T>`/`DynamicGump` with builders
- `EventSink.WorldSave` → `GenericPersistence`
- `ObjectPropertyList` → `IPropertyList` with string hole rules
- Universal changes: naming (`m_` → `_`), `[Constructable]` → `[Constructible]`, logging, spatial queries
This commit is contained in:
Kamron Batman 2026-03-13 00:33:45 -07:00 • committed by GitHub
parent 31b22d4773
commit 4f9bc1d9f6
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
26 changed files with 4216 additions and 7 deletions

View file

@ -116,19 +116,32 @@ using var list = PooledRefList<Mobile>.CreateMT();
## World Saves
World saves DO involve background work, but this is handled by server infrastructure:
1. **Serialization** happens on the main thread (safe access to game state)
2. **Disk I/O** may happen on background threads (no game state access)
3. Main thread blocks briefly during serialization snapshot
World saves use **parallel serialization threads**. This is critical to understand:
1. **Preserialize**: Allocates heaps and wakes serialization thread workers (background)
2. **Snapshot**: Main thread calls `Persistence.SerializeAll()` which pushes entities into `SerializationThreadWorker` queues (round-robin). Workers call `Serialize(writer)` on **their own background threads** in parallel.
3. **Write snapshot**: Disk I/O on background threads after serialization completes
```csharp
// From World.cs -- save flow:
World.Save();
→ Preserialize() on thread pool (allocate heaps)
→ Snapshot() on main thread (serialize game state)
→ WriteFiles() on thread pool (disk I/O only)
→ Preserialize() on thread pool (allocate heaps, wake serialization workers)
→ Snapshot() on main thread (queues entities to workers, workers serialize in parallel)
→ SerializationThreadWorker.Execute() calls e.Serialize(writer) on background thread
→ PauseSerializationThreads() (wait for workers to finish)
→ WriteSnapshot() on thread pool (disk I/O only)
```
### Serialize() runs on background threads
Because `SerializationThreadWorker` calls `Serialize()` on its own thread, **`Serialize()` must be pure**:
- **NO** creating/destroying Items or Mobiles
- **NO** starting/stopping timers (not thread-safe)
- **NO** sending packets or modifying NetState
- **NO** mutating shared game state
- **ONLY** read fields and write to `IGenericWriter`
See `modernuo-serialization.md` for full purity rules.
## Exceptions: Server Infrastructure
These files MAY use threading (they're server infrastructure, not game logic):