neogate

package module
v0.4.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 2, 2026 License: Apache-2.0 Imports: 13 Imported by: 0

README

neogate

[!WARNING] Neogate is highly experimental and still changes frequently without notice. Old versions will also not be supported. Please wait for a proper release to use it in your projects, if you even want to.

Neogate is Liphium's WebSocket gateway implementation. Feel free to peak around and see how all of Liphium's real-time pipeline works. It's separated out to make it reusable in other projects or smaller services we might add to this repository in the future. Who knows what might happen?

The adapter pattern found in this module is something that makes it really easy to develop real-time systems no matter how complex. Everything can be modelled using them and that's also a reason why I maybe want to reuse it in future projects since it's already been tested well here in Liphium.

Documentation

Index

Constants

This section is empty.

Variables

View Source
var DebugLogs = true
View Source
var Log = log.New(log.Writer(), "neogate ", log.Flags())

Functions

func CreateHandlerFor

func CreateHandlerFor[T, A any](instance *Instance[T], action string, handler func(*Context[T], A) Event)

Create a handler for an action using generics (with parsing already implemented)

func DefaultDecodingMiddleware

func DefaultDecodingMiddleware[T any](session *Session[T], instance *Instance[T], bytes []byte) ([]byte, error)

Default pipes-fiber decoding middleware (using JSON)

func DefaultEncodingMiddleware

func DefaultEncodingMiddleware[T any](session *Session[T], instance *Instance[T], message []byte) ([]byte, error)

Default pipes-fiber encoding middleware (using JSON)

func GenerateToken

func GenerateToken(tkLength int32) string

Types

type Adapter

type Adapter struct {
	ID    string      // Identifier of the adapter
	Mutex *sync.Mutex // Mutex to prevent concurrent exceptions (can happen with connections, better handle this on the neogate level)

	// Functions
	OnEvent AdapterFunc
	OnError func(error)
}

type AdapterContext

type AdapterContext struct {
	Event   *Event
	Message []byte
	Adapter *Adapter
}

type AdapterFunc

type AdapterFunc = func(*AdapterContext) error

type AdapterSendError

type AdapterSendError struct {
	AdapterErrors map[string]error // adapterId -> error
}

func (*AdapterSendError) Error

func (err *AdapterSendError) Error() string

type Config

type Config[T any] struct {

	// Called when a client attempts to connect(create a session). Return the session info and true if the connection is allowed.
	// MUST BE SPECIFIED.
	Handshake func(c *fiber.Ctx) (SessionInfo[T], bool)

	// Session handlers
	SessionDisconnectHandler   func(session *Session[T])
	SessionEnterNetworkHandler func(session *Session[T], data T) bool // Called after pipes adapter is registered, returns if the client should be disconnected (true = disconnect)

	// Determines the id of the event adapter for a session.
	// Returns id of user adapter based on session.GetUserId(), and if of session adapter based on session.GetSessionId()
	SessionAdapterHandler func(userId string, sessionId string) (string, string)

	// Codec middleware
	EncodingMiddleware func(session *Session[T], instance *Instance[T], message []byte) ([]byte, error)
	DecodingMiddleware func(session *Session[T], instance *Instance[T], message []byte) ([]byte, error)

	// Error handler
	ErrorHandler func(err error)
}

! If the functions aren't implemented pipesfiber will panic The generic should be the type of the handshake request

type Context

type Context[T any] struct {
	Session    *Session[T]
	Action     string // The action to perform
	ResponseId string
	Data       []byte
	Instance   *Instance[T]
}

type CreateAction

type CreateAction struct {
	ID      string      // Id of the adapter
	OnEvent AdapterFunc // Function that handles events received by the adapter
	OnError func(error) // Function that handles errors encountered by the adapter
}

type Event

type Event struct {
	Name string `json:"name"`
	Data any    `json:"data"`
}

func ErrorResponse

func ErrorResponse[T any](ctx *Context[T], message string, err error) Event

func NormalResponse

func NormalResponse[T any](ctx *Context[T], data any) Event

func Response

func Response[T any](ctx *Context[T], data any) Event

func SuccessResponse

func SuccessResponse[T any](ctx *Context[T]) Event

type Instance

type Instance[T any] struct {
	Config Config[T]
	// contains filtered or unexported fields
}

func Setup

func Setup[T any](config Config[T]) *Instance[T]

Setup neogate using the config. Use the returned *Instance for interfacing with neogate.

func (*Instance[T]) Adapt

func (instance *Instance[T]) Adapt(createAction CreateAction)

Register a new adapter for websocket/sl (all safe protocols)

func (*Instance[T]) AdapterReceive

func (instance *Instance[T]) AdapterReceive(ID string, event Event, msg []byte) error

Handles receiving messages from the target and passes them to the adapter

func (*Instance[T]) DisconnectSession

func (instance *Instance[T]) DisconnectSession(userId string, sessionId string)

DisconnectSession closes/disconnects the session

func (*Instance[T]) ExistsConnection

func (instance *Instance[T]) ExistsConnection(userId string, sessionId string) bool

func (*Instance[T]) Get

func (instance *Instance[T]) Get(userId string, sessionId string) (*Session[T], bool)

func (*Instance[T]) GetConnections

func (instance *Instance[T]) GetConnections(userId string) int

func (*Instance[T]) GetSessions

func (instance *Instance[T]) GetSessions(userId string) []string

func (*Instance[T]) Handle

func (instance *Instance[T]) Handle(ctx *Context[T]) bool

func (*Instance[T]) MountGateway

func (instance *Instance[T]) MountGateway(router fiber.Router)

Mount the neogate gateway using a fiber router.

func (*Instance[T]) RemoveAdapter

func (instance *Instance[T]) RemoveAdapter(ID string)

Remove an adapter from the instance

func (*Instance[T]) RemoveSession

func (instance *Instance[T]) RemoveSession(userId string, sessionId string)

RemoveSession a session from the users sessions (DOES NOT DISCONNECT, there is an extra method for that)

func (*Instance[T]) ReportGeneralError

func (instance *Instance[T]) ReportGeneralError(context string, err error)

func (*Instance[T]) ReportSessionError

func (instance *Instance[T]) ReportSessionError(session *Session[T], context string, err error)

func (*Instance[T]) Send

func (instance *Instance[T]) Send(adapters []string, event Event) error

Send an event to all adapters

func (*Instance[T]) SendEventToSession

func (instance *Instance[T]) SendEventToSession(c *Session[T], event Event) error

Sends an event to a specific Session

func (*Instance[T]) SendEventToUser

func (instance *Instance[T]) SendEventToUser(userId string, event Event) error

SendEventToUser sends the event to all sessions connected to the userId

func (*Instance[T]) SendOne

func (instance *Instance[T]) SendOne(adapter string, event Event) error

Sends an event to the account.

Only returns errors for encoding, not retrieval (cause adapters handle that themselves).

type Message

type Message[T any] struct {
	Action string `json:"action"`
	Data   T      `json:"data"`
}

Message received from the session

type None

type None struct{}

type NormalResponseStruct

type NormalResponseStruct struct {
	Success bool   `json:"success"`
	Message string `json:"message,omitempty"`
}

type Session

type Session[T any] struct {
	// contains filtered or unexported fields
}

func (*Session[T]) GetData

func (session *Session[T]) GetData() T

func (*Session[T]) GetSessionId

func (session *Session[T]) GetSessionId() string

func (*Session[T]) GetUserId

func (session *Session[T]) GetUserId() string

func (*Session[T]) SetData

func (session *Session[T]) SetData(data T)

type SessionCache

type SessionCache struct {
	// contains filtered or unexported fields
}

type SessionInfo

type SessionInfo[T any] struct {
	UserId string // Identifier of the user

	Data T // Session data you can decide how to fill
	// contains filtered or unexported fields
}

Used to provide information for session creation

type SessionsList

type SessionsList struct {
	// contains filtered or unexported fields
}

func (*SessionsList) Add

func (sessionList *SessionsList) Add(sessionId string)

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL