diff --git a/actors/src/udsactor/linux/store.py b/actors/src/udsactor/linux/store.py index dd5e6efec..a6d12da30 100644 --- a/actors/src/udsactor/linux/store.py +++ b/actors/src/udsactor/linux/store.py @@ -81,3 +81,8 @@ def writeConfig(data): def useOldJoinSystem(): return False + +# Right now, we do not really need an application to be run on "startup" as could ocur with windows +def runApplication(): + return None + diff --git a/actors/src/udsactor/service.py b/actors/src/udsactor/service.py index 9e6069975..e6ab9cf3e 100644 --- a/actors/src/udsactor/service.py +++ b/actors/src/udsactor/service.py @@ -87,8 +87,25 @@ class CommonService(object): def reboot(self): self.rebootRequested = True - def setReady(self, hostName=None): - self.api.setReady([(v.mac, v.ip) for v in operations.getNetworkInfo()], hostName) + def execute(self, cmd, section): + import os + import subprocess + import stat + + if os.path.isfile(cmd): + if (os.stat(cmd).st_mode & stat.S_IXUSR) != 0: + subprocess.call([cmd, ]) + return True + else: + logger.info('{} file exists but it it is not executable (needs execution permission by admin/root)'.format(section)) + else: + logger.info('{} file not found & not executed'.format(section)) + + return False + + + def setReady(self): + self.api.setReady([(v.mac, v.ip) for v in operations.getNetworkInfo()]) def interactWithBroker(self): ''' @@ -139,6 +156,13 @@ class CommonService(object): # Wait a bit before next check self.doWait(5000) + # Now try to run the "runonce" element + runOnce = store.runApplication() + if runOnce is not None: + if self.execute(runOnce, 'RunOnce') is True: + # operations.reboot() + return False + # Broker connection is initialized, now get information about what to # do counter = 0 diff --git a/actors/src/udsactor/windows/UDSActorService.py b/actors/src/udsactor/windows/UDSActorService.py index 857ae2142..9d7ec048d 100644 --- a/actors/src/udsactor/windows/UDSActorService.py +++ b/actors/src/udsactor/windows/UDSActorService.py @@ -57,7 +57,7 @@ from .SENS import SENSGUID_PUBLISHER from .SENS import PROGID_EventSubscription from .SENS import PROGID_EventSystem -POST_CMD = 'c:\\windows\post-uds.bat' +POST_CMD = 'c:\\windows\\post-uds.bat' class UDSActorSvc(win32serviceutil.ServiceFramework, CommonService): diff --git a/actors/src/udsactor/windows/store.py b/actors/src/udsactor/windows/store.py index 08c54d4f1..1d8829fe7 100644 --- a/actors/src/udsactor/windows/store.py +++ b/actors/src/udsactor/windows/store.py @@ -105,3 +105,19 @@ def useOldJoinSystem(): data = '' return data == 'old' + +# Gives the oportunity to run an application ONE TIME (because, the registry key "run" will be deleted after read) +def runApplication(): + try: + key = wreg.OpenKey(baseKey, 'Software\\UDSEnterpriseActor', 0, wreg.KEY_ALL_ACCESS) # @UndefinedVariable + try: + data, _ = wreg.QueryValueEx(key, 'run') # @UndefinedVariable + wreg.DeleteValue(key, 'run') # @UndefinedVariable + except Exception: + data = None + wreg.CloseKey(key) # @UndefinedVariable + except: + data = None + + return data + diff --git a/server/samples/REST1.py b/server/samples/REST1.py index 1b79f763f..2c2f4f82e 100644 --- a/server/samples/REST1.py +++ b/server/samples/REST1.py @@ -112,8 +112,8 @@ def request_service_info(provider_id, service_id): resp, content = h.request(rest_url + 'providers/{0}/services/{1}'.format(provider_id, service_id), headers=headers) if resp['status'] != '200': # error due to incorrect parameters, bad request, etc... - print "Error requesting pools" - return {} + print "Error requesting pools: response: {}, content: {}".format(resp, content) + return None return json.loads(content) @@ -125,14 +125,17 @@ if __name__ == '__main__': print res for r in res: res2 = request_service_info(r['provider_id'], r['service_id']) - print "Base Service info por pool {0}: {1}".format(r['name'], res2) + if res2 is not None: + print "Base Service info por pool {0}: {1}".format(r['name'], res2['type']) + else: + print "Base service {} is not accesible".format(r['name']) print "First logout" print logout() # This will success print "Second logout" print logout() # This will fail (already logged out) # Also new requests will fail print request_pools() - # Untin we do log in again + # Until we do log in again login() print request_pools() diff --git a/server/samples/REST3.py b/server/samples/REST3.py new file mode 100644 index 000000000..eecedf37b --- /dev/null +++ b/server/samples/REST3.py @@ -0,0 +1,279 @@ +# -*- coding: utf-8 -*- + +# +# Copyright (c) 2014 Virtual Cable S.L. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above copyright notice, +# this list of conditions and the following disclaimer in the documentation +# and/or other materials provided with the distribution. +# * Neither the name of Virtual Cable S.L. nor the names of its contributors +# may be used to endorse or promote products derived from this software +# without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +''' +@author: Adolfo Gómez, dkmaster at dkmon dot com +''' + +from __future__ import unicode_literals + +from httplib2 import Http +import json +import sys + +rest_url = 'http://172.27.0.1:8000/rest/' + + + +headers = {} + +# Hace login con el root, puede usarse cualquier autenticador y cualquier usuario, pero en la 1.5 solo está implementado poder hacer +# este tipo de login con el usuario "root" +def login(): + global headers + h = Http() + + # parameters = '{ "auth": "admin", "username": "root", "password": "temporal" }' + parameters = '{ "auth": "interna", "username": "admin", "password": "temporal" }' + + resp, content = h.request(rest_url + 'auth/login', method='POST', body=parameters) + + if resp['status'] != '200': # Authentication error due to incorrect parameters, bad request, etc... + print "Authentication error" + return -1 + + # resp contiene las cabeceras, content el contenido de la respuesta (que es json), pero aún está en formato texto + res = json.loads(content) + print "Authentication response: {}".format(res) + if res['result'] != 'ok': # Authentication error + print "Authentication error" + sys.exit(1) + + headers['X-Auth-Token'] = res['token'] + headers['content-type'] = 'application/json' + + return 0 + +def logout(): + global headers + h = Http() + + resp, content = h.request(rest_url + 'auth/logout', headers=headers) + + if resp['status'] != '200': # Logout error due to incorrect parameters, bad request, etc... + print "Error requesting logout" + return -1 + + # Return value of logout method is nonsense (returns always done right now, but it's not important) + + return 0 + +def list_supported_auths_and_fields(): + h = Http() + + resp, content = h.request(rest_url + 'authenticators/types', headers=headers) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + r = json.loads(content) + + for auth in r: # r is an array + print '* {}'.format(auth['name']) + for fld in auth: # every auth is converted to a dictionary in python by json.load + # Skip icon + if fld != 'icon': + print " > {}: {}".format(fld, auth[fld]) + resp, content = h.request(rest_url + 'authenticators/gui/{}'.format(auth['type']), headers=headers) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + print " > GUI" + rr = json.loads(content) + for field in rr: + print " - Name: {}".format(field['name']) + print " - Value: {}".format(field['value']) + print " - GUI: " + for gui in field['gui']: + print " + {}: {}".format(gui, field['gui'][gui]) + print " > Simplified fields:" + for field in rr: + print " - Name: {}, Type: {}, is Required?: {}".format(field['name'], field['gui']['type'], field['gui']['required']) + +def create_simpleldap_auth(): + h = Http() + + # Keep in mind that parameters are related to kind of authenticator. + # To ensure what parameters you need, yo can invoke first its gui + # Take a look at list_supported_auths_and_fields method + data = {"tags":["Tag1","Tag2","Tag3"],"name":"name_Field","comments":"comments__Field","priority":"1","small_name":"label_Field","host":"host_Field","port":"389","ssl":False,"timeout":"10","username":"username__Field","password":"password_Field","ldapBase":"base_Field","userClass":"userClass_Field","userIdAttr":"userIdAttr_Field","userNameAttr":"userName_Field","groupClass":"groupClass_Field","groupIdAttr":"groupId_Field","memberAttr":"groupMembership_Field","data_type":"SimpleLdapAuthenticator"} + resp, content = h.request(rest_url + 'authenticators','PUT', headers=headers, body=json.dumps(data)) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + # Expected content is something like this: + # { + # "numeric_id": 18, + # "groupIdAttr": "groupId_Field", + # "port": "389", + # "memberAttr": "groupMembership_Field", + # "id": "790b9d85-67ec-51dc-847f-dee1daa96a7c", + # "userClass": "userClass_Field", + # "permission": 96, + # "comments": "comments__Field", + # "users_count": 0, + # "priority": "1", + # "type": "SimpleLdapAuthenticator", + # "username": "username__Field", + # "ldapBase": "base_Field", "userNameAttr": + # "userName_Field", + # "tags": ["Tag1", "Tag2", "Tag3"], + # "groupClass": "groupClass_Field", + # "ssl": false, + # "host": "host_Field", + # "userIdAttr": "userIdAttr_Field", + # "password": "password_Field", + # "small_name": "label_Field", + # "name": "name_Field", + # "timeout": "10" + # } + r = json.loads(content) + print "Correctly created {} with id {}".format(r['name'], r['id']) + print "The record created was: {}".format(r) + return r + +def delete_auth(auth_id): + h = Http() + + # Sample delete URL for an auth + # http://172.27.0.1:8000/rest/authenticators/790b9d85-67ec-51dc-847f-dee1daa96a7c + # Method MUST be DELETE + resp, content = h.request(rest_url + 'authenticators/{}'.format(auth_id), 'DELETE', headers=headers) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + print "Correctly deleted {}".format(auth_id) + +def create_internal_auth(): + h = Http() + + data = {"tags":[""],"name":"name_Field","comments":"comments_Field","priority":"1","small_name":"label_Field","differentForEachHost":False,"reverseDns":False,"acceptProxy":False,"data_type":"InternalDBAuth"} + resp, content = h.request(rest_url + 'authenticators','PUT', headers=headers, body=json.dumps(data)) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + r = json.loads(content) + print "Correctly created {} with id {}".format(r['name'], r['id']) + print "The record created was: {}".format(r) + return r + +def create_internal_group(auth_id): + h = Http() + + # Type can also be a metagroup, composed of groups, but for this sample a group is enoutgh + data = {"type":"group","name":"groupname_Field","comments":"comments_Field","state":"A"} + resp, content = h.request(rest_url + 'authenticators/{}/groups'.format(auth_id),'PUT', headers=headers, body=json.dumps(data)) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + r = json.loads(content) + print "Correctly created {} with id {}".format(r['name'], r['id']) + print "The record created was: {}".format(r) + return r + +def delete_group(auth_id, group_id): + h = Http() + + # Method MUST be DELETE + resp, content = h.request(rest_url + 'authenticators/{}/groups/{}'.format(auth_id, group_id), 'DELETE', headers=headers) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + print "Correctly deleted {}".format(auth_id) + + +def create_internal_user(auth_id, group_id): + # Note: internal users NEEDS to store password on UDS, description of auth describes if password field is needed (in this case, we need it) + # Also, if authenticator is marked as "external" on its description, the groups field will be ignored. + # On internal auths, we can incluide de ID of the groups we want this user to belong to, or it will not belong to any group + h = Http() + + data = {"id":"","name":"username_Field","real_name":"name_Field","comments":"comments_Field","state":"A","staff_member":False, "is_admin":False,"password":"password_Field","groups":[group_id]} + + resp, content = h.request(rest_url + 'authenticators/{}/users'.format(auth_id),'PUT', headers=headers, body=json.dumps(data)) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + r = json.loads(content) + print "Correctly created {} with id {}".format(r['name'], r['id']) + print "The record created was: {}".format(r) + return r + +def delete_user(auth_id, user_id): + # Deleting user will result in deleting in cascade all asigned resources (machines, apps, etc...) + + h = Http() + + # Method MUST be DELETE + resp, content = h.request(rest_url + 'authenticators/{}/users/{}'.format(auth_id, user_id), 'DELETE', headers=headers) + if resp['status'] != '200': + print "Error in request: \n-------------------\n{}\n{}\n----------------".format(resp, content) + sys.exit(1) + + print "Correctly deleted {}".format(auth_id) + +def list_currents_auths(): + pass + +if __name__ == '__main__': + if login() == 0: # If we can log in, will get the pools correctly + print "Listing supported auths and related info" + list_supported_auths_and_fields() + print "*******************************" + print "Creating a simple ldap authenticator" + auth = create_simpleldap_auth() + print "*******************************" + print "Deleting the created simple ldap authenticator" + delete_auth(auth['id']) + print "*******************************" + print "Creating internal auth" + auth = create_internal_auth() + print "*******************************" + print "Creating internal group" + print "*******************************" + group = create_internal_group(auth['id']) + print "Creating internal user" + print "*******************************" + user = create_internal_user(auth['id'], group['id']) + print "*******************************" + print "Deleting user" + delete_user(auth['id'], user['id']) + print "*******************************" + print "Deleting Group" + delete_group(auth['id'], group['id']) + print "*******************************" + print "Deleting the created internal auth" + delete_auth(auth['id']) diff --git a/server/samples/sample_output_REST3.txt b/server/samples/sample_output_REST3.txt new file mode 100644 index 000000000..586b8ae6b --- /dev/null +++ b/server/samples/sample_output_REST3.txt @@ -0,0 +1,1494 @@ +Authentication response: {u'token': u'xlm22vchla3eao2t2w9chdeqx2ta9enr', u'result': u'ok'} +Listing supported auths and related info +* SAML Authenticator + > canCreateUsers: False + > name: SAML Authenticator + > passwordLabel: Password + > type: SAML20Authenticator + > description: SAML (v2.0) Authenticator + > userNameLabel: User + > canSearchUsers: False + > canSearchGroups: False + > groupNameLabel: Group + > needsPassword: False + > isExternal: True + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: manageUrl + - Value: + - GUI: + + required: False + + defvalue: + + value: + + label: + + length: 32 + + tooltip: + + rdonly: False + + type: hidden + + order: 0 + - Name: privateKey + - Value: + - GUI: + + tab: Certificates + + required: True + + defvalue: + + tooltip: Private key used for sign and encription, as generated in base 64 from openssl + + label: Private key + + length: 4096 + + multiline: 8 + + value: + + rdonly: False + + type: text + + order: 1 + - Name: serverCertificate + - Value: + - GUI: + + tab: Certificates + + required: True + + defvalue: + + tooltip: Public key used for sign and encription (public part of previous private key), as generated in base 64 from openssl + + label: Certificate + + length: 4096 + + multiline: 8 + + value: + + rdonly: False + + type: text + + order: 2 + - Name: idpMetadata + - Value: + - GUI: + + tab: Metadata + + required: True + + defvalue: + + tooltip: You can enter here the URL or the IDP metadata or the metadata itself (xml) + + label: IDP Metadata + + length: 8192 + + multiline: 4 + + value: + + rdonly: False + + type: text + + order: 3 + - Name: entityID + - Value: + - GUI: + + tab: Metadata + + required: False + + defvalue: + + tooltip: ID of the SP. If left blank, this will be autogenerated from server URL + + label: Entity ID + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 4 + - Name: userNameAttr + - Value: + - GUI: + + tab: Attributes + + required: True + + defvalue: + + tooltip: Fields from where to extract user name + + label: User name attrs + + length: 2048 + + multiline: 2 + + value: + + rdonly: False + + type: text + + order: 5 + - Name: groupNameAttr + - Value: + - GUI: + + tab: Attributes + + required: True + + defvalue: + + tooltip: Fields from where to extract the groups + + label: Group name attrs + + length: 2048 + + multiline: 2 + + value: + + rdonly: False + + type: text + + order: 6 + - Name: realNameAttr + - Value: + - GUI: + + tab: Attributes + + required: True + + defvalue: + + tooltip: Fields from where to extract the real name + + label: Real name attrs + + length: 2048 + + multiline: 2 + + value: + + rdonly: False + + type: text + + order: 7 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: manageUrl, Type: hidden, is Required?: False + - Name: privateKey, Type: text, is Required?: True + - Name: serverCertificate, Type: text, is Required?: True + - Name: idpMetadata, Type: text, is Required?: True + - Name: entityID, Type: text, is Required?: False + - Name: userNameAttr, Type: text, is Required?: True + - Name: groupNameAttr, Type: text, is Required?: True + - Name: realNameAttr, Type: text, is Required?: True +* SimpleLDAP Authenticator + > canCreateUsers: True + > name: SimpleLDAP Authenticator + > passwordLabel: Password + > type: SimpleLdapAuthenticator + > description: Simple LDAP authenticator + > userNameLabel: Username + > canSearchUsers: True + > canSearchGroups: True + > groupNameLabel: Group + > needsPassword: False + > isExternal: True + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: host + - Value: + - GUI: + + required: True + + defvalue: + + value: + + label: Host + + length: 64 + + multiline: 0 + + tooltip: Ldap Server IP or Hostname + + rdonly: False + + type: text + + order: 1 + - Name: port + - Value: + - GUI: + + required: True + + defvalue: 389 + + maxValue: 987654321 + + tooltip: Ldap port (usually 389 for non ssl and 636 for ssl) + + minValue: 987654321 + + length: 5 + + value: + + rdonly: False + + label: Port + + type: numeric + + order: 2 + - Name: ssl + - Value: + - GUI: + + required: False + + defvalue: + + value: + + label: Use SSL + + length: 32 + + tooltip: If checked, the connection will be ssl, using port 636 instead of 389 + + rdonly: False + + type: checkbox + + order: 3 + - Name: username + - Value: + - GUI: + + tab: Credentials + + required: True + + defvalue: + + tooltip: Username with read privileges on the base selected + + label: Ldap User + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 4 + - Name: password + - Value: + - GUI: + + rdonly: False + + required: True + + defvalue: + + value: + + label: Password + + length: 32 + + tooltip: Password of the ldap user + + tab: Credentials + + type: password + + order: 5 + - Name: timeout + - Value: + - GUI: + + required: True + + defvalue: 10 + + maxValue: 987654321 + + tooltip: Timeout in seconds of connection to LDAP + + minValue: 1 + + length: 3 + + value: + + rdonly: False + + label: Timeout + + type: numeric + + order: 6 + - Name: ldapBase + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: + + tooltip: Common search base (used for "users" and "groups") + + label: Base + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 7 + - Name: userClass + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: posixAccount + + tooltip: Class for LDAP users (normally posixAccount) + + label: User class + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 8 + - Name: userIdAttr + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: uid + + tooltip: Attribute that contains the user id + + label: User Id Attr + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 9 + - Name: userNameAttr + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: uid + + tooltip: Attributes that contains the user name (list of comma separated values) + + label: User Name Attr + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 10 + - Name: groupClass + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: posixGroup + + tooltip: Class for LDAP groups (normally poxisGroup) + + label: Group class + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 11 + - Name: groupIdAttr + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: cn + + tooltip: Attribute that contains the group id + + label: Group Id Attr + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 12 + - Name: memberAttr + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: memberUid + + tooltip: Attribute of the group that contains the users belonging to it + + label: Group membership attr + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 13 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: host, Type: text, is Required?: True + - Name: port, Type: numeric, is Required?: True + - Name: ssl, Type: checkbox, is Required?: False + - Name: username, Type: text, is Required?: True + - Name: password, Type: password, is Required?: True + - Name: timeout, Type: numeric, is Required?: True + - Name: ldapBase, Type: text, is Required?: True + - Name: userClass, Type: text, is Required?: True + - Name: userIdAttr, Type: text, is Required?: True + - Name: userNameAttr, Type: text, is Required?: True + - Name: groupClass, Type: text, is Required?: True + - Name: groupIdAttr, Type: text, is Required?: True + - Name: memberAttr, Type: text, is Required?: True +* Sample Authenticator + > canCreateUsers: True + > name: Sample Authenticator + > passwordLabel: Password + > type: SampleAuthenticator + > description: Sample dummy authenticator + > userNameLabel: Fake User + > canSearchUsers: True + > canSearchGroups: True + > groupNameLabel: Fake Group + > needsPassword: False + > isExternal: True + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: groups + - Value: + - GUI: + + required: False + + defvalue: + + value: + + label: Groups + + length: 32 + + values: [u'Gods', u'Daemons', u'Mortals'] + + tooltip: + + rdonly: False + + type: editlist + + order: 0 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: groups, Type: editlist, is Required?: False +* IP Authenticator + > canCreateUsers: False + > name: IP Authenticator + > passwordLabel: Password + > type: IPAuth + > description: IP Authenticator + > userNameLabel: IP + > canSearchUsers: False + > canSearchGroups: False + > groupNameLabel: IP Range + > needsPassword: False + > isExternal: True + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: acceptProxy + - Value: + - GUI: + + rdonly: False + + required: False + + defvalue: + + value: + + label: Accept proxy + + length: 32 + + tooltip: If checked, requests via proxy will get FORWARDED ip address (take care with this bein checked, can take internal IP addresses from internet) + + tab: Advanced + + type: checkbox + + order: 3 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: acceptProxy, Type: checkbox, is Required?: False +* Internal Database + > canCreateUsers: True + > name: Internal Database + > passwordLabel: Password + > type: InternalDBAuth + > description: Internal dabasase authenticator. Doesn't use external sources + > userNameLabel: User name + > canSearchUsers: False + > canSearchGroups: False + > groupNameLabel: Group name + > needsPassword: True + > isExternal: False + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: differentForEachHost + - Value: + - GUI: + + rdonly: True + + required: False + + defvalue: false + + value: + + label: Different user for each host + + length: 32 + + tooltip: If checked, each host will have a different user name + + tab: Advanced + + type: checkbox + + order: 1 + - Name: reverseDns + - Value: + - GUI: + + rdonly: True + + required: False + + defvalue: false + + value: + + label: Reverse DNS + + length: 32 + + tooltip: If checked, the host will be reversed dns + + tab: Advanced + + type: checkbox + + order: 2 + - Name: acceptProxy + - Value: + - GUI: + + rdonly: False + + required: False + + defvalue: + + value: + + label: Accept proxy + + length: 32 + + tooltip: If checked, requests via proxy will get FORWARDED ip address (take care with this bein checked, can take internal IP addresses from internet) + + tab: Advanced + + type: checkbox + + order: 3 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: differentForEachHost, Type: checkbox, is Required?: False + - Name: reverseDns, Type: checkbox, is Required?: False + - Name: acceptProxy, Type: checkbox, is Required?: False +* Active Directory Authenticator + > canCreateUsers: True + > name: Active Directory Authenticator + > passwordLabel: Password + > type: ActiveDirectoryAuthenticator + > description: Authenticate against Active Directory + > userNameLabel: Username + > canSearchUsers: True + > canSearchGroups: True + > groupNameLabel: Group + > needsPassword: False + > isExternal: True + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: host + - Value: + - GUI: + + required: True + + defvalue: + + value: + + label: Host + + length: 64 + + multiline: 0 + + tooltip: Active Directory Server IP or Hostname + + rdonly: False + + type: text + + order: 1 + - Name: ssl + - Value: + - GUI: + + required: False + + defvalue: + + value: + + label: Use SSL + + length: 32 + + tooltip: If checked, a ssl connection to Active Directory will be used + + rdonly: False + + type: checkbox + + order: 2 + - Name: compat + - Value: + - GUI: + + required: True + + defvalue: w2x + + value: + + label: Compatibility + + length: 32 + + values: [{u'text': u'Windows NT', u'id': u'nt'}, {u'text': u'Windows 2000 and later', u'id': u'w2x'}] + + tooltip: Compatibility of AD connection (Usually windows 2000 and later) + + rdonly: True + + type: choice + + order: 3 + - Name: username + - Value: + - GUI: + + tab: Credentials + + required: True + + defvalue: + + tooltip: Username with read privileges on the base selected (use USER@DOMAIN.DOM form for this) + + label: User + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 4 + - Name: password + - Value: + - GUI: + + rdonly: False + + required: True + + defvalue: + + value: + + label: Password + + length: 32 + + tooltip: Password of the ldap user + + tab: Credentials + + type: password + + order: 5 + - Name: timeout + - Value: + - GUI: + + required: True + + defvalue: 10 + + maxValue: 987654321 + + tooltip: Timeout in seconds of connection to Active Directory + + minValue: 987654321 + + length: 3 + + value: + + rdonly: False + + label: Timeout + + type: numeric + + order: 6 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: host, Type: text, is Required?: True + - Name: ssl, Type: checkbox, is Required?: False + - Name: compat, Type: choice, is Required?: True + - Name: username, Type: text, is Required?: True + - Name: password, Type: password, is Required?: True + - Name: timeout, Type: numeric, is Required?: True +* eDirectory Authenticator + > canCreateUsers: True + > name: eDirectory Authenticator + > passwordLabel: Password + > type: EDirectoryAuthenticator + > description: Authenticate against eDirectory + > userNameLabel: Username + > canSearchUsers: True + > canSearchGroups: False + > groupNameLabel: Group + > needsPassword: False + > isExternal: True + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: host + - Value: + - GUI: + + required: True + + defvalue: + + value: + + label: Host + + length: 64 + + multiline: 0 + + tooltip: EDirectory Server IP or Hostname + + rdonly: False + + type: text + + order: 1 + - Name: port + - Value: + - GUI: + + required: True + + defvalue: 389 + + maxValue: 987654321 + + tooltip: Ldap port (usually 389 for non ssl and 636 for ssl) + + minValue: 987654321 + + length: 5 + + value: + + rdonly: False + + label: Port + + type: numeric + + order: 2 + - Name: ssl + - Value: + - GUI: + + required: False + + defvalue: + + value: + + label: Use SSL + + length: 32 + + tooltip: If checked, the connection will be ssl, using port 636 instead of 389 + + rdonly: False + + type: checkbox + + order: 3 + - Name: username + - Value: + - GUI: + + tab: Credentials + + required: True + + defvalue: + + tooltip: Username with read privileges on the eDirectory + + label: User + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 4 + - Name: password + - Value: + - GUI: + + rdonly: False + + required: True + + defvalue: + + value: + + label: Password + + length: 32 + + tooltip: Password of the ldap user + + tab: Credentials + + type: password + + order: 5 + - Name: timeout + - Value: + - GUI: + + required: True + + defvalue: 10 + + maxValue: 987654321 + + tooltip: Timeout in seconds of connection to LDAP + + minValue: 1 + + length: 3 + + value: + + rdonly: False + + label: Timeout + + type: numeric + + order: 6 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: host, Type: text, is Required?: True + - Name: port, Type: numeric, is Required?: True + - Name: ssl, Type: checkbox, is Required?: False + - Name: username, Type: text, is Required?: True + - Name: password, Type: password, is Required?: True + - Name: timeout, Type: numeric, is Required?: True +* Regex LDAP Authenticator + > canCreateUsers: True + > name: Regex LDAP Authenticator + > passwordLabel: Password + > type: RegexLdapAuthenticator + > description: Regular Expressions LDAP authenticator + > userNameLabel: Username + > canSearchUsers: True + > canSearchGroups: False + > groupNameLabel: Group + > needsPassword: False + > isExternal: True + > GUI + - Name: tags + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Tags for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Tags + + type: taglist + + order: -101 + - Name: name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Name of this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Name + + type: text + + order: -100 + - Name: comments + - Value: + - GUI: + + required: False + + defvalue: + + tooltip: Comments for this element + + minValue: 987654321 + + length: 256 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Comments + + type: text + + order: -99 + - Name: priority + - Value: + - GUI: + + required: True + + defvalue: 1 + + tooltip: Selects the priority of this element (lower number means higher priority) + + minValue: 987654321 + + length: 4 + + multiline: 0 + + value: 1 + + rdonly: False + + values: [] + + label: Priority + + type: numeric + + order: -97 + - Name: small_name + - Value: + - GUI: + + required: True + + defvalue: + + tooltip: Label for this element + + minValue: 987654321 + + length: 128 + + multiline: 0 + + value: + + rdonly: False + + values: [] + + label: Label + + type: text + + order: -96 + - Name: host + - Value: + - GUI: + + required: True + + defvalue: + + value: + + label: Host + + length: 64 + + multiline: 0 + + tooltip: Ldap Server Host + + rdonly: False + + type: text + + order: 1 + - Name: port + - Value: + - GUI: + + required: True + + defvalue: 389 + + maxValue: 987654321 + + tooltip: Ldap port (usually 389 for non ssl and 636 for ssl) + + minValue: 987654321 + + length: 5 + + value: + + rdonly: False + + label: Port + + type: numeric + + order: 2 + - Name: ssl + - Value: + - GUI: + + required: False + + defvalue: + + value: + + label: Use SSL + + length: 32 + + tooltip: If checked, the connection will be ssl, using port 636 instead of 389 + + rdonly: False + + type: checkbox + + order: 3 + - Name: username + - Value: + - GUI: + + tab: Credentials + + required: True + + defvalue: + + tooltip: Username with read privileges on the base selected + + label: User + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 4 + - Name: password + - Value: + - GUI: + + rdonly: False + + required: True + + defvalue: + + value: + + label: Password + + length: 32 + + tooltip: Password of the ldap user + + tab: Credentials + + type: password + + order: 5 + - Name: timeout + - Value: + - GUI: + + required: True + + defvalue: 10 + + maxValue: 987654321 + + tooltip: Timeout in seconds of connection to LDAP + + minValue: 1 + + length: 3 + + value: + + rdonly: False + + label: Timeout + + type: numeric + + order: 6 + - Name: ldapBase + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: + + tooltip: Common search base (used for "users" and "groups") + + label: Base + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 7 + - Name: userClass + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: posixAccount + + tooltip: Class for LDAP users (normally posixAccount) + + label: User class + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 8 + - Name: userIdAttr + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: uid + + tooltip: Attribute that contains the user id + + label: User Id Attr + + length: 64 + + multiline: 0 + + value: + + rdonly: False + + type: text + + order: 9 + - Name: userNameAttr + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: uid + + tooltip: Attributes that contains the user name (list of comma separated values) + + label: User Name Attr + + length: 640 + + multiline: 2 + + value: + + rdonly: False + + type: text + + order: 10 + - Name: groupNameAttr + - Value: + - GUI: + + tab: Ldap info + + required: True + + defvalue: cn + + tooltip: Attribute that contains the group name + + label: Group Name Attr + + length: 640 + + multiline: 2 + + value: + + rdonly: False + + type: text + + order: 11 + > Simplified fields: + - Name: tags, Type: taglist, is Required?: False + - Name: name, Type: text, is Required?: True + - Name: comments, Type: text, is Required?: False + - Name: priority, Type: numeric, is Required?: True + - Name: small_name, Type: text, is Required?: True + - Name: host, Type: text, is Required?: True + - Name: port, Type: numeric, is Required?: True + - Name: ssl, Type: checkbox, is Required?: False + - Name: username, Type: text, is Required?: True + - Name: password, Type: password, is Required?: True + - Name: timeout, Type: numeric, is Required?: True + - Name: ldapBase, Type: text, is Required?: True + - Name: userClass, Type: text, is Required?: True + - Name: userIdAttr, Type: text, is Required?: True + - Name: userNameAttr, Type: text, is Required?: True + - Name: groupNameAttr, Type: text, is Required?: True +******************************* +Creating a simple ldap authenticator +Correctly created name_Field with id a0b0c503-1147-5185-83c3-bf1ee8763703 +The record created was: {u'numeric_id': 56, u'groupIdAttr': u'groupId_Field', u'memberAttr': u'groupMembership_Field', u'id': u'a0b0c503-1147-5185-83c3-bf1ee8763703', u'port': u'389', u'userClass': u'userClass_Field', u'tags': [u'Tag1', u'Tag2', u'Tag3'], u'comments': u'comments__Field', u'users_count': 0, u'priority': u'1', u'type': u'SimpleLdapAuthenticator', u'username': u'username__Field', u'ldapBase': u'base_Field', u'userNameAttr': u'userName_Field', u'permission': 96, u'groupClass': u'groupClass_Field', u'ssl': False, u'host': u'host_Field', u'userIdAttr': u'userIdAttr_Field', u'password': u'password_Field', u'small_name': u'label_Field', u'name': u'name_Field', u'timeout': u'10'} +******************************* +Deleting the created simple ldap authenticator +Correctly deleted a0b0c503-1147-5185-83c3-bf1ee8763703 +******************************* +Creating internal auth +Correctly created name_Field with id 417e9102-d90e-52fd-bb46-6ad6613a4d17 +The record created was: {u'numeric_id': 57, u'small_name': u'label_Field', u'name': u'name_Field', u'tags': [u''], u'permission': 96, u'comments': u'comments_Field', u'users_count': 0, u'priority': u'1', u'acceptProxy': False, u'reverseDns': False, u'differentForEachHost': False, u'type': u'InternalDBAuth', u'id': u'417e9102-d90e-52fd-bb46-6ad6613a4d17'} +******************************* +Creating internal group +******************************* +Correctly created groupname_Field with id 16c8e525-d8f9-5d61-a05a-24f6c1d0e67b +The record created was: {u'name': u'groupname_Field', u'comments': u'comments_Field', u'state': u'A', u'meta_if_any': False, u'type': u'group', u'id': u'16c8e525-d8f9-5d61-a05a-24f6c1d0e67b'} +Creating internal user +******************************* +Correctly created username_Field with id 405fb9e4-4f03-5272-9d20-a0d2642b7d0e +The record created was: {u'name': u'username_Field', u'parent': None, u'staff_member': False, u'comments': u'comments_Field', u'real_name': u'name_Field', u'state': u'A', u'is_admin': False, u'groups': [u'16c8e525-d8f9-5d61-a05a-24f6c1d0e67b'], u'last_access': 78793200, u'id': u'405fb9e4-4f03-5272-9d20-a0d2642b7d0e'} +******************************* +Deleting user +Correctly deleted 417e9102-d90e-52fd-bb46-6ad6613a4d17 +******************************* +Deleting Group +Correctly deleted 417e9102-d90e-52fd-bb46-6ad6613a4d17 +******************************* +Deleting the created internal auth +Correctly deleted 417e9102-d90e-52fd-bb46-6ad6613a4d17 diff --git a/server/src/uds/osmanagers/WindowsOsManager/WinDomainOsManager.py b/server/src/uds/osmanagers/WindowsOsManager/WinDomainOsManager.py index 1f8e67918..e37bc3ab7 100644 --- a/server/src/uds/osmanagers/WindowsOsManager/WinDomainOsManager.py +++ b/server/src/uds/osmanagers/WindowsOsManager/WinDomainOsManager.py @@ -31,10 +31,11 @@ class WinDomainOsManager(WindowsOsManager): iconFile = 'wosmanager.png' # Apart form data from windows os manager, we need also domain and credentials - domain = gui.TextField(length=64, label=_('Domain'), order=1, tooltip=_('Domain to join machines to (use FQDN form, Netbios name not allowed)'), required=True) + domain = gui.TextField(length=64, label=_('Domain'), order=1, tooltip=_('Domain to join machines to (use FQDN form, Netbios name not supported for most operations)'), required=True) account = gui.TextField(length=64, label=_('Account'), order=2, tooltip=_('Account with rights to add machines to domain'), required=True) password = gui.PasswordField(length=64, label=_('Password'), order=3, tooltip=_('Password of the account'), required=True) ou = gui.TextField(length=64, label=_('OU'), order=4, tooltip=_('Organizational unit where to add machines in domain (check it before using it). i.e.: ou=My Machines,dc=mydomain,dc=local')) + grp = gui.TextField(length=64, label=_('Group'), order=5, tooltip=_('Group to which add machines on creation. If empty, no group will be used. (experimental)')) # Inherits base "onLogout" onLogout = WindowsOsManager.onLogout idle = WindowsOsManager.idle @@ -56,6 +57,7 @@ class WinDomainOsManager(WindowsOsManager): self._ou = values['ou'].strip() self._account = values['account'] self._password = values['password'] + self._group = values['grp'].strip() else: self._domain = "" self._ou = "" @@ -115,6 +117,57 @@ class WinDomainOsManager(WindowsOsManager): raise ldap.LDAPError(_str) + def __getGroup(self, l): + base = ','.join(['DC=' + i for i in self._domain.split('.')]) + group = self._group.replace('\\', '\\\\').replace('(', '\\(').replace(')', '\\)') + + res = l.search_ext_s(base=base, scope=ldap.SCOPE_SUBTREE, filterstr="(&(objectClass=group)(|(cn={0})(sAMAccountName={0})))".format(group), attrlist=[b'dn']) + if res[0] is None: + return None + + return res[0][0] # Returns the DN + + def __getMachine(self, l, machineName): + if self._ou: + ou = self._ou + else: + ou = ','.join(['DC=' + i for i in self._domain.split('.')]) + + fltr = '(&(objectClass=computer)(sAMAccountName={}$))'.format(machineName) + res = l.search_ext_s(base=ou, scope=ldap.SCOPE_SUBTREE, filterstr=fltr, attrlist=[b'dn']) + if res[0] is None: + return None + + return res[0][0] # Returns the DN + + def readyReceived(self, userService, data): + # No group to add + if self._group == '': + return + + if not '.' in self._domain: + logger.info('Adding to a group for a non FQDN domain is not supported') + return + + try: + l = self.__connectLdap() + except dns.resolver.NXDOMAIN: # No domain found, log it and pass + logger.warn('Could not find _ldap._tcp.' + self._domain) + log.doLog(service, log.WARN, "Could not remove machine from domain (_ldap._tcp.{0} not found)".format(self._domain), log.OSMANAGER) + except ldap.LDAPError: + logger.exception('Ldap Exception caught') + log.doLog(service, log.WARN, "Could not remove machine from domain (invalid credentials for {0})".format(self._account), log.OSMANAGER) + + try: + machine = self.__getMachine(l, userService.friendly_name) + group = self.__getGroup(l) + l.modify_s(group, ((ldap.MOD_ADD, 'member', machine),)) + except ldap.ALREADY_EXISTS: + # Already added this machine to this group, pass + pass + except Exception: + logger.error('Got exception trying to add machine to group') + def release(self, service): ''' service is a db user service object @@ -134,15 +187,11 @@ class WinDomainOsManager(WindowsOsManager): logger.exception('Ldap Exception caught') log.doLog(service, log.WARN, "Could not remove machine from domain (invalid credentials for {0})".format(self._account), log.OSMANAGER) - try: - if self._ou: - ou = self._ou - else: - ou = ','.join(['DC=' + i for i in self._domain.split('.')]) - fltr = '(&(objectClass=computer)(sAMAccountName={}$))'.format(service.friendly_name) - res = l.search_ext_s(base=ou, scope=ldap.SCOPE_SUBTREE, filterstr=fltr)[0] - l.delete_s(res[0]) # Remove by DN, SYNC + res = self.__getMachine(l, service.friendly_name) + if res is None: + raise Exception('Machine {} not found on AD (permissions?)'.format(service.friendly_name)) + l.delete_s(res) # Remove by DN, SYNC except IndexError: logger.error('Error deleting {} from BASE {}'.format(service.friendly_name, ou)) except Exception: @@ -158,11 +207,18 @@ class WinDomainOsManager(WindowsOsManager): except Exception as e: logger.exception('Exception ') return [False, str(e)] + try: l.search_st(self._ou, ldap.SCOPE_BASE) except ldap.LDAPError as e: return _('Check error: {0}').format(self.__getLdapError(e)) + # Group + if self._group != '': + if self.__getGroup(l) is None: + return _('Check Error: group "{}" not found (using "cn" to locate it)').format(self._group) + + return _('Server check was successful') @staticmethod @@ -208,16 +264,22 @@ class WinDomainOsManager(WindowsOsManager): ''' Serializes the os manager data so we can store it in database ''' - return '\t'.join(['v1', self._domain, self._ou, self._account, CryptoManager.manager().encrypt(self._password), base.encode('hex')]) + return '\t'.join(['v2', self._domain, self._ou, self._account, CryptoManager.manager().encrypt(self._password), base.encode('hex'), self._group]) def unmarshal(self, s): data = s.split('\t') - if data[0] == 'v1': + if data[0] in ('v1', 'v2'): self._domain = data[1] self._ou = data[2] self._account = data[3] self._password = CryptoManager.manager().decrypt(data[4]) - super(WinDomainOsManager, self).unmarshal(data[5].decode('hex')) + + if data[0] == 'v2': + self._group = data[6] + else: + self._group = '' + + super(WinDomainOsManager, self).unmarshal(data[5].decode('hex')) def valuesDict(self): dct = super(WinDomainOsManager, self).valuesDict() @@ -225,4 +287,5 @@ class WinDomainOsManager(WindowsOsManager): dct['ou'] = self._ou dct['account'] = self._account dct['password'] = self._password + dct['grp'] = self._group return dct diff --git a/server/src/uds/osmanagers/WindowsOsManager/WindowsOsManager.py b/server/src/uds/osmanagers/WindowsOsManager/WindowsOsManager.py index a060c6980..871101266 100644 --- a/server/src/uds/osmanagers/WindowsOsManager/WindowsOsManager.py +++ b/server/src/uds/osmanagers/WindowsOsManager/WindowsOsManager.py @@ -114,6 +114,7 @@ class WindowsOsManager(osmanagers.OSManager): si = service.getInstance() ip = '' + ip = '' # Notifies IP to deployed for p in data['ips']: if p[0].lower() == uid.lower(): @@ -139,6 +140,10 @@ class WindowsOsManager(osmanagers.OSManager): logger.exception('WindowsOs Manager message log: ') log.doLog(service, log.ERROR, "do not understand {0}".format(data), origin) + # default "ready received" does nothing + def readyReceived(self, userService, data): + pass + def process(self, userService, msg, data, options=None): ''' We understand this messages: @@ -194,6 +199,7 @@ class WindowsOsManager(osmanagers.OSManager): state = State.USABLE notifyReady = True self.notifyIp(userService.unique_id, userService, data) + self.readyReceived(userService, data) userService.setOsState(state) diff --git a/server/src/uds/transports/HTML5RDP/HTML5RDP.py b/server/src/uds/transports/HTML5RDP/HTML5RDP.py index 92ca96e45..03df10611 100644 --- a/server/src/uds/transports/HTML5RDP/HTML5RDP.py +++ b/server/src/uds/transports/HTML5RDP/HTML5RDP.py @@ -78,7 +78,7 @@ class HTML5RDPTransport(Transport): smooth = gui.CheckBoxField(label=_('Font Smoothing'), order=23, tooltip=_('If checked, fonts smoothing will be allowed (windows clients only)'), tab=gui.PARAMETERS_TAB) enableAudio = gui.CheckBoxField(label=_('Enable Audio'), order=24, tooltip=_('If checked, the audio will be redirected to client (if client browser supports it)'), tab=gui.PARAMETERS_TAB) enablePrinting = gui.CheckBoxField(label=_('Enable Printing'), order=25, tooltip=_('If checked, the printing will be redirected to client (if client browser supports it)'), tab=gui.PARAMETERS_TAB) - # enableFileShare = gui.CheckBoxField(label=_('Enable File Sharing'), order=8, tooltip=_('If checked, the user will be able to upload/download files (if client browser supports it)'), tab=gui.PARAMETERS_TAB) + # enableFileSharing = gui.CheckBoxField(label=_('Enable File Sharing'), order=8, tooltip=_('If checked, the user will be able to upload/download files (if client browser supports it)'), tab=gui.PARAMETERS_TAB) serverLayout = gui.ChoiceField(order=26, label=_('Layout'), tooltip=_('Keyboards Layout of server'), @@ -189,7 +189,7 @@ class HTML5RDPTransport(Transport): } # if self.enableFileSharing.isTrue(): - # params['enable-drive'] = self.serverLayout.value + # params['enable-drive'] = 'true' if self.serverLayout.value != '-': params['server-layout'] = self.serverLayout.value diff --git a/server/src/uds/transports/RDP/RDPFile.py b/server/src/uds/transports/RDP/RDPFile.py index e6d08fd23..b002b56af 100644 --- a/server/src/uds/transports/RDP/RDPFile.py +++ b/server/src/uds/transports/RDP/RDPFile.py @@ -40,7 +40,7 @@ from uds.core.util import OsDetector import six import os -__updated__ = '2017-06-07' +__updated__ = '2017-07-06' class RDPFile(object): @@ -227,7 +227,6 @@ class RDPFile(object): res += 'compression:i:' + compression + '\n' res += 'keyboardhook:i:2' + '\n' res += 'audiomode:i:' + audioMode + '\n' - res += 'redirectdrives:i:' + drives + '\n' res += 'redirectprinters:i:' + printers + '\n' res += 'redirectcomports:i:' + serials + '\n' res += 'redirectsmartcards:i:' + scards + '\n' @@ -260,8 +259,15 @@ class RDPFile(object): if self.redirectAudio is True: res += 'audiocapturemode:i:1\n' + if self.redirectDrives is True: + res += 'drivestoredirect:s:*\n' + res += 'devicestoredirect:s:*\n' + res += 'enablecredsspsupport:i:{}\n'.format(0 if self.enablecredsspsupport is False else 1) + # DirectX? + res += 'redirectdirectx:i:1\n' + return res def getMacOsX(self):