NetStack

Godot addon

Godot 4.2+ addon for connecting a game to a NetStack project. It handles the connection, keeps a local copy of synchronized properties, and lets you call server Functions with await.

Install

  1. Download netstack-godot.zip and extract it into your project, so you have an addons/netstack folder.
  2. Open Project > Project Settings > Plugins and enable NetStack.
  3. Open Project Settings > General > Netstack and fill in your project's address from the dashboard Overview tab.

Enabling the plugin registers a global NetStack client and the project settings below.

Setting Meaning
connection/transport WebSocket (default) or UDP
connection/websocket_url wss://yourgame.netstack.network
connection/udp_host, udp_port yourgame.netstack.network, 7351
connection/api_key Needed for UDP only. Do not ship it in builds that players can download.
session/default_room, default_player_id Used when you call connect_to_room() with no arguments. An empty player ID generates a random one.
session/auto_connect Connect when the game starts
session/auto_reconnect Reconnect with backoff if the connection drops
session/call_timeout Seconds to wait for a Function result

Quick start

func _ready() -> void:
	NetStack.joined.connect(_on_joined)
	NetStack.connect_to_room("lobby-1", "alice")


func _on_joined(room: Dictionary) -> void:
	var result := await NetStack.call_function("useItem", {"itemId": "potion"})
	if result.ok:
		print(result.get_value("remaining"))
	elif result.has_error("ITEM_NOT_OWNED"):
		print("You do not own that item")

call_function always returns a NetStackResult and never throws. Check result.ok, then read result.value, or result.error_code and result.error_message. Besides Function errors, the codes NOT_CONNECTED, CALL_TIMEOUT and DISCONNECTED are produced locally.

Events

NetStack.listen("itemUsed", func(data): play_use_animation(data.playerId, data.itemId))
NetStack.server_event.connect(func(name, data): print(name, data))
NetStack.player_joined.connect(spawn_player)
NetStack.player_left.connect(remove_player)

Properties

var round_number = NetStack.get_room_property("round", 0)
var gold = NetStack.get_player_property("gold", "", 0)
var others_hp = NetStack.get_player_property("hp", "bob", 100)

NetStack.property_changed.connect(func(scope, player_id, key, value): print(scope, key, value))

Player properties are private by default, so you only see your own private values. Room properties are public. Global properties arrive as room properties.

JSON numbers arrive as float. Convert with int() when you need an integer.

Nodes

  • NetStackClient: the same client as the global NetStack, as a node. Add one if you want a second connection or per-scene settings.
  • NetStackPropertyBinding: add as a child of a Label, ProgressBar, Sprite2D and so on. Pick a scope and key and it keeps the parent's property updated. format uses {value}, for example Gold: {value}.
  • NetStackEventListener: set event_name and connect its received(data) signal in the editor.

Rooms

NetStack.switch_room("match-4821")
NetStack.leave_room()
NetStack.disconnect_from_server()

Notes

  • Room and player IDs use letters, numbers, underscores and hyphens, up to 64 characters. The addon checks this before connecting.
  • NetStack does not authenticate players. The player ID is a claim.
  • example/inventory_example.gd shows a complete flow against the inventory demo server.