diff --git a/.travis.yml b/.travis.yml
index 4cbe7db..07cfa2b 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -20,6 +20,7 @@ script:
   - sbt test assembly doc
 
 deploy:
+  skip_cleanup: true
   provider: releases
   api_key:
     secure: EgJ7RuEBzNjcKBuQP4jtwPU1hp8LzoacGufAaimOfG4+3pTfbPFttXjMXjb/8HP4QF1vcFH3BemPyZng20qTTP1LuoNvU3Ae4ZakCFDS0F9KfajibcmJRCqoJ7LSI6olFS/zyMWNVWkEUiBcOcLIafBTz1HB6M0ucxanN6/dUS4=
diff --git a/build.sbt b/build.sbt
index 4e08ce0..f014215 100644
--- a/build.sbt
+++ b/build.sbt
@@ -15,7 +15,7 @@ val akkaVersion = "2.4.14"
 resolvers += "konstructs" at "http://dl.bintray.com/konstructs/maven"
 
 libraryDependencies ++= Seq(
-  "org.konstructs" % "konstructs-server-api" % "0.2.2",
+  "org.konstructs" % "konstructs-server-api" % "0.2.3",
   "com.typesafe.akka" %% "akka-actor" % akkaVersion,
   "commons-io" % "commons-io" % "2.5",
   "com.google.code.gson" % "gson" % "2.8.0",
diff --git a/src/main/scala/konstructs/api/api.scala b/src/main/scala/konstructs/api/api.scala
index 57b1280..9ac5134 100644
--- a/src/main/scala/konstructs/api/api.scala
+++ b/src/main/scala/konstructs/api/api.scala
@@ -9,16 +9,6 @@ import com.google.gson.JsonElement
 case object GetTextures
 case class Textures(textures: Array[Byte])
 
-case class CreateInventory(blockId: UUID, size: Int)
-case class GetInventory(blockId: UUID)
-case class GetInventoryResponse(blockId: UUID, inventory: Option[Inventory])
-case class PutStack(blockId: UUID, slot: Int, stack: Stack)
-case class RemoveStack(blockId: UUID, slot: Int, amount: StackAmount)
-case class GetStack(blockId: UUID, slot: Int)
-case class GetStackResponse(blockId: UUID, slot: Int, stack: Stack)
-case class DeleteInventory(blockId: UUID)
-case class ReceiveStack(stack: Stack)
-
 /* Manage konstructing */
 case class MatchPattern(pattern: Pattern)
 case class PatternMatched(result: Stack)
@@ -26,13 +16,6 @@ case class KonstructPattern(pattern: Pattern)
 case class PatternKonstructed(pattern: PatternTemplate, result: Stack, number: Int)
 case object PatternNotKonstructed
 
-/* Manage player */
-case class ConnectView(manager: ActorRef, view: View)
-case class UpdateView(view: View)
-case class PutViewStack(stack: Stack, to: Int)
-case class RemoveViewStack(from: Int, amount: StackAmount)
-case object CloseInventory
-
 /* Messages for binary storage */
 case class StoreBinary(id: String, ns: String, data: ByteString)
 case class LoadBinary(id: String, ns: String)
diff --git a/src/main/scala/konstructs/inventory.scala b/src/main/scala/konstructs/inventory.scala
index 7795dd0..8447a56 100644
--- a/src/main/scala/konstructs/inventory.scala
+++ b/src/main/scala/konstructs/inventory.scala
@@ -9,6 +9,7 @@ import akka.actor.{Actor, Props, ActorRef, Stash}
 
 import com.google.gson.reflect.TypeToken
 import konstructs.plugin.{PluginConstructor, Config}
+import konstructs.api.messages._
 import konstructs.api._
 
 class InventoryActor(val ns: String, val jsonStorage: ActorRef)
@@ -23,24 +24,72 @@ class InventoryActor(val ns: String, val jsonStorage: ActorRef)
   loadGson(InventoriesFile)
 
   val typeOfInventories = new TypeToken[java.util.Map[String, Inventory]]() {}.getType
-  var inventories: java.util.Map[String, Inventory] = null
+  val typeOfOtherInventories =
+    new TypeToken[java.util.Map[String, java.util.Map[String, Inventory]]]() {}.getType
+  var storageInventories: java.util.Map[String, Inventory] = null
+  var otherInventories: java.util.Map[String, java.util.Map[String, Inventory]] = null
+
+  private def inventoryExists(blockId: UUID, inventoryId: InventoryId) =
+    if (inventoryId == InventoryId.STORAGE) {
+      storageInventories.containsKey(blockId.toString)
+    } else {
+      if (otherInventories.containsKey(blockId.toString)) {
+        otherInventories.get(blockId.toString).containsKey(inventoryId.idString)
+      } else {
+        false
+      }
+    }
+
+  private def getInventory(blockId: UUID, inventoryId: InventoryId) =
+    if (inventoryId == InventoryId.STORAGE) {
+      storageInventories.get(blockId.toString)
+    } else {
+      val blockInventories = otherInventories.get(blockId.toString)
+      if (blockInventories != null) {
+        blockInventories.get(inventoryId.idString)
+      } else {
+        null
+      }
+    }
+
+  private def putInventory(blockId: UUID, inventoryId: InventoryId, inventory: Inventory): Unit = {
+    if (inventoryId == InventoryId.STORAGE) {
+      storageInventories.put(blockId.toString, inventory)
+    } else {
+      if (otherInventories.get(blockId.toString) == null) {
+        otherInventories.put(blockId.toString, new java.util.HashMap[String, Inventory]())
+      }
+      otherInventories.get(blockId.toString).put(inventoryId.idString, inventory)
+    }
+  }
+
+  private def removeInventory(blockId: UUID, inventoryId: InventoryId) =
+    if (inventoryId == InventoryId.STORAGE) {
+      storageInventories.remove(blockId.toString)
+    } else {
+      val blockInventories = otherInventories.get(blockId.toString)
+      blockInventories.remove(inventoryId.idString)
+      if (blockInventories.isEmpty) {
+        otherInventories.remove(blockId.toString)
+      }
+    }
 
-  private def put(blockId: UUID, slot: Int, stack: Stack): Stack = {
-    if (inventories.containsKey(blockId.toString)) {
-      val inventory = inventories.get(blockId.toString)
+  private def put(blockId: UUID, inventoryId: InventoryId, slot: Int, stack: Stack): Stack = {
+    if (inventoryExists(blockId, inventoryId)) {
+      val inventory = getInventory(blockId, inventoryId)
       val oldStack = inventory.getStack(slot)
 
       if (oldStack != null) {
         if (oldStack.canAcceptPartOf(stack)) {
           val r = oldStack.acceptPartOf(stack)
-          inventories.put(blockId.toString, inventory.withSlot(slot, r.getAccepting))
+          putInventory(blockId, inventoryId, inventory.withSlot(slot, r.getAccepting))
           r.getGiving
         } else {
-          inventories.put(blockId.toString, inventory.withSlot(slot, stack))
+          putInventory(blockId, inventoryId, inventory.withSlot(slot, stack))
           oldStack
         }
       } else {
-        inventories.put(blockId.toString, inventory.withSlot(slot, stack))
+        putInventory(blockId, inventoryId, inventory.withSlot(slot, stack))
         null;
       }
     } else {
@@ -48,76 +97,156 @@ class InventoryActor(val ns: String, val jsonStorage: ActorRef)
     }
   }
 
-  private def get(blockId: UUID, slot: Int): Stack =
-    if (inventories.containsKey(blockId.toString)) {
-      inventories.get(blockId.toString).getStack(slot)
+  private def add(blockId: UUID, inventoryId: InventoryId, stack: Stack) =
+    if (inventoryExists(blockId, inventoryId)) {
+      val result = getInventory(blockId, inventoryId).acceptPartOf(stack)
+      putInventory(blockId, inventoryId, result.getAccepting())
+      result.getGiving
+    } else {
+      stack
+    }
+
+  private def get(blockId: UUID, inventoryId: InventoryId, slot: Int): Stack =
+    if (inventoryExists(blockId, inventoryId)) {
+      getInventory(blockId, inventoryId).getStack(slot)
     } else {
       null
     }
 
-  private def remove(blockId: UUID, slot: Int, amount: StackAmount): Stack =
-    if (inventories.containsKey(blockId.toString)) {
-      val i = inventories.get(blockId.toString)
+  private def remove(blockId: UUID, inventoryId: InventoryId, slot: Int, amount: StackAmount): Stack =
+    if (inventoryExists(blockId, inventoryId)) {
+      val i = getInventory(blockId, inventoryId)
       val s = i.getStack(slot)
       if (s == null)
         return null
-      inventories.put(blockId.toString, i.withSlot(slot, s.drop(amount)))
+      putInventory(blockId, inventoryId, i.withSlot(slot, s.drop(amount)))
       s.take(amount)
     } else {
       null
     }
 
+  private def remove(blockId: UUID, inventoryId: InventoryId, blockTypeId: BlockTypeId, amount: Int): Stack =
+    if (inventoryExists(blockId, inventoryId)) {
+      val i = getInventory(blockId, inventoryId)
+      putInventory(blockId, inventoryId, i.drop(blockTypeId, amount))
+      i.take(blockTypeId, amount)
+    } else {
+      null
+    }
+
+  private def transfer(fromBlockId: UUID,
+                       fromInventoryId: InventoryId,
+                       toBlockId: UUID,
+                       toInventoryId: InventoryId,
+                       blockTypeId: BlockTypeId,
+                       amount: Int) {
+    if (inventoryExists(fromBlockId, fromInventoryId) && inventoryExists(toBlockId, toInventoryId)) {
+      val from = getInventory(fromBlockId, fromInventoryId)
+      val to = getInventory(toBlockId, toInventoryId)
+
+      val stack = from.take(blockTypeId, amount)
+      if (stack != null) {
+        val leftovers = to.acceptPartOf(stack)
+
+        /* Check if we could successfully add all blocks from the stack to the inventory */
+        if (leftovers.getGiving == null) {
+          /* Save the transfer */
+          putInventory(fromBlockId, fromInventoryId, from.drop(blockTypeId, amount))
+          putInventory(toBlockId, toInventoryId, leftovers.getAccepting)
+        }
+      }
+    }
+  }
+
   def receive = {
     case GsonLoaded(_, json) if json != null =>
-      inventories = gson.fromJson(json, typeOfInventories)
+      storageInventories = gson.fromJson(json, typeOfInventories)
       // This handles old inventories where empty stacks wasn't null
       val updatedInventories = new java.util.HashMap[String, Inventory]()
-      inventories.asScala.toMap foreach {
+      storageInventories.asScala.toMap foreach {
         case (pos, inventory) =>
           updatedInventories.put(pos, Inventory.convertPre0_1(inventory))
       }
-      inventories = updatedInventories
-      context.become(ready)
+      storageInventories = updatedInventories
+      context.become(loadOtherInventories())
       unstashAll()
     case GsonLoaded(_, _) =>
-      inventories = new java.util.HashMap()
-      context.become(ready)
+      storageInventories = new java.util.HashMap()
+      context.become(loadOtherInventories())
       unstashAll()
     case _ =>
       stash()
   }
 
+  def loadOtherInventories(): Receive = {
+    loadGson(OtherInventoriesFile)
+    val f: Receive = {
+      case GsonLoaded(_, json) if json != null =>
+        otherInventories = gson.fromJson(json, typeOfOtherInventories)
+        context.become(ready)
+        unstashAll()
+      case GsonLoaded(_, _) =>
+        otherInventories = new java.util.HashMap()
+        context.become(ready)
+        unstashAll()
+      case _ =>
+        stash()
+    }
+    f
+  }
+
   def ready: Receive = {
-    case CreateInventory(blockId, size) =>
-      if (!inventories.containsKey(blockId.toString)) {
-        inventories.put(blockId.toString, Inventory.createEmpty(size))
+    case c: CreateInventory =>
+      if (!inventoryExists(c.getBlockId, c.getInventoryId)) {
+        putInventory(c.getBlockId, c.getInventoryId, Inventory.createEmpty(c.getSize))
       }
 
-    case GetInventory(blockId) =>
-      sender ! GetInventoryResponse(blockId, Option(inventories.get(blockId.toString)))
+    case g: GetInventory =>
+      sender ! new GetInventoryResult(g.getBlockId, g.getInventoryId, getInventory(g.getBlockId, g.getInventoryId))
 
-    case PutStack(blockId, slot, stack) =>
-      val leftovers = put(blockId, slot, stack)
-      sender ! new ReceiveStack(leftovers)
+    case p: PutStackIntoSlot =>
+      sender ! new ReceiveStack(put(p.getBlockId, p.getInventoryId, p.getSlot, p.getStack))
 
-    case RemoveStack(blockId, slot, amount) =>
-      sender ! new ReceiveStack(remove(blockId, slot, amount))
+    case a: AddToInventory =>
+      sender ! new ReceiveStack(add(a.getBlockId, a.getInventoryId, a.getStack))
 
-    case GetStack(blockId, slot) =>
-      sender ! GetStackResponse(blockId, slot, get(blockId, slot))
+    case r: RemoveFromInventory =>
+      sender ! new ReceiveStack(remove(r.getBlockId, r.getInventoryId, r.getBlockTypeId, r.getAmount))
 
-    case DeleteInventory(blockId) =>
-      inventories.remove(blockId.toString)
+    case r: RemoveStackFromSlot =>
+      sender ! new ReceiveStack(remove(r.getBlockId, r.getInventoryId, r.getSlot, r.getAmount))
 
-    case StoreData =>
-      storeGson(InventoriesFile, gson.toJsonTree(inventories, typeOfInventories))
+    case t: TransferBetweenInventories =>
+      transfer(t.getFromBlockId,
+               t.getFromInventoryId,
+               t.getToBlockId,
+               t.getToInventoryId,
+               t.getBlockTypeId,
+               t.getAmount)
 
+    case d: DeleteInventory =>
+      removeInventory(d.getBlockId, d.getInventoryId)
+
+    case StoreData =>
+      storeGson(InventoriesFile, gson.toJsonTree(storageInventories, typeOfInventories))
+      storeGson(OtherInventoriesFile, gson.toJsonTree(otherInventories, typeOfOtherInventories))
+
+    case g: GetInventoriesView =>
+      var view = View.EMPTY
+      for ((inventoryId, inventoryView) <- g.getInventories.asScala) {
+        val inventory = getInventory(g.getBlockId, inventoryId)
+        if (inventory != null) {
+          view = view.add(inventoryView, inventory)
+        }
+      }
+      sender ! new UpdateView(view)
   }
 }
 
 object InventoryActor {
   case object StoreData
   val InventoriesFile = "inventories"
+  val OtherInventoriesFile = "other_inventories"
 
   @PluginConstructor
   def props(name: String, universe: ActorRef, @Config(key = "json-storage") jsonStorage: ActorRef): Props =
diff --git a/src/main/scala/konstructs/konstructing.scala b/src/main/scala/konstructs/konstructing.scala
index f8bc76a..369517f 100644
--- a/src/main/scala/konstructs/konstructing.scala
+++ b/src/main/scala/konstructs/konstructing.scala
@@ -10,7 +10,7 @@ import com.typesafe.config.{Config => TypesafeConfig, ConfigValueType}
 import com.typesafe.config.ConfigException.BadValue
 import akka.actor.{Actor, Props, ActorRef, Stash}
 import konstructs.api._
-import konstructs.api.messages.GetBlockFactory
+import konstructs.api.messages._
 import konstructs.plugin.{PluginConstructor, Config, ListConfig}
 
 class KonstructingActor(universe: ActorRef, konstructs: Set[Konstruct]) extends Actor with Stash {
@@ -145,24 +145,24 @@ class KonstructingViewActor(player: ActorRef,
     case f: BlockFactory =>
       factory = f
       if (inventoryId != null) {
-        universe ! GetInventory(inventoryId)
+        universe ! new GetInventory(inventoryId)
       } else {
         context.become(ready(EmptyInventory))
-        player ! ConnectView(self, view(EmptyInventory))
+        player ! new ConnectView(self, view(EmptyInventory))
       }
-    case GetInventoryResponse(_, Some(inventory)) =>
-      context.become(ready(inventory))
-      player ! ConnectView(self, view(inventory))
+    case g: GetInventoryResult if g.getInventory != null =>
+      context.become(ready(g.getInventory))
+      player ! new ConnectView(self, view(g.getInventory))
     case _ =>
       context.stop(self)
   }
 
   def awaitInventory: Receive = {
-    case GetInventoryResponse(_, Some(inventory)) =>
-      context.become(ready(inventory))
-      player ! UpdateView(view(inventory))
+    case g: GetInventoryResult if g.getInventory != null =>
+      context.become(ready(g.getInventory))
+      player ! new UpdateView(view(g.getInventory))
       unstashAll()
-    case CloseInventory =>
+    case CloseView.MESSAGE =>
       context.stop(self)
     case _ =>
       stash()
@@ -183,10 +183,10 @@ class KonstructingViewActor(player: ActorRef,
       val newKonstructing = konstructing.remove(pattern, factory, toKonstruct)
       if (newKonstructing != null)
         updateKonstructing(newKonstructing)
-      player ! ReceiveStack(Stack.createOfSize(stack.getTypeId, toKonstruct * stack.size))
-      player ! UpdateView(view(inventory))
+      player ! new ReceiveStack(Stack.createOfSize(stack.getTypeId, toKonstruct * stack.size))
+      player ! new UpdateView(view(inventory))
       unstashAll()
-    case CloseInventory =>
+    case CloseView.MESSAGE =>
       context.stop(self)
     case _ =>
       stash()
@@ -197,42 +197,47 @@ class KonstructingViewActor(player: ActorRef,
       player ! r
     case PatternMatched(stack) =>
       result = result.withSlot(0, stack)
-      player ! UpdateView(view(inventory))
-    case PutViewStack(stack, to) =>
+      player ! new UpdateView(view(inventory))
+    case p: PutViewStack =>
+      val stack = p.getStack
+      val to = p.getPosition
       if (inventoryView.contains(to)) {
         context.become(awaitInventory)
-        universe.forward(PutStack(inventoryId, inventoryView.translate(to), stack))
-        universe ! GetInventory(inventoryId)
+        universe.forward(new PutStackIntoSlot(inventoryId, InventoryId.STORAGE, inventoryView.translate(to), stack))
+        universe ! new GetInventory(inventoryId)
       } else if (konstructingView.contains(to)) {
         val index = konstructingView.translate(to)
         val oldStack = konstructing.getStack(index)
         if (oldStack != null) {
           if (oldStack.acceptsPartOf(stack)) {
             val r = oldStack.acceptPartOf(stack)
-            sender ! ReceiveStack(r.getGiving)
+            sender ! new ReceiveStack(r.getGiving)
             updateKonstructing(konstructing.withSlot(index, r.getAccepting()))
           } else {
             updateKonstructing(konstructing.withSlot(index, stack))
-            sender ! ReceiveStack(oldStack)
+            sender ! new ReceiveStack(oldStack)
           }
         } else {
           updateKonstructing(konstructing.withSlot(index, stack))
-          sender ! ReceiveStack(null)
+          sender ! new ReceiveStack(null)
         }
-        player ! UpdateView(view(inventory))
+        player ! new UpdateView(view(inventory))
       } else {
-        sender ! ReceiveStack(stack)
+        sender ! new ReceiveStack(stack)
       }
-    case RemoveViewStack(from, amount) =>
+    case r: RemoveViewStack =>
+      val from = r.getPosition
+      val amount = r.getAmount
       if (inventoryView.contains(from)) {
         context.become(awaitInventory)
-        universe.forward(RemoveStack(inventoryId, inventoryView.translate(from), amount))
-        universe ! GetInventory(inventoryId)
+        universe.forward(
+          new RemoveStackFromSlot(inventoryId, InventoryId.STORAGE, inventoryView.translate(from), amount))
+        universe ! new GetInventory(inventoryId)
       } else if (konstructingView.contains(from)) {
         val stack = konstructing.getStack(konstructingView.translate(from))
         updateKonstructing(konstructing.withSlot(konstructingView.translate(from), stack.drop(amount)))
-        sender ! ReceiveStack(stack.take(amount))
-        player ! UpdateView(view(inventory))
+        sender ! new ReceiveStack(stack.take(amount))
+        player ! new UpdateView(view(inventory))
       } else if (resultView.contains(from)) {
         val pattern = konstructing.getPattern(konstructingView)
         if (pattern != null) {
@@ -240,13 +245,13 @@ class KonstructingViewActor(player: ActorRef,
             context.become(awaitKonstruction(inventory, amount))
             universe ! KonstructPattern(pattern)
           } else {
-            sender ! ReceiveStack(null)
+            sender ! new ReceiveStack(null)
           }
         } else {
-          sender ! ReceiveStack(null)
+          sender ! new ReceiveStack(null)
         }
       }
-    case CloseInventory =>
+    case CloseView.MESSAGE =>
       context.stop(self)
   }
 
diff --git a/src/main/scala/konstructs/player.scala b/src/main/scala/konstructs/player.scala
index 845733f..b5a5cab 100644
--- a/src/main/scala/konstructs/player.scala
+++ b/src/main/scala/konstructs/player.scala
@@ -48,7 +48,7 @@ class PlayerActor(
         data = newData
         if (data.inventory.isEmpty) {
           val inventoryBlock = Block.createWithId(ToolSackActor.BlockId)
-          universe ! CreateInventory(inventoryBlock.getId, 16)
+          universe ! new CreateInventory(inventoryBlock.getId, 16)
           val inventory = Inventory.createEmpty(9).withSlot(0, Stack.createFromBlock(inventoryBlock))
           data = data.copy(inventory = inventory)
         } else {
@@ -276,11 +276,11 @@ class PlayerActor(
       if (!r.getBlock.getType.equals(BlockTypeId.VACUUM)) {
         putInBelt(Stack.createFromBlock(r.getBlock))
       }
-    case ReceiveStack(stack) =>
-      putInBelt(stack)
-    case ConnectView(inventoryActor, view) =>
-      context.become(manageInventory(inventoryActor, view) orElse handleBasics orElse stashAll)
-      client ! InventoryUpdate(addBelt(view))
+    case r: ReceiveStack =>
+      putInBelt(r.getStack)
+    case c: ConnectView =>
+      context.become(manageInventory(c.getManager, c.getView) orElse handleBasics orElse stashAll)
+      client ! InventoryUpdate(addBelt(c.getView))
   }
 
   val BeltView = new InventoryView(0, 4, 1, 9)
@@ -317,16 +317,16 @@ class PlayerActor(
           client ! InventoryUpdate(addBelt(view))
         } else {
           context.become(manageInventory(inventoryActor, view) orElse handleBasics orElse stashAll)
-          inventoryActor ! PutViewStack(stack, index)
+          inventoryActor ! new PutViewStack(stack, index)
         }
         unstashAll()
-      case UpdateView(view) =>
-        context.become(stackSelected(inventoryActor, view, stack) orElse handleBasics orElse stashAll)
+      case u: UpdateView =>
+        context.become(stackSelected(inventoryActor, u.getView, stack) orElse handleBasics orElse stashAll)
         unstashAll()
-        client ! InventoryUpdate(addBelt(view))
-      case CloseInventory =>
+        client ! InventoryUpdate(addBelt(u.getView))
+      case CloseView.MESSAGE =>
         context.become(ready orElse handleBasics)
-        inventoryActor ! CloseInventory
+        inventoryActor ! CloseView.MESSAGE
         unstashAll()
     }
     f
@@ -354,17 +354,17 @@ class PlayerActor(
             client ! InventoryUpdate(addBelt(view))
           }
         } else {
-          inventoryActor ! RemoveViewStack(index, amount)
+          inventoryActor ! new RemoveViewStack(amount, index)
         }
-      case UpdateView(view) =>
-        context.become(manageInventory(inventoryActor, view) orElse handleBasics orElse stashAll)
-        client ! InventoryUpdate(addBelt(view))
-      case ReceiveStack(stack) =>
-        if (stack != null)
-          context.become(stackSelected(inventoryActor, view, stack) orElse handleBasics orElse stashAll)
-      case CloseInventory =>
+      case u: UpdateView =>
+        context.become(manageInventory(inventoryActor, u.getView) orElse handleBasics orElse stashAll)
+        client ! InventoryUpdate(addBelt(u.getView))
+      case r: ReceiveStack =>
+        if (r.getStack != null)
+          context.become(stackSelected(inventoryActor, view, r.getStack) orElse handleBasics orElse stashAll)
+      case CloseView.MESSAGE =>
         context.become(ready orElse handleBasics)
-        inventoryActor ! CloseInventory
+        inventoryActor ! CloseView.MESSAGE
         unstashAll()
     }
     f
diff --git a/src/main/scala/konstructs/plugin/toolsack/sack.scala b/src/main/scala/konstructs/plugin/toolsack/sack.scala
index 0bb6b0c..1fbb78f 100644
--- a/src/main/scala/konstructs/plugin/toolsack/sack.scala
+++ b/src/main/scala/konstructs/plugin/toolsack/sack.scala
@@ -15,7 +15,7 @@ class ToolSackActor(universe: ActorRef) extends Actor {
         case i: InteractTertiary if !i.isWorldPhase && i.getBlock != null && i.getBlock.getType == BlockId =>
           val b = if (i.getBlock.getId == null) {
             val newBlock = i.getBlock.withId(UUID.randomUUID)
-            universe ! CreateInventory(newBlock.getId, 16)
+            universe ! new CreateInventory(newBlock.getId, 16)
             newBlock
           } else {
             i.getBlock
@@ -27,7 +27,7 @@ class ToolSackActor(universe: ActorRef) extends Actor {
             if i.isWorldPhase && i.getBlockAtPosition != null && i.getBlockAtPosition.getType == BlockId =>
           val b = if (i.getBlockAtPosition.getId == null) {
             val newBlock = i.getBlockAtPosition.withId(UUID.randomUUID)
-            universe ! CreateInventory(newBlock.getId, 16)
+            universe ! new CreateInventory(newBlock.getId, 16)
             newBlock
           } else {
             i.getBlockAtPosition
diff --git a/src/main/scala/konstructs/protocol/client.scala b/src/main/scala/konstructs/protocol/client.scala
index 62c9ef9..5f1a614 100644
--- a/src/main/scala/konstructs/protocol/client.scala
+++ b/src/main/scala/konstructs/protocol/client.scala
@@ -6,7 +6,7 @@ import akka.io.Tcp
 import akka.util.{ByteString, ByteStringBuilder}
 import konstructs.{PlayerActor, UniverseActor, DbActor}
 import konstructs.api._
-import konstructs.api.messages.Said
+import konstructs.api.messages.{Said, CloseView}
 import konstructs.shard.ChunkPosition
 
 class ClientActor(universe: ActorRef, factory: BlockFactory, textures: Array[Byte]) extends Actor with Stash {
@@ -58,7 +58,7 @@ class ClientActor(universe: ActorRef, factory: BlockFactory, textures: Array[Byt
       val message = command.substring(2)
       player.actor ! Say(message)
     } else if (command.startsWith("I")) {
-      player.actor ! CloseInventory
+      player.actor ! CloseView.MESSAGE
     } else if (command.startsWith("R,")) {
       val ints = readData(_.toInt, command.drop(2))
       player.actor ! SelectItem(ints(0), ints(1))
diff --git a/src/main/scala/konstructs/shard/ShardActor.scala b/src/main/scala/konstructs/shard/ShardActor.scala
index 2b86625..f1ff7de 100644
--- a/src/main/scala/konstructs/shard/ShardActor.scala
+++ b/src/main/scala/konstructs/shard/ShardActor.scala
@@ -27,13 +27,13 @@ import konstructs.api.{
   BlockType,
   BlockUpdate,
   Health,
-  ReceiveStack,
   Stack,
   MetricId
 }
 import konstructs.api.messages.{
   BoxQuery,
   BoxQueryResult,
+  ReceiveStack,
   ReplaceBlock,
   ReplaceBlockResult,
   ViewBlock,
@@ -347,7 +347,7 @@ class ShardActor(db: ActorRef,
       val block = Option(i.block).getOrElse(VacuumBlock)
       damageBlock(i.position, block, positionMapping) { (using, damaged) =>
         if (damaged != null) {
-          s ! ReceiveStack(Stack.createFromBlock(damaged))
+          s ! new ReceiveStack(Stack.createFromBlock(damaged))
         }
         if (block != null)
           s ! new InteractResult(i.position, using, damaged)
diff --git a/src/main/scala/konstructs/universe.scala b/src/main/scala/konstructs/universe.scala
index 87b1bcf..f3dedca 100644
--- a/src/main/scala/konstructs/universe.scala
+++ b/src/main/scala/konstructs/universe.scala
@@ -123,14 +123,20 @@ class UniverseActor(
       db forward r
     case c: CreateInventory =>
       inventoryManager.forward(c)
+    case g: GetInventoriesView =>
+      inventoryManager.forward(g)
     case g: GetInventory =>
       inventoryManager.forward(g)
-    case p: PutStack =>
+    case a: AddToInventory =>
+      inventoryManager.forward(a)
+    case r: RemoveFromInventory =>
+      inventoryManager.forward(r)
+    case t: TransferBetweenInventories =>
+      inventoryManager.forward(t)
+    case p: PutStackIntoSlot =>
       inventoryManager.forward(p)
-    case r: RemoveStack =>
+    case r: RemoveStackFromSlot =>
       inventoryManager.forward(r)
-    case g: GetStack =>
-      inventoryManager.forward(g)
     case d: DeleteInventory =>
       inventoryManager.forward(d)
     case m: MatchPattern =>