Skip to main content

ServerNetWire

This item only works when running on the server. Server

Server-side NetWire implementation using Sleitnick's Comm under the hood. Provides a comprehensive interface for creating and managing networking infrastructure across your server codebase.

Structure:

  • ServerNetWireClass: Contains static methods (constructors, utilities)
  • ServerNetWire: Contains instance methods (RegisterEvent, RegisterProperty, etc.)

This separation ensures better linting support and prevents static methods from appearing in instance method suggestions.

Key Features:

  • Declarative API: Use markers to declare networking infrastructure
  • Memoization: NetWires are cached by namespace for consistency
  • Service Integration: Built-in support for Roam and similar frameworks
  • Middleware Support: Comprehensive inbound and outbound middleware system
  • Type Safety: Full typing with proper metatable integration

NetWire Creation: The following variables are all equivalent as NetWires are memoized by their namespace, so creating a new one with the same namespace will return the same object.

local TestNetWire1 = NetWire.Server.new("MyNetWire")
local TestNetWire2 = NetWire.Server("MyNetWire")

print(TestNetWire1 == TestNetWire2) -- true 
INFO

You can also create a by calling the package directly, but this is not encouraged as it obscures the RunContext in which the NetWire is being created.

local TestNetWire3 = NetWire("MyNetWire")

Event and Property Creation: You can create client exposed events by registering them with the method or setting their index: The following two lines accomplish the same thing.

TestNetWire:RegisterEvent("TestEvent")
TestNetWire.TestEvent = NetWire.createEvent()

More examples can be found under the respective construction methods.

Types

ServerMiddleware

type ServerMiddleware = (
playerPlayer,
args{any}
) → (
shouldContinueboolean,
...any
)

Middleware function for server-side operations. Returns whether to continue processing and any modified arguments.

Functions

new

constructorstatic
ServerNetWire.new(
nameSpacestring | Service--

The namespace for the NetWire or a Service object

) → ServerNetWire

Constructs a new ServerNetWire. If a ServerNetWire with the same nameSpace already exists, it will be returned instead.

setupServiceNetworking

constructorstatic
ServerNetWire.setupServiceNetworking(serviceService) → ServerNetWire

Creates a ServerNetWire from a Roam Service. This method will read the service's Name and Client table to create the NetWire. The goal of this function is to recreate the simplicity of Knit's networking features without the systems being coupled together. In order to access the service on the client, use NetWire.Client("SERVICE_NAME").

local NetWire = require(Packages.NetWire).Server
local Roam = require(Packages.Roam)
----------------------------------------------------------------

local ExampleService = {}
ExampleService.Client = {
    TestEvent = NetWire.createEvent()
}

function ExampleService.Client:Greeting(plr: Player, msg: string)
    print(plr.Name, "said", msg) 
end

----------------------------------------------------------------

function ExampleService:RoamInit()
     -- Build the NetWire from the service Client table and replace it
    NetWire.setupServiceNetworking(self)
end

function ExampleService:RoamStart()
    task.wait(10)
     -- send a message to all clients
    self.Client.TestEvent:FireAll("Hello from ExampleService!")
end

----------------------------------------------------------------

Roam.registerService(ExampleService, "ExampleService")
return ExampleService
Client Table Overwrite

Calling this function will overwrite the service's Client table with the NetWire. You should not store anything aside from supported NetWire objects in the Client table.

Where to call

This function should be called within the init method of the service. This is to prevent netwires from being created outside of a running game.

RegisterEvent

ServerNetWire:RegisterEvent(
eventNamestring,
isUnreliableboolean?,
inboundMiddleware{ServerMiddleware}?,
outboundMiddleware{ServerMiddleware}?
) → ()

Creates a remote event with the given name.

Server Documentation: https://sleitnick.github.io/RbxUtil/api/RemoteSignal

Client Documentation: https://sleitnick.github.io/RbxUtil/api/ClientRemoteSignal

-- Server Side
local myWire = NetWire.Server("MyWire")

myWire.TestEvent = NetWire.createEvent()

myWire.TestEvent:Connect(function(plr: Player, someArg)
    print(someArg)
end)

myWire.TestEvent:FireAll("Hello from the server!")

---------------------------------------------------------
-- Client Side
local myWire = NetWire.Client("MyWire")

myWire.TestEvent:Connect(function(someArg)
    print(someArg)
end)

myWire.TestEvent:Fire("Hello from the client!")

RegisterProperty

ServerNetWire:RegisterProperty(
propertyNamestring,
initialValueany?,
inboundMiddleware{ServerMiddleware}?,
outboundMiddleware{ServerMiddleware}?
) → ()

Creates a remote property with the given name.

Server Documentation: https://sleitnick.github.io/RbxUtil/api/RemoteProperty

Client Documentation: https://sleitnick.github.io/RbxUtil/api/ClientRemoteProperty

-- Server Side
local myWire = NetWire.Server("MyWire")

myWire.TestProperty = NetWire.createProperty("Hello")

---------------------------------------------------------
-- Client Side
local myWire = NetWire.Client("MyWire")

if myWire.TestProperty:IsReady() then -- Check if its ready first
    print( myWire.TestProperty:Get() ) -- "Hello"
end

RegisterMethod

ServerNetWire:RegisterMethod(
functionNamestring,
callback(
selfany,
plrPlayer,
...any
) → (...any),
tbl{}?,
inboundMiddleware{ServerMiddleware}?,
outboundMiddleware{ServerMiddleware}?
) → ()

Creates a remote function with the given name. This is not suggested to be used by end users; instead you should just append a function to a netwire object and it will properly wrap it for you.

-- Server Side
local myWire = NetWire.Server("MyWire")

function myWire:TestMethod(plr: Player, arg: number)
    return arg * 2
end

---------------------------------------------------------
-- Client Side
local myWire = NetWire.Client("MyWire")

myWire:TestMethod(5):andThen(function(result)
    print(result) -- 10
end)
Show raw api
{
    "functions": [
        {
            "name": "new",
            "desc": "Constructs a new ServerNetWire. If a ServerNetWire with the same nameSpace already exists, it will\nbe returned instead.",
            "params": [
                {
                    "name": "nameSpace",
                    "desc": "The namespace for the NetWire or a Service object",
                    "lua_type": "string | Service"
                }
            ],
            "returns": [
                {
                    "desc": "",
                    "lua_type": "ServerNetWire"
                }
            ],
            "function_type": "static",
            "tags": [
                "constructor",
                "static"
            ],
            "source": {
                "line": 253,
                "path": "lib/netwire/src/ServerWire.luau"
            }
        },
        {
            "name": "setupServiceNetworking",
            "desc": "Creates a ServerNetWire from a Roam Service.\nThis method will read the service's Name and Client table to create the NetWire.\nThe goal of this function is to recreate the simplicity of Knit's networking features without\nthe systems being coupled together. \nIn order to access the service on the client, use `NetWire.Client(\"SERVICE_NAME\")`.\n\n```lua\nlocal NetWire = require(Packages.NetWire).Server\nlocal Roam = require(Packages.Roam)\n----------------------------------------------------------------\n\nlocal ExampleService = {}\nExampleService.Client = {\n    TestEvent = NetWire.createEvent()\n}\n\nfunction ExampleService.Client:Greeting(plr: Player, msg: string)\n    print(plr.Name, \"said\", msg) \nend\n\n----------------------------------------------------------------\n\nfunction ExampleService:RoamInit()\n     -- Build the NetWire from the service Client table and replace it\n    NetWire.setupServiceNetworking(self)\nend\n\nfunction ExampleService:RoamStart()\n    task.wait(10)\n     -- send a message to all clients\n    self.Client.TestEvent:FireAll(\"Hello from ExampleService!\")\nend\n\n----------------------------------------------------------------\n\nRoam.registerService(ExampleService, \"ExampleService\")\nreturn ExampleService\n```\n\n:::caution Client Table Overwrite\nCalling this function will overwrite the service's `Client` table with the NetWire.\nYou should not store anything aside from supported NetWire objects in the Client table.\n:::\n\n:::info Where to call\nThis function should be called within the init method of the service. This is\nto prevent netwires from being created outside of a running game.\n:::",
            "params": [
                {
                    "name": "service",
                    "desc": "",
                    "lua_type": "Service"
                }
            ],
            "returns": [
                {
                    "desc": "",
                    "lua_type": "ServerNetWire"
                }
            ],
            "function_type": "static",
            "tags": [
                "constructor",
                "static"
            ],
            "source": {
                "line": 342,
                "path": "lib/netwire/src/ServerWire.luau"
            }
        },
        {
            "name": "Destroy",
            "desc": "Destroys the NetWire and removes it from the internal cache.",
            "params": [],
            "returns": [],
            "function_type": "method",
            "tags": [
                "destructor"
            ],
            "private": true,
            "source": {
                "line": 388,
                "path": "lib/netwire/src/ServerWire.luau"
            }
        },
        {
            "name": "RegisterEvent",
            "desc": "Creates a remote event with the given name.\n\n\nServer Documentation: https://sleitnick.github.io/RbxUtil/api/RemoteSignal\n\nClient Documentation: https://sleitnick.github.io/RbxUtil/api/ClientRemoteSignal\n\n```lua\n-- Server Side\nlocal myWire = NetWire.Server(\"MyWire\")\n\nmyWire.TestEvent = NetWire.createEvent()\n\nmyWire.TestEvent:Connect(function(plr: Player, someArg)\n    print(someArg)\nend)\n\nmyWire.TestEvent:FireAll(\"Hello from the server!\")\n\n---------------------------------------------------------\n-- Client Side\nlocal myWire = NetWire.Client(\"MyWire\")\n\nmyWire.TestEvent:Connect(function(someArg)\n    print(someArg)\nend)\n\nmyWire.TestEvent:Fire(\"Hello from the client!\")\n```",
            "params": [
                {
                    "name": "eventName",
                    "desc": "",
                    "lua_type": "string"
                },
                {
                    "name": "isUnreliable",
                    "desc": "",
                    "lua_type": "boolean?"
                },
                {
                    "name": "inboundMiddleware",
                    "desc": "",
                    "lua_type": "{ ServerMiddleware }?"
                },
                {
                    "name": "outboundMiddleware",
                    "desc": "",
                    "lua_type": "{ ServerMiddleware }?\n"
                }
            ],
            "returns": [],
            "function_type": "method",
            "source": {
                "line": 426,
                "path": "lib/netwire/src/ServerWire.luau"
            }
        },
        {
            "name": "RegisterProperty",
            "desc": "Creates a remote property with the given name.\n\nServer Documentation: https://sleitnick.github.io/RbxUtil/api/RemoteProperty\n\nClient Documentation: https://sleitnick.github.io/RbxUtil/api/ClientRemoteProperty\n\n```lua\n-- Server Side\nlocal myWire = NetWire.Server(\"MyWire\")\n\nmyWire.TestProperty = NetWire.createProperty(\"Hello\")\n\n---------------------------------------------------------\n-- Client Side\nlocal myWire = NetWire.Client(\"MyWire\")\n\nif myWire.TestProperty:IsReady() then -- Check if its ready first\n    print( myWire.TestProperty:Get() ) -- \"Hello\"\nend\n```",
            "params": [
                {
                    "name": "propertyName",
                    "desc": "",
                    "lua_type": "string"
                },
                {
                    "name": "initialValue",
                    "desc": "",
                    "lua_type": "any?"
                },
                {
                    "name": "inboundMiddleware",
                    "desc": "",
                    "lua_type": "{ ServerMiddleware }?"
                },
                {
                    "name": "outboundMiddleware",
                    "desc": "",
                    "lua_type": "{ ServerMiddleware }?\n"
                }
            ],
            "returns": [],
            "function_type": "method",
            "source": {
                "line": 463,
                "path": "lib/netwire/src/ServerWire.luau"
            }
        },
        {
            "name": "RegisterMethod",
            "desc": "Creates a remote function with the given name. This is not suggested to be used by end users; instead\nyou should just append a function to a netwire object and it will properly wrap it for you.\n\n```lua\n-- Server Side\nlocal myWire = NetWire.Server(\"MyWire\")\n\nfunction myWire:TestMethod(plr: Player, arg: number)\n    return arg * 2\nend\n\n---------------------------------------------------------\n-- Client Side\nlocal myWire = NetWire.Client(\"MyWire\")\n\nmyWire:TestMethod(5):andThen(function(result)\n    print(result) -- 10\nend)\n```",
            "params": [
                {
                    "name": "functionName",
                    "desc": "",
                    "lua_type": "string"
                },
                {
                    "name": "callback",
                    "desc": "",
                    "lua_type": "(self: any, plr: Player, ...any) -> (...any)"
                },
                {
                    "name": "tbl",
                    "desc": "",
                    "lua_type": "{}?"
                },
                {
                    "name": "inboundMiddleware",
                    "desc": "",
                    "lua_type": "{ ServerMiddleware }?"
                },
                {
                    "name": "outboundMiddleware",
                    "desc": "",
                    "lua_type": "{ ServerMiddleware }?\n"
                }
            ],
            "returns": [],
            "function_type": "method",
            "source": {
                "line": 510,
                "path": "lib/netwire/src/ServerWire.luau"
            }
        }
    ],
    "properties": [
        {
            "name": "ClassName",
            "desc": "",
            "lua_type": "\"ServerNetWire\"",
            "private": true,
            "readonly": true,
            "source": {
                "line": 240,
                "path": "lib/netwire/src/ServerWire.luau"
            }
        }
    ],
    "types": [
        {
            "name": "ServerMiddleware",
            "desc": "Middleware function for server-side operations.\nReturns whether to continue processing and any modified arguments.",
            "lua_type": "(player: Player, args: {any}) -> (shouldContinue: boolean, ...any)",
            "source": {
                "line": 64,
                "path": "lib/netwire/src/NetWireTypes.luau"
            }
        }
    ],
    "name": "ServerNetWire",
    "desc": "Server-side NetWire implementation using Sleitnick's Comm under the hood. \nProvides a comprehensive interface for creating and managing networking infrastructure\nacross your server codebase.\n\n**Structure:**\n- `ServerNetWireClass`: Contains static methods (constructors, utilities)\n- `ServerNetWire`: Contains instance methods (RegisterEvent, RegisterProperty, etc.)\n\nThis separation ensures better linting support and prevents static methods from appearing \nin instance method suggestions.\n\n**Key Features:**\n- **Declarative API**: Use markers to declare networking infrastructure\n- **Memoization**: NetWires are cached by namespace for consistency\n- **Service Integration**: Built-in support for Roam and similar frameworks\n- **Middleware Support**: Comprehensive inbound and outbound middleware system\n- **Type Safety**: Full typing with proper metatable integration\n\n**NetWire Creation:**\nThe following variables are all equivalent as NetWires are memoized by their namespace,\nso creating a new one with the same namespace will return the same object.\n```lua\nlocal TestNetWire1 = NetWire.Server.new(\"MyNetWire\")\nlocal TestNetWire2 = NetWire.Server(\"MyNetWire\")\n\nprint(TestNetWire1 == TestNetWire2) -- true \n```\n:::info\nYou can also create a by calling the package directly, but this is not encouraged as it\nobscures the RunContext in which the NetWire is being created.\n```lua\nlocal TestNetWire3 = NetWire(\"MyNetWire\")\n```\n:::\n\n**Event and Property Creation:**\nYou can create client exposed events by registering them with the method or setting their index:\nThe following two lines accomplish the same thing.\n```lua\nTestNetWire:RegisterEvent(\"TestEvent\")\nTestNetWire.TestEvent = NetWire.createEvent()\n```\nMore examples can be found under the respective construction methods.",
    "realm": [
        "Server"
    ],
    "source": {
        "line": 52,
        "path": "lib/netwire/src/ServerWire.luau"
    }
}