The newly-released SpatialOS 11 SDK version brings some big improvements, particularly to the way workers interact with core parts of the SpatialOS runtime. One of the most obvious changes is the extension of the “standard library components” concept to cover some functionality previously available as dedicated SDK features, and some new functionality, too! We wanted to give you a quick update to explain what this is all about, what’s new, and why we decided to move in this direction.
What’s the background of the standard library components?
We first introduced the notion of a “standard schema library” all the way back in SpatialOS version 9. At that time, the only way to control which workers had read or write access to particular entities or components was from a legacy worker type called the “gsim”, using APIs only available in Scala. In order to remove this reliance on the gsim worker, we were faced with the task of coming up with a new way to expose this functionality.
But read/write access is really just a small piece of structured data associated with each entity, and we already had a perfectly good way of associating bits of data with entities - components. And we already had perfectly good ways of allowing components to be manipulated from workers written in any language - using the generated APIs associated with those components.
Therefore, the notion of a standard library component was born: components whose schema definitions were provided by SpatialOS, and which the runtime could inspect to provide core features, but otherwise functionally identical to any user-defined component. The read/write mechanism became the
EntityAcl component you might have used already.
What are the new standard library components?
In SpatialOS 11, we’re extending the set of standard library components. The
EntityAcl component, which manages read/write access to entities as described above, has been simplified in a minor way. In addition, there are three new standard library components:
Positiondefines the canonical position of each entity whenever SpatialOS needs to know it - specifically, for deciding how to distribute authority among workers in a spatially-coherent way, for determining which entities lie in the interest region of a given worker, and for entity queries.
The special schema language type for telling SpatialOS to read this information from a custom component (
EntityPosition) has been removed, but you’re still free to define a custom position component that works differently if you like - as long as you also update the standard library
Positioncomponent often enough that it doesn’t get too out of sync.
Metadatareplaces the built-in “Prefab” (Unity-specific terminology) concept. This component is intended to provide data about an entity for the inspector to make use of. Currently, it contains a single string used to denote the “type” of an entity, which is prominently displayed by the inspector. It’s also used by default in Unity and Unreal to associate entities with prefabs or blueprints (i.e. game assets), respectively.
In the future, we might add more options to this component, like the ability to dynamically configure icons and colours for entities in the inspector.
Persistencecomponent is a brand-new feature that lets you choose which entities are included in snapshots taken from a running deployment. Some kinds of entities created at runtime might not make sense to store in these snapshots. For example, entities associated with players might be best excluded, since the players won’t still be connected after a deployment restart. Another example could be temporary entities, perhaps powerups or environmental hazards. You can now exclude an entity from deployment snapshots by simply not adding the Persistence component to the entity. (We’ve added helper APIs to Unity and Unreal to make sure you don’t forget about this component when creating a new entity.)
This is by no means the end. We plan to expose new runtime features via standard library components in the future, when the model fits.
Why are you doing this? What are the benefits of standard library components?
The common theme above is that we’re removing special pieces of entity data with first-class SDK support (such as Prefab), and replacing them with standard components. This might seem odd at first (surely first-class support is better?), so it could use some justification.
There are many reasons we think this will be great for SpatialOS in the long run. If all entity data is represented by components, then:
All platform features work equally well with all entity data, out of the box. Standard library components are visible in the inspector, can be queried like any other component, read from snapshots, and so on. Any new features we provide (optimizations, API improvements, guarantees…) will automatically work with the standard library components, too.
We can provide consistent APIs across the board. Piggy-backing on the generated APIs for user-defined components means all of the functionality and semantics you’re used to for your own components work in exactly the same way for standard library components. Updates and authority are identical; the data can be read and written by any worker.
We can deliver more features, faster. Providing dedicated APIs in every language and every engine integration for interacting with “special” bits of entity data is a tremendous maintenance overhead. Standard library components mean we can write a single schema definition, and then implement its runtime behaviour, once. Additionally, standard library components need no special support to be stored by the runtime and made available to internal systems. As an example, the new Persistence component took one engineer just a few hours to design and implement end-to-end. Without standard library components, this feature would have taken at least a week to implement, and been much more prone to bugs.
The conceptual clarity will be beneficial in the long term. We feel that the idea of standard components that are “understood by SpatialOS” is very natural. Just like user-defined components are implemented by workers, standard library components allow you to opt-in to an implementation of some system provided by the platform. This closely mirrors the way entity-component systems work in common game engines. Once we’re past the transition period, SpatialOS will be easier to understand and use as a result.
Where can I learn more about how to use the standard library components?
Please refer to the standard schema library documentation for a more detailed explanation of each standard library component, and the documentation for your chosen language or game engine SDK for usage examples.