Studio 2

The Model Redesign

Refactoring data models so systems can evolve without hidden state corruption.

The Situation

Studio 1 gave us tiny working versions of all three systems, each built around a single operation. They held up as long as nothing changed. Once a delivery task can be reassigned, a document can link to another, and a world object can move under rules, the tiny models start to strain: the same thing goes by several names, and nothing stops a task from being completed before it is assigned. The weaknesses fall into four groups:

  • entity identity is unclear ("task", "route" and "request" used interchangeably)
  • relationships are implicit (IDs inside free-text fields)
  • transition rules are scattered (status changes happen from many places)
  • invalid states are easy to create and hard to detect

Part II gave us the tools to fix this:

  • model entities explicitly
  • define relationships with constraints
  • design data around real operations
  • model change with legal transitions and invariants

In Studio 2, we redesign all three systems using those principles.

Engineering Brief

Redesign the core data models for all three systems (delivery, knowledge, virtual world).

Required outcomes:

  • explicit entities with stable identity
  • explicit relationships with clear cardinality and constraints
  • transition operations with contracts (require and ensure)
  • invariants that make invalid states hard to represent
  • migrated behavior examples from Studio 1

Implementation guidance:

  • aim for correctness and clarity before performance
  • keep model boundaries obvious
  • make failure behavior explicit (not silent)

Implementation In Nex

Use Nex to encode model assumptions directly in code.

Suggested files:

  • delivery_model_v2.nex
  • knowledge_model_v2.nex
  • world_model_v2.nex
  • studio_2_main.nex

Delivery Model V2

Focus: identity, legal transitions, and the assignment relationship.

class Delivery_Task
feature
  task_id: String
  origin: String
  destination: String
  status: String
  assigned_robot_id: String

  assign(robot_id: String)
  require
    robot_present: robot_id /= ""
    can_assign: status = "PENDING" 
                or status = "FAILED"
  do
    assigned_robot_id := robot_id
    status := "IN_TRANSIT"
  ensure
    assigned: assigned_robot_id = robot_id 
              and status = "IN_TRANSIT"
  end

  complete()
  require
    in_transit: status = "IN_TRANSIT"
  do
    status := "DELIVERED"
  ensure
    delivered: status = "DELIVERED"
  end

  fail(reason: String)
  require
    reason_present: reason /= ""
    not_delivered: status /= "DELIVERED"
  do
    status := "FAILED"
  ensure
    failed: status = "FAILED"
  end
create
  pending(task_id: String, origin: String, 
          destination: String) do
    this.task_id := task_id
    this.origin := origin
    this.destination := destination
    this.status := "PENDING"
  end
invariant
  id_present: task_id /= ""
  endpoints_present: origin /= "" 
                     and destination /= ""
  valid_status:
    status = "PENDING" or status = "IN_TRANSIT" 
             or status = "DELIVERED" 
             or status = "FAILED"
  transit_has_assignment:
    status /= "IN_TRANSIT" 
    or assigned_robot_id /= ""
end

Knowledge Model V2

Focus: relationship as first-class entity (Doc_Link) rather than ad hoc references.

class Document
feature
  doc_id: String
  title: String
  body: String
create
  make(doc_id: String, title: String) do
    this.doc_id := doc_id
    this.title := title
  end
invariant
  id_present: doc_id /= ""
  title_present: title /= ""
end

class Doc_Link
feature
  from_doc_id: String
  to_doc_id: String
  link_type: String

  is_valid(): Boolean do
    result :=
      from_doc_id /= "" and
      to_doc_id /= "" and
      from_doc_id /= to_doc_id and
      (link_type = "references" 
       or link_type = "related" 
       or link_type = "contradicts")
  end
create
  make(f: String, t: String, lt: String) do
    from_doc_id := f
    to_doc_id := t
    link_type := lt
  end
invariant
  endpoints_present: from_doc_id /= "" 
                     and to_doc_id /= ""
  no_self_link: from_doc_id /= to_doc_id
end

Virtual World Model V2

Focus: deterministic update transition with explicit bounds.

class World_Object
feature
  object_id: String
  x: Integer
  vx: Integer

  step(max_x: Integer)
  require
    valid_bound: max_x >= 0
  do
    let next: Integer := x + vx
    if next < 0 then
      x := 0
    elseif next > max_x then
      x := max_x
    else
      x := next
    end
  ensure
    bounded_after_step: x >= 0 and x <= max_x
  end
create
  make(id: String, x: Integer, vx: Integer) do
    object_id := id
    this.x := x
    this.vx := vx
  end
invariant
  id_present: object_id /= ""
end

Studio Driver

Use one driver to validate nominal and edge behavior.

class App
feature
  run() do
    -- Delivery
    let t: Delivery_Task := 
      create Delivery_Task.pending("T001", "A", "C")
    t.assign("R7")
    print(t.status)              -- IN_TRANSIT
    t.complete
    print(t.status)              -- DELIVERED

    -- Knowledge
    let l: Doc_Link := 
      create Doc_Link.make("D1", "D2", "references")
    print(l.is_valid)            -- true

    -- World
    let w: World_Object := 
      create World_Object.make("0-1", 9, 4)
    w.step(10)
    print(w.x)                   -- 10 (clamped)
  end
end

Studio Challenges

Level 1 — Core Implementation

  • Redesign one system model (delivery, knowledge, or world).
  • Encode at least two invariants and two transition operations.
  • Run one nominal and two edge cases.

Level 2 — Cross-System Model Consistency

  • Redesign all three systems.
  • Use a common modeling vocabulary in notes:
    • entity
    • relationship
    • invariant
    • transition
  • Show one bug that the new model prevents, with before-and-after runs.

Level 3 — Exploration

Pick one experiment:

  • State-centric versus event-centric transition handling for delivery reassignment.
  • Direct references versus link entities in the knowledge model.
  • Single-step deterministic update versus queued events in virtual world updates.

Evaluate:

  • complexity impact
  • testability impact
  • failure-mode clarity

Postmortem

Discuss:

  • Which entity boundary decision removed the most confusion?
  • Which relationship constraint prevented a real invalid state?
  • Which transition rule was hardest to make explicit?
  • Which tradeoff did we accept deliberately, and why?

Use concrete evidence from our runs, not just opinions.

Deliverables

  • redesigned Nex models for delivery, knowledge, and world systems
  • short modeling notes per system:
    • entities
    • relationships
    • invariants
    • transitions
  • nominal and edge test output logs
  • one before-and-after comparison showing reduced accidental complexity

Exit Criteria

We are ready for Part III if:

  • we can explain identity versus state for each core entity
  • invalid states are blocked by model rules (not just comments)
  • transition legality is encoded in operations and their contracts
  • relationship constraints are explicit and testable