Updated OS Manager base methods "loggedIn" and "loggedOut" to be status, so they can be more usable, and finished v3 "notify" method

This commit is contained in:
Adolfo Gómez García 2020-02-06 09:29:38 +01:00
parent 8549f3cfa8
commit ac03d142d9
6 changed files with 44 additions and 41 deletions

View File

@ -227,11 +227,10 @@ class Actor(Handler):
try: try:
if osmanager is None: if osmanager is None:
if message in ('login', 'logout'): if message in ('login', 'logout'):
osm = OSManager(None, None) # Dummy os manager, just for using "logging" capability
if message == 'login': if message == 'login':
osm.loggedIn(service) OSManager.loggedIn(service)
else: else:
osm.loggedOut(service) OSManager.loggedOut(service)
# Mark for removal... # Mark for removal...
service.release() # Release for removal service.release() # Release for removal
return 'ok' return 'ok'

View File

@ -43,6 +43,7 @@ from uds.models import (
#from uds.core import VERSION #from uds.core import VERSION
from uds.core.managers import userServiceManager from uds.core.managers import userServiceManager
from uds.core import osmanagers
from uds.core.util import log, certs from uds.core.util import log, certs
from uds.core.util.state import State from uds.core.util.state import State
from uds.core.util.cache import Cache from uds.core.util.cache import Cache
@ -51,8 +52,7 @@ from uds.core.util.config import GlobalConfig
from ..handlers import Handler, AccessDenied, RequestError from ..handlers import Handler, AccessDenied, RequestError
# Not imported at runtime, just for type checking # Not imported at runtime, just for type checking
if typing.TYPE_CHECKING: # if typing.TYPE_CHECKING:
from uds.core import osmanagers
logger = logging.getLogger(__name__) logger = logging.getLogger(__name__)
@ -239,7 +239,6 @@ class Initiialize(ActorV3Action):
except ActorToken.DoesNotExist: except ActorToken.DoesNotExist:
raise BlockAccess() raise BlockAccess()
class ChangeIp(ActorV3Action): class ChangeIp(ActorV3Action):
""" """
Records the IP change of actor Records the IP change of actor
@ -324,11 +323,12 @@ class Login(ActorV3Action):
def action(self) -> typing.MutableMapping[str, typing.Any]: def action(self) -> typing.MutableMapping[str, typing.Any]:
logger.debug('Login Args: %s, Params: %s', self._args, self._params) logger.debug('Login Args: %s, Params: %s', self._args, self._params)
userService = self.getUserService() userService = self.getUserService()
osManager = userService.getOsManagerInstance() osManager: typing.Optional[osmanagers.OSManager] = userService.getOsManagerInstance()
if osManager:
if not userService.in_use: # If already logged in, do not add a second login (windows does this i.e.) if not userService.in_use: # If already logged in, do not add a second login (windows does this i.e.)
osManager.loggedIn(userService, self._params.get('username') or '') osmanagers.OSManager.loggedIn(userService, self._params.get('username') or '')
maxIdle = osManager.maxIdle()
maxIdle = osManager.maxIdle() if osManager else None
logger.debug('Max idle: %s', maxIdle) logger.debug('Max idle: %s', maxIdle)
ip, hostname = userService.getConnectionSource() ip, hostname = userService.getConnectionSource()
@ -349,9 +349,10 @@ class Logout(ActorV3Action):
def action(self) -> typing.MutableMapping[str, typing.Any]: def action(self) -> typing.MutableMapping[str, typing.Any]:
logger.debug('Args: %s, Params: %s', self._args, self._params) logger.debug('Args: %s, Params: %s', self._args, self._params)
userService = self.getUserService() userService = self.getUserService()
osManager = userService.getOsManagerInstance() osManager: typing.Optional[osmanagers.OSManager] = userService.getOsManagerInstance()
if osManager and userService.in_use: # If already logged out, do not add a second logout (windows does this i.e.) if userService.in_use: # If already logged out, do not add a second logout (windows does this i.e.)
osManager.loggedOut(userService, self._params.get('username') or '') osmanagers.OSManager.loggedOut(userService, self._params.get('username') or '')
if osManager:
if osManager.isRemovableOnLogout(userService): if osManager.isRemovableOnLogout(userService):
logger.debug('Removable on logout: %s', osManager) logger.debug('Removable on logout: %s', osManager)
userService.remove() userService.remove()
@ -407,8 +408,10 @@ class Notify(ActorV3Action):
try: try:
# Check block manually # Check block manually
checkBlockedIp(self._request.ip) # pylint: disable=protected-access checkBlockedIp(self._request.ip) # pylint: disable=protected-access
userService = UserService.objects.get(uuid=self._params['token']) if 'action' == 'login':
# TODO: finish this when needed :) Login.action(typing.cast(Login, self))
else:
Logout.action(typing.cast(Logout, self))
return ActorV3Action.actorResult('ok') return ActorV3Action.actorResult('ok')
except UserService.DoesNotExist: except UserService.DoesNotExist:

View File

@ -68,9 +68,9 @@ class SimpleLDAPAuthenticator(auths.Authenticator):
groupIdAttr = gui.TextField(length=64, label=_('Group Id Attr'), defvalue='cn', order=12, tooltip=_('Attribute that contains the group id'), required=True, tab=_('Ldap info')) groupIdAttr = gui.TextField(length=64, label=_('Group Id Attr'), defvalue='cn', order=12, tooltip=_('Attribute that contains the group id'), required=True, tab=_('Ldap info'))
memberAttr = gui.TextField(length=64, label=_('Group membership attr'), defvalue='memberUid', order=13, tooltip=_('Attribute of the group that contains the users belonging to it'), required=True, tab=_('Ldap info')) memberAttr = gui.TextField(length=64, label=_('Group membership attr'), defvalue='memberUid', order=13, tooltip=_('Attribute of the group that contains the users belonging to it'), required=True, tab=_('Ldap info'))
typeName = _('SimpleLDAP Authenticator') typeName = _('SimpleLDAP (DEPRECATED)')
typeType = 'SimpleLdapAuthenticator' typeType = 'SimpleLdapAuthenticator'
typeDescription = _('Simple LDAP authenticator') typeDescription = _('Simple LDAP authenticator (DEPRECATED)')
iconFile = 'auth.png' iconFile = 'auth.png'
# If it has and external source where to get "new" users (groups must be declared inside UDS) # If it has and external source where to get "new" users (groups must be declared inside UDS)
@ -267,7 +267,7 @@ class SimpleLDAPAuthenticator(auths.Authenticator):
''' '''
res = self.__getUser(usrData['name']) res = self.__getUser(usrData['name'])
if res is None: if res is None:
raise auths.AuthenticatorException(_('Username not found')) raise auths.exceptions.AuthenticatorException(_('Username not found'))
# Fills back realName field # Fills back realName field
usrData['real_name'] = self.__getUserRealName(res) usrData['real_name'] = self.__getUserRealName(res)
@ -300,7 +300,7 @@ class SimpleLDAPAuthenticator(auths.Authenticator):
''' '''
res = self.__getGroup(groupData['name']) res = self.__getGroup(groupData['name'])
if res is None: if res is None:
raise auths.AuthenticatorException(_('Group not found')) raise auths.exceptions.AuthenticatorException(_('Group not found'))
def getGroups(self, username: str, groupsManager: 'auths.GroupsManager'): def getGroups(self, username: str, groupsManager: 'auths.GroupsManager'):
''' '''
@ -310,7 +310,7 @@ class SimpleLDAPAuthenticator(auths.Authenticator):
''' '''
user = self.__getUser(username) user = self.__getUser(username)
if user is None: if user is None:
raise auths.AuthenticatorException(_('Username not found')) raise auths.exceptions.AuthenticatorException(_('Username not found'))
groupsManager.validate(self.__getGroups(user)) groupsManager.validate(self.__getGroups(user))
def searchUsers(self, pattern: str) -> typing.Iterable[typing.Dict[str, str]]: def searchUsers(self, pattern: str) -> typing.Iterable[typing.Dict[str, str]]:
@ -331,7 +331,7 @@ class SimpleLDAPAuthenticator(auths.Authenticator):
return res return res
except Exception: except Exception:
logger.exception("Exception: ") logger.exception("Exception: ")
raise auths.AuthenticatorException(_('Too many results, be more specific')) raise auths.exceptions.AuthenticatorException(_('Too many results, be more specific'))
def searchGroups(self, pattern: str) -> typing.Iterable[typing.Dict[str, str]]: def searchGroups(self, pattern: str) -> typing.Iterable[typing.Dict[str, str]]:
try: try:
@ -351,7 +351,7 @@ class SimpleLDAPAuthenticator(auths.Authenticator):
return res return res
except Exception: except Exception:
logger.exception("Exception: ") logger.exception("Exception: ")
raise auths.AuthenticatorException(_('Too many results, be more specific')) raise auths.exceptions.AuthenticatorException(_('Too many results, be more specific'))
@staticmethod @staticmethod
def test(env, data): def test(env, data):

View File

@ -210,7 +210,8 @@ class OSManager(Module):
''' '''
userService.setProperty('loginsCounter', '0') userService.setProperty('loginsCounter', '0')
def loggedIn(self, userService: 'UserService', userName: typing.Optional[str] = None) -> None: @staticmethod
def loggedIn(userService: 'UserService', userName: typing.Optional[str] = None) -> None:
""" """
This method: This method:
- Add log in event to stats - Add log in event to stats
@ -241,8 +242,8 @@ class OSManager(Module):
counter = int(typing.cast(str, userService.getProperty('loginsCounter', '0'))) + 1 counter = int(typing.cast(str, userService.getProperty('loginsCounter', '0'))) + 1
userService.setProperty('loginsCounter', str(counter)) userService.setProperty('loginsCounter', str(counter))
@staticmethod
def loggedOut(self, userService: 'UserService', userName: typing.Optional[str] = None) -> None: def loggedOut(userService: 'UserService', userName: typing.Optional[str] = None) -> None:
""" """
This method: This method:
- Add log in event to stats - Add log in event to stats
@ -281,10 +282,10 @@ class OSManager(Module):
log.useLog('logout', uniqueId, serviceIp, userName, knownUserIP, fullUserName, userService.friendly_name, userService.deployed_service.name) log.useLog('logout', uniqueId, serviceIp, userName, knownUserIP, fullUserName, userService.friendly_name, userService.deployed_service.name)
def loginNotified(self, userService: 'UserService', userName: typing.Optional[str] = None) -> None: def loginNotified(self, userService: 'UserService', userName: typing.Optional[str] = None) -> None:
self.loggedIn(userService, userName) OSManager.loggedIn(userService, userName)
def logoutNotified(self, userService: 'UserService', userName: typing.Optional[str] = None) -> None: def logoutNotified(self, userService: 'UserService', userName: typing.Optional[str] = None) -> None:
self.loggedOut(userService, userName) OSManager.loggedOut(userService, userName)
def readyNotified(self, userService: 'UserService') -> None: def readyNotified(self, userService: 'UserService') -> None:
""" """

View File

@ -149,10 +149,10 @@ class LinuxOsManager(osmanagers.OSManager):
def loginNotified(self, userService, userName=None): def loginNotified(self, userService, userName=None):
if '\\' not in userName: if '\\' not in userName:
self.loggedIn(userService, userName) osmanagers.OSManager.loggedIn(userService, userName)
def logoutNotified(self, userService, userName=None): def logoutNotified(self, userService, userName=None):
self.loggedOut(userService, userName) osmanagers.OSManager.loggedOut(userService, userName)
if self.isRemovableOnLogout(userService): if self.isRemovableOnLogout(userService):
userService.release() userService.release()
@ -197,12 +197,12 @@ class LinuxOsManager(osmanagers.OSManager):
elif message == "log": elif message == "log":
self.doLog(userService, data, log.ACTOR) self.doLog(userService, data, log.ACTOR)
elif message == "login": elif message == "login":
self.loggedIn(userService, data) osmanagers.OSManager.loggedIn(userService, data)
ip, hostname = userService.getConnectionSource() ip, hostname = userService.getConnectionSource()
deadLine = userService.deployed_service.getDeadline() deadLine = userService.deployed_service.getDeadline()
ret = "{}\t{}\t{}".format(ip, hostname, 0 if deadLine is None else deadLine) ret = "{}\t{}\t{}".format(ip, hostname, 0 if deadLine is None else deadLine)
elif message == "logout": elif message == "logout":
self.loggedOut(userService, data) osmanagers.OSManager.loggedOut(userService, data)
doRemove = self.isRemovableOnLogout(userService) doRemove = self.isRemovableOnLogout(userService)
elif message == "ip": elif message == "ip":
# This ocurss on main loop inside machine, so userService is usable # This ocurss on main loop inside machine, so userService is usable

View File

@ -152,10 +152,10 @@ class WindowsOsManager(osmanagers.OSManager):
def loginNotified(self, userService, userName=None): def loginNotified(self, userService, userName=None):
if '\\' not in userName: if '\\' not in userName:
self.loggedIn(userService, userName) osmanagers.OSManager.loggedIn(userService, userName)
def logoutNotified(self, userService, userName=None): def logoutNotified(self, userService, userName=None):
self.loggedOut(userService, userName) osmanagers.OSManager.loggedOut(userService, userName)
if self.isRemovableOnLogout(userService): if self.isRemovableOnLogout(userService):
userService.release() userService.release()
@ -200,7 +200,7 @@ class WindowsOsManager(osmanagers.OSManager):
self.doLog(userService, data, log.ACTOR) self.doLog(userService, data, log.ACTOR)
elif message in("logon", 'login'): elif message in("logon", 'login'):
if '\\' not in data: if '\\' not in data:
self.loggedIn(userService, data) osmanagers.OSManager.loggedIn(userService, data)
userService.setInUse(True) userService.setInUse(True)
# We get the userService logged hostname & ip and returns this # We get the userService logged hostname & ip and returns this
ip, hostname = userService.getConnectionSource() ip, hostname = userService.getConnectionSource()
@ -210,7 +210,7 @@ class WindowsOsManager(osmanagers.OSManager):
else: else:
ret = "{0}\t{1}".format(ip, hostname) ret = "{0}\t{1}".format(ip, hostname)
elif message in ('logoff', 'logout'): elif message in ('logoff', 'logout'):
self.loggedOut(userService, data) osmanagers.OSManager.loggedOut(userService, data)
doRemove = self.isRemovableOnLogout(userService) doRemove = self.isRemovableOnLogout(userService)
elif message == "ip": elif message == "ip":
# This ocurss on main loop inside machine, so userService is usable # This ocurss on main loop inside machine, so userService is usable
@ -253,7 +253,7 @@ class WindowsOsManager(osmanagers.OSManager):
'password': password, 'password': password,
'domain': domain 'domain': domain
} }
ticket = TicketStore.create(creds, validator=None, validity=300) # , owner=SECURE_OWNER, secure=True) ticket = TicketStore.create(creds, validatorFnc=None, validity=300) # , owner=SECURE_OWNER, secure=True)
return ticket, '' return ticket, ''
return osmanagers.OSManager.processUserPassword(self, userService, username, password) return osmanagers.OSManager.processUserPassword(self, userService, username, password)