Пример #1
0
 def preprocess_entity(self, entity):
     """return a dictionary to use as extra argument to cursor.execute
     to insert/update an entity into a SQL database
     """
     attrs = {}
     eschema = entity.e_schema
     converters = getattr(self.dbhelper, 'TYPE_CONVERTERS', {})
     for attr, value in entity.cw_edited.items():
         if value is not None and eschema.subjrels[attr].final:
             atype = str(entity.e_schema.destination(attr))
             if atype in converters:
                 # It is easier to modify preprocess_entity rather
                 # than add_entity (native) as this behavior
                 # may also be used for update.
                 value = converters[atype](value)
             elif atype == 'Password':  # XXX could be done using a TYPE_CONVERTERS callback
                 # if value is a Binary instance, this mean we got it
                 # from a query result and so it is already encrypted
                 if isinstance(value, Binary):
                     value = value.getvalue()
                 else:
                     value = crypt_password(value)
                 value = self._binary(value)
             elif isinstance(value, Binary):
                 value = self._binary(value.getvalue())
         attrs[SQL_PREFIX + str(attr)] = value
     attrs[SQL_PREFIX + 'eid'] = entity.eid
     return attrs
Пример #2
0
 def extentities_generator(self):
     self.debug('processing ldapfeed source %s %s', self.source,
                self.searchgroupfilterstr)
     # get existing users *not* managed by this source
     non_managed_users = dict(
         self._cw.execute(
             'Any L, SN WHERE'
             ' U is CWUser, U login L,'
             ' U cw_source S, S name SN,'
             ' NOT S eid %(eid)s', {'eid': self.source.eid},
             build_descr=False))
     # generate users and email addresses
     for userdict in self.user_source_entities_by_extid.values():
         attrs = self.ldap2cwattrs(userdict, 'CWUser')
         login = attrs['login'][0]
         try:
             source = non_managed_users[login]
         except KeyError:
             pass
         else:
             self.error(
                 'not synchronizing user %s. User already exist in source %s',
                 login, source)
             continue
         pwd = attrs.get('upassword')
         if not pwd:
             # generate a dumb password if not fetched from ldap (see
             # userPassword)
             pwd = crypt_password(generate_password())
             attrs['upassword'] = set([pwd])
         self._source_uris.pop(userdict['dn'], None)
         extuser = importer.ExtEntity('CWUser',
                                      userdict['dn'].encode('ascii'), attrs)
         extuser.values['owned_by'] = set([extuser.extid])
         for extemail in self._process_email(extuser, userdict):
             yield extemail
         groups = list(
             filter(None, [
                 self._get_group(name)
                 for name in self.source.user_default_groups
             ]))
         if groups:
             extuser.values['in_group'] = groups
         yield extuser
     # generate groups
     for groupdict in self.group_source_entities_by_extid.values():
         attrs = self.ldap2cwattrs(groupdict, 'CWGroup')
         self._source_uris.pop(groupdict['dn'], None)
         extgroup = importer.ExtEntity('CWGroup',
                                       groupdict['dn'].encode('ascii'),
                                       attrs)
         yield extgroup
         # record group membership for later insertion
         members = groupdict.get(self.source.group_rev_attrs['member'], ())
         self._group_members[attrs['name']] = members
Пример #3
0
 def run(self, args):
     """run the command with its specific arguments"""
     from cubicweb.server.utils import crypt_password, manager_userpasswd
     appid = args[0]
     config = ServerConfiguration.config_for(appid)
     sourcescfg = config.read_sources_file()
     try:
         adminlogin = sourcescfg['admin']['login']
     except KeyError:
         print('-> Error: could not get cubicweb administrator login.')
         sys.exit(1)
     cnx = source_cnx(sourcescfg['system'])
     driver = sourcescfg['system']['db-driver']
     dbhelper = get_db_helper(driver)
     cursor = cnx.cursor()
     # check admin exists
     cursor.execute("SELECT * FROM cw_CWUser WHERE cw_login=%(l)s",
                    {'l': adminlogin})
     if not cursor.fetchall():
         print("-> error: admin user %r specified in sources doesn't exist "
               "in the database" % adminlogin)
         print("   fix your sources file before running this command")
         cnx.close()
         sys.exit(1)
     if self.config.password is None:
         # ask for a new password
         msg = 'new password for %s' % adminlogin
         _, pwd = manager_userpasswd(adminlogin,
                                     confirm=True,
                                     passwdmsg=msg)
     else:
         pwd = self.config.password
     try:
         cursor.execute(
             "UPDATE cw_CWUser SET cw_upassword=%(p)s WHERE cw_login=%(l)s",
             {
                 'p': dbhelper.binary_value(crypt_password(pwd)),
                 'l': adminlogin
             })
         sconfig = Configuration(options=USER_OPTIONS)
         sconfig['login'] = adminlogin
         sconfig['password'] = pwd
         sourcescfg['admin'] = sconfig
         config.write_sources_file(sourcescfg)
     except Exception as ex:
         cnx.rollback()
         import traceback
         traceback.print_exc()
         print('-> an error occurred:', ex)
     else:
         cnx.commit()
         print('-> password reset, sources file regenerated.')
     cnx.close()
Пример #4
0
    def add_user(self, user_name, password, group_name="users"):
        """ Add a new user in the database.

        Parameters
        ----------
        user_name: str
            the login of the user in the database.
        password: str
            the password of the user in the database.
        group_name: str
            the database group name the user will be rattached to.
        """
        # Get the activated State entity
        rql = "Any X Where X is State, X name 'activated'"
        rset = self.session.execute(rql)
        if rset.rowcount != 1:
            raise Exception("Can't insert users, no activated State entity "
                            "detected.")
        state_eid = rset[0][0]

        # Insert the user
        crypted = crypt_password(password)
        user_entity, is_created = self._get_or_create_unique_entity(
            rql=("Any X Where X is CWUser, X login "
                 "'{0}'".format(user_name)),
            check_unicity=True,
            entity_name="CWUser",
            login=unicode(user_name),
            upassword=Binary(crypted))

        # If the user is created, add relation with the State entity
        if is_created:

            # Activate the account
            self._set_unique_relation(
                user_entity.eid, "in_state", state_eid, check_unicity=False)

            # Add the user to the default group
            rset = self.session.execute(
                "Any X Where X is CWGroup, X name '{0}'".format(group_name))
            if rset.rowcount != 1:
                raise Exception(
                    "Can't insert user '{0}' in group '{1}', got {2} "
                    "matches.".format(user_name, group_name, rset.rowcount))
            group_eid = rset[0][0]
            self._set_unique_relation(
                user_entity.eid, "in_group", group_eid, check_unicity=False)
Пример #5
0
    def test_crypt(self):
        for hash in (
                utils.crypt_password('xxx'),  # default sha512
                b'ab$5UsKFxRKKN.d8iBIFBnQ80',  # custom md5
                b'ab4Vlm81ZUHlg',  # DES
        ):
            self.assertEqual(utils.crypt_password('xxx', hash), hash)
            self.assertEqual(utils.crypt_password(u'xxx', hash), hash)
            self.assertEqual(
                utils.crypt_password(u'xxx', hash.decode('ascii')),
                hash.decode('ascii'))
            self.assertEqual(utils.crypt_password('yyy', hash), b'')

        # accept any password for empty hashes (is it a good idea?)
        self.assertEqual(utils.crypt_password('xxx', ''), '')
        self.assertEqual(utils.crypt_password('yyy', ''), '')
Пример #6
0
 def _process_ldap_item(self, dn, iterator):
     """Turn an ldap received item into a proper dict."""
     itemdict = {'dn': dn}
     for key, value in iterator:
         if self.user_attrs.get(
                 key) == 'upassword':  # XXx better password detection
             value = value[0].encode('utf-8')
             # we only support ldap_salted_sha1 for ldap sources, see: server/utils.py
             if not value.startswith(b'{SSHA}'):
                 value = utils.crypt_password(value)
             itemdict[key] = Binary(value)
         elif self.user_attrs.get(key) == 'modification_date':
             itemdict[key] = datetime.strptime(value[0], '%Y%m%d%H%M%SZ')
         else:
             if len(value) == 1:
                 itemdict[key] = value = value[0]
             else:
                 itemdict[key] = value
     # we expect memberUid to be a list of user ids, make sure of it
     member = self.group_rev_attrs['member']
     if isinstance(itemdict.get(member), str):
         itemdict[member] = [itemdict[member]]
     return itemdict
Пример #7
0
    def import_data(self):
        """ Method that import the users in cw.

        .. note::

            This procedure create a user as a 'CWUser' entity which is related
            to different groups through the 'in_group' relation.

            |

            .. image:: ../schemas/users.png
                :width: 500px
                :align: center
                :alt: schema

        .. warning::

            This procedure expect that the 'CWGroup' of interest are already
            created.
        """
        # Get the activated State entity
        rql = "Any X Where X is State, X name 'activated'"
        rset = self.session.execute(rql)
        if rset.rowcount != 1:
            logging.error("Can't insert users, no activated State entity detected.")
            raise Exception("Can't insert users, no activated State entity " "detected.")
        state_eid = rset[0][0]

        # Go through the goup names
        nb_of_users = float(len(self.users))
        maxsize = max([len(name) for name in self.users])
        cnt_user = 1.0
        for user_name, user_item in self.users.iteritems():

            # Print a progress bar
            self._progress_bar(
                cnt_user / nb_of_users, title="{0}(users)".format(user_name), bar_length=40, maxsize=maxsize + 7
            )
            cnt_user += 1.0

            # Create the user
            crypted = crypt_password(user_item["password"])
            user_entity, is_created = self._get_or_create_unique_entity(
                rql=("Any X Where X is CWUser, X login " "'{0}'".format(user_item["login"])),
                check_unicity=True,
                entity_name="CWUser",
                login=unicode(user_item["login"]),
                upassword=Binary(crypted),
            )

            # If the user is created, add relation with the State entity
            if is_created:
                self._set_unique_relation(user_entity.eid, "in_state", state_eid, check_unicity=False)

            # Go through group names
            for group_name in user_item["group_names"]:

                # Check if the group exists
                rql = "Any X Where X is CWGroup, X name '{0}'".format(group_name)

                # Execute the rql request
                rset = self.session.execute(rql)

                # The request returns some data -> do nothing
                if rset.rowcount != 1:
                    logging.error(
                        "Can't insert user '{0}' in group '{1}', got {2} "
                        "matches.".format(user_name, group_name, rset.rowcount)
                    )
                    continue

                # Get the group entity
                group_eid = rset[0][0]
                # > add relation with the user
                self._set_unique_relation(user_entity.eid, "in_group", group_eid, check_unicity=True)

        print  # new line after last progress bar update
Пример #8
0
    def import_data(self):
        """ Method that import the users in cw.

        .. note::

            This procedure create a user as a 'CWUser' entity which is related
            to different groups through the 'in_group' relation.

            |

            .. image:: ../schemas/users.png
                :width: 500px
                :align: center
                :alt: schema

        .. warning::

            This procedure expect that the 'CWGroup' of interest are already
            created.
        """
        # Get the activated State entity
        rql = "Any X Where X is State, X name 'activated'"
        rset = self.session.execute(rql)
        if rset.rowcount != 1:
            logging.error(
                "Can't insert users, no activated State entity detected.")
            raise Exception("Can't insert users, no activated State entity "
                            "detected.")
        state_eid = rset[0][0]

        # Go through the goup names
        nb_of_users = float(len(self.users))
        maxsize = max([len(name) for name in self.users])
        cnt_user = 1.
        for user_name, user_item in self.users.iteritems():

            # Print a progress bar
            self._progress_bar(
                cnt_user / nb_of_users,
                title="{0}(users)".format(user_name),
                bar_length=40, maxsize=maxsize + 7)
            cnt_user += 1.

            # Create the user
            crypted = crypt_password(user_item["password"])
            user_entity, is_created = self._get_or_create_unique_entity(
                rql=("Any X Where X is CWUser, X login "
                     "'{0}'".format(user_item["login"])),
                check_unicity=True,
                entity_name="CWUser",
                login=unicode(user_item["login"]),
                upassword=Binary(crypted))

            # If the user is created, add relation with the State entity
            if is_created:
                self._set_unique_relation(user_entity.eid,
                        "in_state", state_eid, check_unicity=False)

            # Go through group names
            for group_name in user_item["group_names"]:

                # Check if the group exists
                rql = "Any X Where X is CWGroup, X name '{0}'".format(group_name)

                # Execute the rql request
                rset = self.session.execute(rql)

                # The request returns some data -> do nothing
                if rset.rowcount != 1:
                    logging.error(
                        "Can't insert user '{0}' in group '{1}', got {2} "
                        "matches.".format(user_name, group_name, rset.rowcount))
                    continue

                # Get the group entity
                group_eid = rset[0][0]
                # > add relation with the user
                self._set_unique_relation(user_entity.eid,
                        "in_group", group_eid, check_unicity=True)

        print  # new line after last progress bar update
Пример #9
0
from __future__ import print_function

from logilab.common.shellutils import generate_password
from cubicweb.server.utils import crypt_password

for user in rql('CWUser U WHERE U cw_source S, S name "system", U upassword P, U login L').entities():
    salt = user.upassword.getvalue()
    if crypt_password('', salt) == salt:
        passwd = generate_password()
        print('setting random password for user %s' % user.login)
        user.set_attributes(upassword=passwd)

commit()
Пример #10
0
import sys
import getpass

from cubicweb import Binary
from cubicweb.server.utils import crypt_password


if __args__:
    login = __args__.pop()
else:
    login = raw_input("login? ")

rset = rql('Any U WHERE U is CWUser, U login %(login)s', {'login': login})

if len(rset) != 1:
    sys.exit("user '%s' does not exist!" % login)

pass1 = getpass.getpass(prompt='Enter new password? ')
pass2 = getpass.getpass(prompt='Confirm? ')

if pass1 != pass2:
    sys.exit("passwords don't match!")

crypted = crypt_password(pass1)

cwuser = rset.get_entity(0,0)
cwuser.cw_set(upassword=Binary(crypted))
commit()

print("password updated.")