mirror of
https://github.com/m1k1o/neko.git
synced 2024-07-24 14:40:50 +12:00
implement control protection.
This commit is contained in:
parent
3ee6078256
commit
0f45aa3f19
@ -13,6 +13,7 @@ type Session struct {
|
|||||||
PrivateMode bool
|
PrivateMode bool
|
||||||
LockedLogins bool
|
LockedLogins bool
|
||||||
LockedControls bool
|
LockedControls bool
|
||||||
|
ControlProtection bool
|
||||||
ImplicitHosting bool
|
ImplicitHosting bool
|
||||||
InactiveCursors bool
|
InactiveCursors bool
|
||||||
MercifulReconnect bool
|
MercifulReconnect bool
|
||||||
@ -45,6 +46,11 @@ func (Session) Init(cmd *cobra.Command) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cmd.PersistentFlags().Bool("session.control_protection", false, "users can gain control only if at least one admin is in the room")
|
||||||
|
if err := viper.BindPFlag("session.control_protection", cmd.PersistentFlags().Lookup("session.control_protection")); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
cmd.PersistentFlags().Bool("session.implicit_hosting", true, "allow implicit control switching")
|
cmd.PersistentFlags().Bool("session.implicit_hosting", true, "allow implicit control switching")
|
||||||
if err := viper.BindPFlag("session.implicit_hosting", cmd.PersistentFlags().Lookup("session.implicit_hosting")); err != nil {
|
if err := viper.BindPFlag("session.implicit_hosting", cmd.PersistentFlags().Lookup("session.implicit_hosting")); err != nil {
|
||||||
return err
|
return err
|
||||||
@ -95,6 +101,7 @@ func (s *Session) Set() {
|
|||||||
s.PrivateMode = viper.GetBool("session.private_mode")
|
s.PrivateMode = viper.GetBool("session.private_mode")
|
||||||
s.LockedLogins = viper.GetBool("session.locked_logins")
|
s.LockedLogins = viper.GetBool("session.locked_logins")
|
||||||
s.LockedControls = viper.GetBool("session.locked_controls")
|
s.LockedControls = viper.GetBool("session.locked_controls")
|
||||||
|
s.ControlProtection = viper.GetBool("session.control_protection")
|
||||||
s.ImplicitHosting = viper.GetBool("session.implicit_hosting")
|
s.ImplicitHosting = viper.GetBool("session.implicit_hosting")
|
||||||
s.InactiveCursors = viper.GetBool("session.inactive_cursors")
|
s.InactiveCursors = viper.GetBool("session.inactive_cursors")
|
||||||
s.MercifulReconnect = viper.GetBool("session.merciful_reconnect")
|
s.MercifulReconnect = viper.GetBool("session.merciful_reconnect")
|
||||||
|
@ -21,7 +21,8 @@ func New(config *config.Session) *SessionManagerCtx {
|
|||||||
settings: types.Settings{
|
settings: types.Settings{
|
||||||
PrivateMode: config.PrivateMode,
|
PrivateMode: config.PrivateMode,
|
||||||
LockedLogins: config.LockedLogins,
|
LockedLogins: config.LockedLogins,
|
||||||
LockedControls: config.LockedControls,
|
LockedControls: config.LockedControls || config.ControlProtection,
|
||||||
|
ControlProtection: config.ControlProtection,
|
||||||
ImplicitHosting: config.ImplicitHosting,
|
ImplicitHosting: config.ImplicitHosting,
|
||||||
InactiveCursors: config.InactiveCursors,
|
InactiveCursors: config.InactiveCursors,
|
||||||
MercifulReconnect: config.MercifulReconnect,
|
MercifulReconnect: config.MercifulReconnect,
|
||||||
@ -194,6 +195,17 @@ func (manager *SessionManagerCtx) List() []types.Session {
|
|||||||
return sessions
|
return sessions
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (manager *SessionManagerCtx) Range(f func(session types.Session) bool) {
|
||||||
|
manager.sessionsMu.Lock()
|
||||||
|
defer manager.sessionsMu.Unlock()
|
||||||
|
|
||||||
|
for _, session := range manager.sessions {
|
||||||
|
if !f(session) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// ---
|
// ---
|
||||||
// host
|
// host
|
||||||
// ---
|
// ---
|
||||||
@ -371,6 +383,23 @@ func (manager *SessionManagerCtx) UpdateSettings(new types.Settings) {
|
|||||||
manager.settings = new
|
manager.settings = new
|
||||||
manager.settingsMu.Unlock()
|
manager.settingsMu.Unlock()
|
||||||
|
|
||||||
|
manager.updateSettings(new, old)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (manager *SessionManagerCtx) UpdateSettingsFunc(f func(settings *types.Settings) bool) {
|
||||||
|
manager.settingsMu.Lock()
|
||||||
|
new := manager.settings
|
||||||
|
if f(&new) {
|
||||||
|
old := manager.settings
|
||||||
|
manager.settings = new
|
||||||
|
manager.settingsMu.Unlock()
|
||||||
|
manager.updateSettings(new, old)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
manager.settingsMu.Unlock()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (manager *SessionManagerCtx) updateSettings(new, old types.Settings) {
|
||||||
// if private mode changed
|
// if private mode changed
|
||||||
if old.PrivateMode != new.PrivateMode {
|
if old.PrivateMode != new.PrivateMode {
|
||||||
// update webrtc paused state for all sessions
|
// update webrtc paused state for all sessions
|
||||||
@ -389,6 +418,26 @@ func (manager *SessionManagerCtx) UpdateSettings(new types.Settings) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// if control protection changed and controls are not locked
|
||||||
|
if old.ControlProtection != new.ControlProtection && new.ControlProtection && !new.LockedControls {
|
||||||
|
// if there is no admin, lock controls
|
||||||
|
hasAdmin := false
|
||||||
|
manager.Range(func(session types.Session) bool {
|
||||||
|
if session.Profile().IsAdmin && session.State().IsConnected {
|
||||||
|
hasAdmin = true
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
})
|
||||||
|
|
||||||
|
if !hasAdmin {
|
||||||
|
manager.settingsMu.Lock()
|
||||||
|
manager.settings.LockedControls = true
|
||||||
|
new.LockedControls = true
|
||||||
|
manager.settingsMu.Unlock()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// if contols have been locked
|
// if contols have been locked
|
||||||
if old.LockedControls != new.LockedControls && new.LockedControls {
|
if old.LockedControls != new.LockedControls && new.LockedControls {
|
||||||
// if the host is not admin, it must release controls
|
// if the host is not admin, it must release controls
|
||||||
|
@ -37,6 +37,16 @@ func (h *MessageHandlerCtx) SessionConnected(session types.Session) error {
|
|||||||
if err := h.systemAdmin(session); err != nil {
|
if err := h.systemAdmin(session); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// update settings in atomic way
|
||||||
|
h.sessions.UpdateSettingsFunc(func(settings *types.Settings) bool {
|
||||||
|
// if control protection & locked controls: unlock controls
|
||||||
|
if settings.LockedControls && settings.ControlProtection {
|
||||||
|
settings.LockedControls = false
|
||||||
|
return true // update settings
|
||||||
|
}
|
||||||
|
return false // do not update settings
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
return h.SessionStateChanged(session)
|
return h.SessionStateChanged(session)
|
||||||
@ -49,6 +59,27 @@ func (h *MessageHandlerCtx) SessionDisconnected(session types.Session) error {
|
|||||||
h.sessions.ClearHost()
|
h.sessions.ClearHost()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if session.Profile().IsAdmin {
|
||||||
|
hasAdmin := false
|
||||||
|
h.sessions.Range(func(s types.Session) bool {
|
||||||
|
if s.Profile().IsAdmin && s.ID() != session.ID() && s.State().IsConnected {
|
||||||
|
hasAdmin = true
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
})
|
||||||
|
|
||||||
|
// update settings in atomic way
|
||||||
|
h.sessions.UpdateSettingsFunc(func(settings *types.Settings) bool {
|
||||||
|
// if control protection & not locked controls & no admin: lock controls
|
||||||
|
if !settings.LockedControls && settings.ControlProtection && !hasAdmin {
|
||||||
|
settings.LockedControls = true
|
||||||
|
return true // update settings
|
||||||
|
}
|
||||||
|
return false // do not update settings
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
return h.SessionStateChanged(session)
|
return h.SessionStateChanged(session)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -43,6 +43,7 @@ type Settings struct {
|
|||||||
PrivateMode bool `json:"private_mode"`
|
PrivateMode bool `json:"private_mode"`
|
||||||
LockedLogins bool `json:"locked_logins"`
|
LockedLogins bool `json:"locked_logins"`
|
||||||
LockedControls bool `json:"locked_controls"`
|
LockedControls bool `json:"locked_controls"`
|
||||||
|
ControlProtection bool `json:"control_protection"`
|
||||||
ImplicitHosting bool `json:"implicit_hosting"`
|
ImplicitHosting bool `json:"implicit_hosting"`
|
||||||
InactiveCursors bool `json:"inactive_cursors"`
|
InactiveCursors bool `json:"inactive_cursors"`
|
||||||
MercifulReconnect bool `json:"merciful_reconnect"`
|
MercifulReconnect bool `json:"merciful_reconnect"`
|
||||||
@ -80,6 +81,7 @@ type SessionManager interface {
|
|||||||
Get(id string) (Session, bool)
|
Get(id string) (Session, bool)
|
||||||
GetByToken(token string) (Session, bool)
|
GetByToken(token string) (Session, bool)
|
||||||
List() []Session
|
List() []Session
|
||||||
|
Range(func(Session) bool)
|
||||||
|
|
||||||
SetHost(host Session)
|
SetHost(host Session)
|
||||||
GetHost() (Session, bool)
|
GetHost() (Session, bool)
|
||||||
@ -102,6 +104,7 @@ type SessionManager interface {
|
|||||||
OnSettingsChanged(listener func(new Settings, old Settings))
|
OnSettingsChanged(listener func(new Settings, old Settings))
|
||||||
|
|
||||||
UpdateSettings(Settings)
|
UpdateSettings(Settings)
|
||||||
|
UpdateSettingsFunc(f func(settings *Settings) bool)
|
||||||
Settings() Settings
|
Settings() Settings
|
||||||
CookieEnabled() bool
|
CookieEnabled() bool
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user