Forest Logo
search
package_2

bitnet

By @minecoiii2

Roblox

Mirrored from Wally

BitNet

Buffer-based networking library for Roblox. Replaces RemoteEvents and RemoteFunctions with typed, batched events and funcs that all run over two shared remotes.

  • Every fire in a frame is packed into one buffer per player and sent once per Heartbeat
  • Schemas describe the payload, so data goes out as tightly packed bytes instead of Lua tables
  • Booleans cost one bit, Instances cost no buffer space
  • Reliable and unreliable events, two-way funcs, rate limiting and runtime typechecking

Installation

BitNet comes with Networking, a template module where you define all of your events and funcs.

Manual: download BitNet.rbxm and Networking.rbxm from Releases and insert both into ReplicatedStorage.

Wally

[dependencies]
BitNet = "minecoiii2/bitnet@3.0.0"

Then copy Networking.luau into your project and change its require to point at your packages folder, e.g. ReplicatedStorage.Packages.BitNet.

Quick start

Every event and func goes in the table that Networking returns. The server and client both require this one module, so everything registers in the same order on both sides.

-- ReplicatedStorage.Networking
return {
	Chat = RemoteEvent({
		Args = args(string, u8),
	}),
	Hit = RemoteEvent({
		Args = struct({ target = Instance, damage = u16 }),
		Reliable = false,
		RateLimit = BuildRatelimit(20, 1),
	}),
	GetPrice = RemoteFunction({
		Args = string,
		Returns = u32,
	}),
}

The template sets up short names for everything at the top: RemoteEvent is BitNet.event, RemoteFunction is BitNet.func, args is tuple, and the types are named after their Roblox equivalents (Vector3, CFrame, Instance, ...). Two names differ from the table below: any is ref, and auto is BitNet's any.

-- Server
const Networking = require(ReplicatedStorage.Networking)

Networking.Chat.OnServerEvent:Connect(function(player, message, channel)
	Networking.Chat:FireAllClients(message, channel)
end)

Networking.GetPrice:SetCallback(function(player, itemId)
	return 100
end)
-- Client
const Networking = require(ReplicatedStorage.Networking)

Networking.Chat.OnClientEvent:Connect(function(message, channel)
	print(message)
end)

Networking.Chat:FireServer("hello", 1)
const price = Networking.GetPrice:InvokeServer("sword")

Types

TypeBytesNotes
u8 u16 u24 u321–4Unsigned integers
i8 i16 i24 i321–4Signed integers
f24 f32 f643, 4, 8number is f64. f24 is lossy (~3e-5 relative error)
bool1 bitPacked eight to a byte
string buffer1–5 + length
uuid16Canonical 36-character lowercase form
vec2 vec38, 12
vec2i16(scale?) vec3i16(scale?)4, 6Fixed point, ±327 studs at the default scale of 100
cframe cframelong18, 24cframe uses 16-bit rotation angles
color338 bits per channel
brickcolor numberrange udim udim22, 8, 4, 8
numbersequence colorsequencevaries
instance ref unknown0Sent next to the buffer as normal Roblox values
any1 + valuePicks an encoding at runtime
nothing0Always nil

The narrow types (u24, i24, f24, vec*i16, cframe) save bytes but cost a bit of CPU. Use them when bandwidth matters.

Combinators

  • struct(format): table with fixed keys
  • array(value): array of one type
  • map(key, value): dictionary, up to 16,383 entries
  • optional(value): value or nil
  • tuple(...): multiple arguments
  • enum(Enum.X): a Roblox EnumItem
  • enumFromKeys(t) / enumFromValues(t): string from a known set, sent as an index
  • compress(value, level?): Zstd-compresses the value when that makes it smaller

Events

bitnet.event(options)

OptionDefaultDescription
ArgsrequiredPayload type
ReliabletrueUse the reliable or unreliable channel
TypecheckStudio onlyValidate payloads before sending
RateLimitnone{ calls, per } limit on fires from each client

Methods: :FireServer(...), :FireClient(player, ...), :FireAllClients(...), :FireClientsStreamed(position, range, ...), :FireClientsStreamedWithExclusion(position, range, player, ...)

Listening: .OnServerEvent gives (player, ...) and .OnClientEvent gives (...). .OnReceived is the same signal under another name.

On the client, fires that arrive before anything is connected are queued and delivered to the first listener.

Funcs

bitnet.func(options)

OptionDefaultDescription
ArgsrequiredRequest type
ReturnsrequiredResponse type
Timeout7Seconds before the invoke errors. 0 or math.huge waits forever
TypecheckStudio onlyValidate payloads before sending
RateLimitnone{ calls, per } limit on invokes from each client

Methods: :InvokeServer(...), :InvokeClient(player, ...), :SetCallback(fn), plus :SetServerCallback(fn) and :SetClientCallback(fn), which error when called on the wrong side.

Funcs work in both directions and are always reliable. Invoking a client has some safety rules built in:

  • :InvokeClient requires a finite Timeout
  • A player can have at most 32 pending invokes
  • Only the invoked player can answer, and pending invokes fail as soon as that player leaves

Signal

bitnet.signal() creates a local signal that isn't networked. It has :Fire, :Connect, :Once, :Wait, :DisconnectAll and :Destroy. Connections have :Disconnect, :Reconnect and :Destroy.

Gotchas

  • Register in the same order on both sides. IDs are assigned in registration order, and a mismatch sends data to the wrong handler without any error. Define everything in Networking and require it before anything fires.
  • enumFromKeys and enumFromValues need the same set on both sides. Keep the source table in ReplicatedStorage, written out literally.
  • array can't hold nil. array(optional(x)) gets cut off at the first nil.
  • udim, udim2 and vec*i16 wrap around when out of range. Only Typecheck catches it.
  • Unreliable fires over 1,000 bytes are dropped with a warning.
  • compress costs about 25µs per fire to decompress. Only use it on large, repetitive payloads.
  • any picks default encodings, so a CFrame inside any is sent as cframe. Name the type yourself when you need a specific one.
  • Typecheck is on in Studio and off in live servers unless you set it.

License

MIT

Package Details

Install command (Click to copy)


Version

3.0.1

License

MIT

check_circle

Safe for commercial use

Automated license review — not legal advice.