84 lines
2.8 KiB
Go
84 lines
2.8 KiB
Go
package ws
|
|
|
|
import (
|
|
"fmt"
|
|
"time"
|
|
)
|
|
|
|
// SessionConfig bounds connection memory and I/O. Zero fields use defaults;
|
|
// DisableHeartbeat explicitly disables automatic ping/pong deadlines.
|
|
type SessionConfig struct {
|
|
MaxMessageBytes int64 `json:"maxMessageBytes"`
|
|
ReadQueueSize int `json:"readQueueSize"`
|
|
ReadQueueBytes int64 `json:"readQueueBytes"`
|
|
WriteQueueSize int `json:"writeQueueSize"`
|
|
WriteQueueBytes int64 `json:"writeQueueBytes"`
|
|
WriteTimeout time.Duration `json:"writeTimeout"`
|
|
PingInterval time.Duration `json:"pingInterval"`
|
|
PongTimeout time.Duration `json:"pongTimeout"`
|
|
CloseTimeout time.Duration `json:"closeTimeout"`
|
|
DisableHeartbeat bool `json:"disableHeartbeat"`
|
|
}
|
|
|
|
func DefaultSessionConfig() SessionConfig {
|
|
return SessionConfig{MaxMessageBytes: 1 << 20, ReadQueueSize: 64, ReadQueueBytes: 4 << 20,
|
|
WriteQueueSize: 64, WriteQueueBytes: 4 << 20, WriteTimeout: 10 * time.Second,
|
|
PingInterval: 30 * time.Second, PongTimeout: 60 * time.Second, CloseTimeout: 5 * time.Second}
|
|
}
|
|
|
|
func (c SessionConfig) defaults() SessionConfig {
|
|
d := DefaultSessionConfig()
|
|
if c.MaxMessageBytes == 0 {
|
|
c.MaxMessageBytes = d.MaxMessageBytes
|
|
}
|
|
if c.ReadQueueSize == 0 {
|
|
c.ReadQueueSize = d.ReadQueueSize
|
|
}
|
|
if c.ReadQueueBytes == 0 {
|
|
c.ReadQueueBytes = d.ReadQueueBytes
|
|
}
|
|
if c.WriteQueueSize == 0 {
|
|
c.WriteQueueSize = d.WriteQueueSize
|
|
}
|
|
if c.WriteQueueBytes == 0 {
|
|
c.WriteQueueBytes = d.WriteQueueBytes
|
|
}
|
|
if c.WriteTimeout == 0 {
|
|
c.WriteTimeout = d.WriteTimeout
|
|
}
|
|
if c.PingInterval == 0 {
|
|
c.PingInterval = d.PingInterval
|
|
}
|
|
if c.PongTimeout == 0 {
|
|
c.PongTimeout = d.PongTimeout
|
|
}
|
|
if c.CloseTimeout == 0 {
|
|
c.CloseTimeout = d.CloseTimeout
|
|
}
|
|
return c
|
|
}
|
|
|
|
func (c SessionConfig) Validate() error {
|
|
if c.MaxMessageBytes < 0 || c.MaxMessageBytes > 1<<30 || c.ReadQueueSize < 0 || c.ReadQueueSize > 65536 || c.ReadQueueBytes < 0 || c.ReadQueueBytes > 1<<30 || c.WriteQueueSize < 0 || c.WriteQueueSize > 65536 || c.WriteQueueBytes < 0 || c.WriteQueueBytes > 1<<30 {
|
|
return fmt.Errorf("ws: message and queue limits must be nonnegative and bounded")
|
|
}
|
|
if c.WriteTimeout < 0 || c.PingInterval < 0 || c.PongTimeout < 0 || c.CloseTimeout < 0 {
|
|
return fmt.Errorf("ws: timeouts must be nonnegative")
|
|
}
|
|
if c.WriteTimeout > 24*time.Hour || c.PingInterval > 24*time.Hour || c.PongTimeout > 24*time.Hour || c.CloseTimeout > 24*time.Hour {
|
|
return fmt.Errorf("ws: timeout exceeds 24 hours")
|
|
}
|
|
c = c.defaults()
|
|
if !c.DisableHeartbeat && c.PongTimeout <= c.PingInterval {
|
|
return fmt.Errorf("ws: pongTimeout must exceed pingInterval")
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func normalizeSessionConfig(c SessionConfig) (SessionConfig, error) {
|
|
if err := c.Validate(); err != nil {
|
|
return SessionConfig{}, err
|
|
}
|
|
return c.defaults(), nil
|
|
}
|