Exemple #1
0
    def check_pool_info(self, pi_uuid=None, pi_ntargets=None, pi_nnodes=None,
                        pi_ndisabled=None, pi_map_ver=None, pi_leader=None,
                        pi_bits=None):
        # pylint: disable=unused-argument
        """Check the pool info attributes.

        Args:
            pi_uuid (str, optional): pool uuid. Defaults to None.
            pi_ntargets (int, optional): number of targets. Defaults to None.
            pi_nnodes (int, optional): number of nodes. Defaults to None.
            pi_ndisabled (int, optional): number of disabled. Defaults to None.
            pi_map_ver (int, optional): pool map version. Defaults to None.
            pi_leader (int, optional): pool leader. Defaults to None.
            pi_bits (int, optional): pool bits. Defaults to None.

        Note:
            Arguments may also be provided as a string with a number preceeded
            by '<', '<=', '>', or '>=' for other comparisions besides the
            default '=='.

        Returns:
            bool: True if at least one expected value is specified and all the
                specified values match; False otherwise

        """
        self.get_info()
        checks = [
            (key,
             c_uuid_to_str(getattr(self.info, key))
             if key == "pi_uuid" else getattr(self.info, key),
             val)
            for key, val in locals().items()
            if key != "self" and val is not None]
        return self._check_info(checks)
Exemple #2
0
    def setUp(self):
        """
        set up method
        """
        super(Snapshot, self).setUp()
        # get parameters from yaml file
        createmode = self.params.get("mode", '/run/poolparams/createmode/')
        createuid = os.geteuid()
        creategid = os.getegid()
        createsetid = self.params.get("setname", '/run/poolparams/createset/')
        createsize = self.params.get("size", '/run/poolparams/createsize/')
        self.log.info("==In setUp, self.context= %s", self.context)

        try:

            # initialize a python pool object then create the underlying
            # daos storage
            self.pool = DaosPool(self.context)
            self.pool.create(createmode, createuid, creategid, createsize,
                             createsetid, None)

            # need a connection to the pool with rw permission
            #    DAOS_PC_RO = int(1 << 0)
            #    DAOS_PC_RW = int(1 << 1)
            #    DAOS_PC_EX = int(1 << 2)
            self.pool.connect(1 << 1)

            # create a container
            self.container = DaosContainer(self.context)
            self.container.create(self.pool.handle)

        except DaosApiError as error:
            self.log.info("Error detected in DAOS pool container setup: %s",
                          str(error))
            self.log.info(traceback.format_exc())
            self.fail("##Test failed on setUp, before snapshot taken")

        # now open it
        self.container.open()

        # do a query and compare the UUID returned from create with
        # that returned by query
        self.container.query()

        if self.container.get_uuid_str() != c_uuid_to_str(
                self.container.info.ci_uuid):
            self.fail("##Container UUID did not match the one in info.")
Exemple #3
0
    def test_container_basics(self):
        """
        Test basic container create/destroy/open/close/query.

        :avocado:tags=all,pr,container,containercreate,containerdestroy,basecont
        """
        try:
            # Parameters used in pool create
            pool_mode = self.params.get("mode", '/run/pool/createmode/')
            pool_name = self.params.get("setname", '/run/pool/createset/')
            pool_size = self.params.get("size", '/run/pool/createsize/')

            # Create pool and connect
            self.pool = get_pool(self.context, pool_mode, pool_size, pool_name,
                                 1, self.d_log)

            # Create a container and open
            self.container = get_container(self.context, self.pool, self.d_log)

            # Query and compare the UUID returned from create with
            # that returned by query
            self.container.query()

            if self.container.get_uuid_str() != c_uuid_to_str(
                    self.container.info.ci_uuid):
                self.fail("Container UUID did not match the one in info'n")

            self.container.close()

            # Wait and destroy
            time.sleep(5)
            self.container.destroy()

        except DaosApiError as excep:
            print(excep)
            print(traceback.format_exc())
            self.fail("Test was expected to pass but it failed.\n")
        except Exception as excep:
            self.fail("Daos code segfaulted most likely, error: %s" % excep)
        finally:
            self.log.info("Clean up pool")
            if self.pool is not None:
                self.pool.disconnect()
                self.pool.destroy(1)
    def test_container_basics(self):
        """
        Test basic container create/destroy/open/close/query.  Nothing fancy
        just making sure they work at a rudimentary level

        :avocado: tags=container,containercreate,containerdestroy,basecont
        """

        pool = None
        hostlist = None

        try:
            hostlist = self.params.get("test_machines", '/run/hosts/*')
            hostfile = write_host_file.write_host_file(hostlist,
                                                       self.workdir)

            self.agent_sessions = AgentUtils.run_agent(self.basepath, hostlist)
            server_utils.run_server(hostfile, self.server_group, self.basepath)

            # give it time to start
            time.sleep(2)

            # parameters used in pool create
            createmode = self.params.get("mode", '/run/conttests/createmode/')
            createuid = self.params.get("uid", '/run/conttests/createuid/')
            creategid = self.params.get("gid", '/run/conttests/creategid/')
            createsetid = self.params.get("setname",
                                          '/run/conttests/createset/')
            createsize = self.params.get("size", '/run/conttests/createsize/')

            # initialize a python pool object then create the underlying
            # daos storage
            pool = DaosPool(self.context)
            pool.create(createmode, createuid, creategid,
                        createsize, createsetid, None)

            # need a connection to create container
            pool.connect(1 << 1)

            # create a container
            container = DaosContainer(self.context)
            container.create(pool.handle)

            # now open it
            container.open()

            # do a query and compare the UUID returned from create with
            # that returned by query
            container.query()

            if container.get_uuid_str() != c_uuid_to_str(
                    container.info.ci_uuid):
                self.fail("Container UUID did not match the one in info'n")

            container.close()

            # wait a few seconds and then destroy
            time.sleep(5)
            container.destroy()

        except DaosApiError as excep:
            print(excep)
            print(traceback.format_exc())
            self.fail("Test was expected to pass but it failed.\n")
        except Exception as excep:
            self.fail("Daos code segfaulted most likely, error: %s" % excep)
        finally:
            # cleanup the pool
            if pool is not None:
                pool.disconnect()
                pool.destroy(1)
            if self.agent_sessions:
                AgentUtils.stop_agent(hostlist, self.agent_sessions)
            server_utils.stop_server(hosts=hostlist)
Exemple #5
0
    def test_array_obj(self):
        """
        Test ID: DAOS-961

        Test Description: Writes an array to an object and then reads it
        back and verifies it.

        :avocado: tags=object,arrayobj,regression,vm,small
        """
        try:
            # parameters used in pool create
            createmode = self.params.get("mode", '/run/conttests/createmode/')
            createsetid = self.params.get("setname",
                                          '/run/conttests/createset/')
            createsize = self.params.get("size", '/run/conttests/createsize/')
            createuid = os.geteuid()
            creategid = os.getegid()
            print("uid is {} gid is {}".format(createuid, creategid))

            # initialize a python pool object then create the underlying
            # daos storage
            pool = DaosPool(self.Context)
            pool.create(createmode, createuid, creategid, createsize,
                        createsetid, None)
            self.pl.info("Pool %s created.", pool.get_uuid_str())

            # need a connection to create container
            pool.connect(1 << 1)

            # create a container
            container = DaosContainer(self.Context)
            container.create(pool.handle)
            self.pl.info("Container %s created.", container.get_uuid_str())

            # now open it
            container.open()

            # do a query and compare the UUID returned from create with
            # that returned by query
            container.query()

            if container.get_uuid_str() != c_uuid_to_str(
                    container.info.ci_uuid):
                self.fail("Container UUID did not match the one in info\n")

            # create an object and write some data into it
            thedata = []
            thedata.append("data string one")
            thedata.append("data string two")
            thedata.append("data string tre")
            dkey = "this is the dkey"
            akey = "this is the akey"

            self.pl.info("writing array to dkey >%s< akey >%s<.", dkey, akey)
            oid, epoch = container.write_an_array_value(thedata, dkey, akey)

            # read the data back and make sure its correct
            length = len(thedata[0])
            thedata2 = container.read_an_array(len(thedata), length + 1, dkey,
                                               akey, oid, epoch)
            if thedata[0][0:length - 1] != thedata2[0][0:length - 1]:
                self.pl.error("Data mismatch")
                self.pl.error("Wrote: >%s<" (thedata[0]))
                self.pl.error("Read: >%s<" (thedata2[0]))
                self.fail("Write data, read it back, didn't match\n")

            if thedata[2][0:length - 1] != thedata2[2][0:length - 1]:
                self.pl.error("Data mismatch")
                self.pl.error("Wrote: >%s<" (thedata[2]))
                self.pl.error("Read: >%s<" (thedata2[2]))
                self.fail("Write data, read it back, didn't match\n")

            container.close()

            # wait a few seconds and then destroy
            time.sleep(5)
            container.destroy()

            # cleanup the pool
            pool.disconnect()
            pool.destroy(1)
            self.pl.info("Test Complete")

        except ValueError as e:
            self.pl.error("Test Failed, exception was thrown.")
            print e
            print traceback.format_exc()
            self.fail("Test was expected to pass but it failed.\n")
    def test_container_basics(self):
        """
        Test basic container create/destroy/open/close/query.  Nothing fancy
        just making sure they work at a rudimentary level

        :avocado: tags=container,containercreate,containerdestroy,basecont
        """

        pool = None
        hostlist = None

        try:
            hostlist = self.params.get("test_machines", '/run/hosts/*')
            hostfile = write_host_file.write_host_file(hostlist,
                                                       self.workdir)

            self.agent_sessions = agent_utils.run_agent(self.basepath, hostlist)
            server_utils.run_server(hostfile, self.server_group, self.basepath)

            # give it time to start
            time.sleep(2)

            # parameters used in pool create
            createmode = self.params.get("mode", '/run/conttests/createmode/')
            createuid = self.params.get("uid", '/run/conttests/createuid/')
            creategid = self.params.get("gid", '/run/conttests/creategid/')
            createsetid = self.params.get("setname",
                                          '/run/conttests/createset/')
            createsize = self.params.get("size", '/run/conttests/createsize/')

            # initialize a python pool object then create the underlying
            # daos storage
            pool = DaosPool(self.context)
            pool.create(createmode, createuid, creategid,
                        createsize, createsetid, None)

            # need a connection to create container
            pool.connect(1 << 1)

            # create a container
            container = DaosContainer(self.context)
            container.create(pool.handle)

            # now open it
            container.open()

            # do a query and compare the UUID returned from create with
            # that returned by query
            container.query()

            if container.get_uuid_str() != c_uuid_to_str(
                    container.info.ci_uuid):
                self.fail("Container UUID did not match the one in info'n")

            container.close()

            # wait a few seconds and then destroy
            time.sleep(5)
            container.destroy()

        except DaosApiError as excep:
            print(excep)
            print(traceback.format_exc())
            self.fail("Test was expected to pass but it failed.\n")
        except Exception as excep:
            self.fail("Daos code segfaulted most likely, error: %s" % excep)
        finally:
            # cleanup the pool
            if pool is not None:
                pool.disconnect()
                pool.destroy(1)
            if self.agent_sessions:
                agent_utils.stop_agent(self.agent_sessions)
            server_utils.stop_server(hosts=hostlist)
Exemple #7
0
    def test_simple_query(self):
        """
        Test querying a pool created on a single server.

        :avocado: tags=pool,poolquery,infotest
        """
        # create pool
        mode = self.params.get("mode", '/run/testparams/modes/*', 0731)
        if mode == 73:
            self.cancel('Cancel the mode test 73 because of DAOS-1877')

        uid = os.geteuid()
        gid = os.getegid()
        size = self.params.get("size", '/run/testparams/sizes/*', 0)
        group = self.server_group

        self.pool.create(mode, uid, gid, size, group, None)

        # connect to the pool
        flags = self.params.get("perms", '/run/testparams/connectperms/*', '')
        connect_flags = 1 << flags
        self.pool.connect(connect_flags)

        # query the pool
        pool_info = self.pool.pool_query()

        # check uuid
        uuid_str = c_uuid_to_str(pool_info.pi_uuid)
        if uuid_str != self.pool.get_uuid_str():
            self.d_log.error("UUID str does not match expected string")
            self.fail("UUID str does not match expected string")
        '''
        # validate size of pool is what we expect
        This check is currently disabled, as space is not implemented in
        DAOS C API yet.
        if size != pool_info.pi_space:
            self.d_log.error("expected size {0} did not match actual size {1}"
                      .format(size, pool_info.pi_space))
            self.fail("expected size {0} did not match actual size {1}"
                      .format(size, pool_info.pi_space))
        '''

        # number of targets
        if pool_info.pi_ntargets != len(self.hostlist):
            self.d_log.error("found number of targets in pool did not match "
                             "expected number, 1. num targets: {0}".format(
                                 pool_info.pi_ntargets))
            self.fail("found number of targets in pool did not match "
                      "expected number, 1. num targets: {0}".format(
                          pool_info.pi_ntargets))

        # number of disabled targets
        if pool_info.pi_ndisabled > 0:
            self.d_log.error("found disabled targets, none expected to be")
            self.fail("found disabled targets, none expected to be disabled")

        # mode
        if pool_info.pi_mode != mode:
            self.d_log.error(
                "found different mode than expected. expected {0}, "
                "found {1}.".format(mode, pool_info.pi_mode))
            self.fail("found different mode than expected. expected {0}, "
                      "found {1}.".format(mode, pool_info.pi_mode))

        # uid
        if pool_info.pi_uid != uid:
            self.d_log.error(
                "found actual pool uid {0} does not match expected "
                "uid {1}".format(pool_info.pi_uid, uid))
            self.fail("found actual pool uid {0} does not match expected uid "
                      "{1}".format(pool_info.pi_uid, uid))

        # gid
        if pool_info.pi_gid != gid:
            self.d_log.error(
                "found actual pool gid {0} does not match expected "
                "gid {1}".format(pool_info.pi_gid, gid))
            self.fail("found actual pool gid {0} does not match expected gid "
                      "{1}".format(pool_info.pi_gid, gid))
Exemple #8
0
    def test_simple_query(self):
        """
        Test querying a pool created on a single server.

        :avocado: tags=pool,poolquery,infotest
        """
        # there is a presumption that this test lives in a specific spot
        # in the repo

        # create pool
        mode = self.params.get("mode", '/run/testparams/modes/*', 0731)
        uid = os.geteuid()
        gid = os.getegid()
        size = self.params.get("size", '/run/testparams/sizes/*', 0)
        tgt_list = None
        group = self.server_group

        self.pool.create(mode, uid, gid, size, group, tgt_list)
        PROGRESS_LOG.info("created pool")

        # connect to the pool
        flags = self.params.get("perms", '/run/testparams/connectperms/*', '')
        connect_flags = 1 << flags
        self.pool.connect(connect_flags)
        PROGRESS_LOG.info("connected to pool")

        # query the pool
        pool_info = self.pool.pool_query()
        PROGRESS_LOG.info("queried pool info")

        # check uuid
        uuid_str = c_uuid_to_str(pool_info.pi_uuid)
        PROGRESS_LOG.info("pool uuid pool_info.pi_uuid: {0}".format(uuid_str))
        PROGRESS_LOG.info("pool uuid saved in api at create time: "
                          "{0}".format(self.pool.get_uuid_str()))
        if uuid_str != self.pool.get_uuid_str():
            self.fail("UUID str does not match expected string")

        # validate size of pool is what we expect
        PROGRESS_LOG.info("pool should be {0} bytes".format(size))
        PROGRESS_LOG.info("pool actual space is {0} bytes".format(
            pool_info.pi_space))
        '''
        This check is currently disabled, as space is not implemented in
        DAOS C API yet.
        if size != pool_info.pi_space:
            self.fail("expected size {0} did not match actual size {1}"
                      .format(size, pool_info.pi_space))
        '''

        # number of targets
        PROGRESS_LOG.info("number of targets in pool: %s",
                          pool_info.pi_ntargets)
        if pool_info.pi_ntargets != len(self.hostlist):
            self.fail("found number of targets in pool did not match "
                      "expected number, 1. num targets: {0}".format(
                          pool_info.pi_ntargets))

        # number of disabled targets
        PROGRESS_LOG.info("number of disabled targets in pool: %s",
                          pool_info.pi_ndisabled)
        if pool_info.pi_ndisabled > 0:
            self.fail("found disabled targets, none expected to be disabled")

        # mode
        PROGRESS_LOG.info("pool mode: %s", pool_info.pi_mode)
        if pool_info.pi_mode != mode:
            self.fail("found different mode than expected. expected {0}, "
                      "found {1}.".format(mode, pool_info.pi_mode))

        # uid
        PROGRESS_LOG.info("expected uid is {0}".format(uid))
        if pool_info.pi_uid != uid:
            self.fail("found actual pool uid {0} does not match expected uid "
                      "{1}".format(pool_info.pi_uid, uid))

        # gid
        PROGRESS_LOG.info("expected gid is {0}".format(gid))
        if pool_info.pi_gid != gid:
            self.fail("found actual pool gid {0} does not match expected gid "
                      "{1}".format(pool_info.pi_gid, gid))
Exemple #9
0
    def test_array_obj(self):
        """
        Test ID: DAOS-961

        Test Description: Writes an array to an object and then reads it
        back and verifies it.

        :avocado: tags=object,arrayobj,regression,vm,small
        """
        try:
            # parameters used in pool create
            createmode = self.params.get("mode", '/run/pool_params/createmode/')
            createsetid = self.params.get("setname",
                                          '/run/pool_params/createset/')
            createsize = self.params.get("size", '/run/pool_params/createsize/')
            createuid = os.geteuid()
            creategid = os.getegid()

            # initialize a python pool object then create the underlying
            # daos storage
            pool = DaosPool(self.context)
            pool.create(createmode, createuid, creategid,
                        createsize, createsetid, None)
            self.plog.info("Pool %s created.", pool.get_uuid_str())

            # need a connection to create container
            pool.connect(1 << 1)

            # create a container
            container = DaosContainer(self.context)
            container.create(pool.handle)
            self.plog.info("Container %s created.", container.get_uuid_str())

            # now open it
            container.open()

            # do a query and compare the UUID returned from create with
            # that returned by query
            container.query()

            if container.get_uuid_str() != c_uuid_to_str(
                    container.info.ci_uuid):
                self.fail("Container UUID did not match the one in info\n")

            # create an object and write some data into it
            thedata = []
            thedata.append("data string one")
            thedata.append("data string two")
            thedata.append("data string tre")
            dkey = "this is the dkey"
            akey = "this is the akey"

            self.plog.info("writing array to dkey >%s< akey >%s<.", dkey, akey)
            oid, epoch = container.write_an_array_value(thedata, dkey, akey,
                                                        obj_cls=3)

            # read the data back and make sure its correct
            length = len(thedata[0])
            thedata2 = container.read_an_array(len(thedata), length+1,
                                               dkey, akey, oid, epoch)
            if thedata[0][0:length-1] != thedata2[0][0:length-1]:
                self.plog.error("Data mismatch")
                self.plog.error("Wrote: >%s<", thedata[0])
                self.plog.error("Read: >%s<", thedata2[0])
                self.fail("Write data, read it back, didn't match\n")

            if thedata[2][0:length-1] != thedata2[2][0:length-1]:
                self.plog.error("Data mismatch")
                self.plog.error("Wrote: >%s<", thedata[2])
                self.plog.error("Read: >%s<", thedata2[2])
                self.fail("Write data, read it back, didn't match\n")

            container.close()

            # wait a few seconds and then destroy
            time.sleep(5)
            container.destroy()

            # cleanup the pool
            pool.disconnect()
            pool.destroy(1)
            self.plog.info("Test Complete")

        except DaosApiError as excep:
            self.plog.error("Test Failed, exception was thrown.")
            print(excep)
            print(traceback.format_exc())
            self.fail("Test was expected to pass but it failed.\n")
Exemple #10
0
    def test_destroy_withdata(self):
        """
        Test destroy and recreate one right after the other multiple times
        Should fail.

        :avocado: tags=pool,pooldestroy,destroydata
        """
        try:
            # write out a hostfile and start the servers with it
            self.hostlist = self.params.get("test_machines1", '/run/hosts/')
            hostfile = write_host_file.write_host_file(self.hostlist, self.tmp)

            self.agent_sessions = AgentUtils.run_agent(self.basepath,
                                                       self.hostlist)
            server_utils.run_server(hostfile, self.server_group, self.basepath)

            # parameters used in pool create
            createmode = self.params.get("mode", '/run/poolparams/createmode/')
            createuid = self.params.get("uid", '/run/poolparams/createuid/')
            creategid = self.params.get("gid", '/run/poolparams/creategid/')
            createsetid = self.params.get("setname",
                                          '/run/poolparams/createset/')
            createsize = self.params.get("size", '/run/poolparams/createsize/')

            # initialize a python pool object then create the underlying
            # daos storage
            pool = DaosPool(self.context)
            pool.create(createmode, createuid, creategid,
                        createsize, createsetid, None)

            # need a connection to create container
            pool.connect(1 << 1)

            # create a container
            container = DaosContainer(self.context)
            container.create(pool.handle)

            pool.disconnect()

            daosctl = self.basepath + '/install/bin/daosctl'

            write_cmd = ('{0} write-pattern -i {1} -l 0 -c {2} -p sequential'.
                         format(daosctl, c_uuid_to_str(pool.uuid),
                                c_uuid_to_str(container.uuid)))

            process.system_output(write_cmd)

            # blow it away
            pool.destroy(1)

        except DaosApiError as excep:
            print(excep)
            print(traceback.format_exc())
            self.fail("create/destroy/create/destroy test failed.\n")

        except Exception as excep:
            self.fail("Daos code segfaulted most likely.  Error: %s" % excep)

        # no matter what happens cleanup
        finally:
            if self.agent_sessions:
                AgentUtils.stop_agent(self.hostlist, self.agent_sessions)
            server_utils.stop_server(hosts=self.hostlist)
            os.remove(hostfile)
    def test_container_basics(self):
        """
        Test basic container create/destroy/open/close/query.  Nothing fancy
        just making sure they work at a rudimentary level

        :avocado: tags=container,containercreate,containerdestroy,basecont
        """

        hostfile = None

        try:
            self.hostlist = self.params.get("test_machines",'/run/hosts/*')
            hostfile = WriteHostFile.WriteHostFile(self.hostlist, self.tmp)

            ServerUtils.runServer(hostfile, self.server_group, self.basepath)

            # give it time to start
            time.sleep(2)

            # parameters used in pool create
            createmode = self.params.get("mode",'/run/conttests/createmode/')
            createuid  = self.params.get("uid",'/run/conttests/createuid/')
            creategid  = self.params.get("gid",'/run/conttests/creategid/')
            createsetid = self.params.get("setname",'/run/conttests/createset/')
            createsize  = self.params.get("size",'/run/conttests/createsize/')

            # initialize a python pool object then create the underlying
            # daos storage
            POOL = DaosPool(self.Context)
            POOL.create(createmode, createuid, creategid,
                        createsize, createsetid, None)

            # need a connection to create container
            POOL.connect(1 << 1)

            # create a container
            CONTAINER = DaosContainer(self.Context)
            CONTAINER.create(POOL.handle)

            # now open it
            CONTAINER.open()

            # do a query and compare the UUID returned from create with
            # that returned by query
            CONTAINER.query()

            if CONTAINER.get_uuid_str() != c_uuid_to_str(
                    CONTAINER.info.ci_uuid):
                self.fail("Container UUID did not match the one in info'n")

            CONTAINER.close()

            # wait a few seconds and then destroy
            time.sleep(5)
            CONTAINER.destroy()

            # cleanup the pool
            POOL.disconnect()
            POOL.destroy(1)

        except DaosApiError as e:
            print(e)
            print(traceback.format_exc())
            self.fail("Test was expected to pass but it failed.\n")
        except Exception as e:
            self.fail("Daos code segfaulted most likely, error: %s" % e)
        finally:
            try:
                if hostfile is not None:
                    os.remove(hostfile)
            finally:
                ServerUtils.stopServer(hosts=self.hostlist)
Exemple #12
0
    def test_epoch_basics(self):
        """
        Perform I/O to an object in a container in 2 different epochs,
        verifying basic I/O and epochs in particular.

        :avocado: tags=container,epoch,basicepoch
        """
        try:
            # parameters used in pool create
            createmode = self.params.get("mode",'/run/conttests/createmode/')
            createuid  = self.params.get("uid",'/run/conttests/createuid/')
            creategid  = self.params.get("gid",'/run/conttests/creategid/')
            createsetid = self.params.get("setname",'/run/conttests/createset/')
            createsize  = self.params.get("size",'/run/conttests/createsize/')

            # initialize a python pool object then create the underlying
            # daos storage
            POOL = DaosPool(self.Context)
            POOL.create(createmode, createuid, creategid,
                        createsize, createsetid, None)

            # need a connection to create container
            POOL.connect(1 << 1)

            # create a container
            CONTAINER = DaosContainer(self.Context)
            CONTAINER.create(POOL.handle)

            # now open it
            CONTAINER.open()

            # do a query and compare the UUID returned from create with
            # that returned by query
            CONTAINER.query()

            if CONTAINER.get_uuid_str() != c_uuid_to_str(
                    CONTAINER.info.ci_uuid):
                self.fail("Container UUID did not match the one in info\n")

            # create an object and write some data into it
            thedata = "a string that I want to stuff into an object"
            thedatasize = 45
            dkey = "this is the dkey"
            akey = "this is the akey"

            oid, epoch = CONTAINER.write_an_obj(thedata, thedatasize,
                                                dkey, akey)

            # read the data back and make sure its correct
            thedata2 = CONTAINER.read_an_obj(thedatasize, dkey, akey,
                                             oid, epoch)
            if thedata != thedata2.value:
                print("thedata>" + thedata)
                print("thedata2>" + thedata2.value)
                self.fail("Write data 1, read it back, didn't match\n")

            # repeat above, but know that the write_an_obj call is advancing
            # the epoch so the original copy remains and the new copy is in
            # a new epoch.
            thedata3 = "a different string"
            thedatasize2 = 19
            # note using the same keys so writing to the same spot
            dkey = "this is the dkey"
            akey = "this is the akey"

            oid, epoch2 = CONTAINER.write_an_obj(thedata3, thedatasize2,
                                                 dkey, akey, oid)

            # read the data back and make sure its correct
            thedata4 = CONTAINER.read_an_obj(thedatasize2, dkey, akey,
                                             oid, epoch2)
            if thedata3 != thedata4.value:
                self.fail("Write data 2, read it back, didn't match\n")

            # the original data should still be there too
            thedata5 = CONTAINER.read_an_obj(thedatasize, dkey, akey,
                                             oid, epoch)
            if thedata != thedata5.value:
                self.fail("Write data 3, read it back, didn't match\n")

            CONTAINER.close()

            # wait a few seconds and then destroy
            time.sleep(5)
            CONTAINER.destroy()

            # cleanup the pool
            POOL.disconnect()
            POOL.destroy(1)

        except DaosApiError as e:
            print(e)
            print(traceback.format_exc())
            self.fail("Test was expected to pass but it failed.\n")
Exemple #13
0
    def test_tx_basics(self):
        """
        Perform I/O to an object in a container in 2 different transactions,
        verifying basic I/O and transactions in particular.

        NOTE: this was an epoch test and all I did was get it working with tx
        Not a good test at this point, need to redesign when tx is fully
        working.

        :avocado: tags=container,tx,basictx
        """
        pool = None

        try:
            # parameters used in pool create
            createmode = self.params.get("mode", '/run/poolparams/createmode/')
            createuid = os.geteuid()
            creategid = os.getegid()
            createsetid = self.params.get("setname",
                                          '/run/poolparams/createset/')
            createsize = self.params.get("size", '/run/poolparams/createsize/')

            # initialize a python pool object then create the underlying
            # daos storage
            pool = DaosPool(self.context)
            pool.create(createmode, createuid, creategid, createsize,
                        createsetid, None)

            # need a connection to create container
            pool.connect(1 << 1)

            # create a container
            container = DaosContainer(self.context)
            container.create(pool.handle)

            # now open it
            container.open()

            # do a query and compare the UUID returned from create with
            # that returned by query
            container.query()

            if container.get_uuid_str() != c_uuid_to_str(
                    container.info.ci_uuid):
                self.fail("Container UUID did not match the one in info\n")

            # create an object and write some data into it
            thedata = "a string that I want to stuff into an object"
            thedatasize = 45
            dkey = "this is the dkey"
            akey = "this is the akey"

            oid, txn = container.write_an_obj(thedata, thedatasize, dkey, akey,
                                              None, None, 2)

            # read the data back and make sure its correct
            thedata2 = container.read_an_obj(thedatasize, dkey, akey, oid, txn)
            if thedata != thedata2.value:
                print("thedata>" + thedata)
                print("thedata2>" + thedata2.value)
                self.fail("Write data 1, read it back, didn't match\n")

            # repeat above, but know that the write_an_obj call is advancing
            # the epoch so the original copy remains and the new copy is in
            # a new epoch.
            thedata3 = "a different string"
            thedatasize2 = 19
            # note using the same keys so writing to the same spot
            dkey = "this is the dkey"
            akey = "this is the akey"

            oid, tx2 = container.write_an_obj(thedata3, thedatasize2, dkey,
                                              akey, oid, None, 2)

            # read the data back and make sure its correct
            thedata4 = container.read_an_obj(thedatasize2, dkey, akey, oid,
                                             tx2)
            if thedata3 != thedata4.value:
                self.fail("Write data 2, read it back, didn't match\n")

            # transactions generally don't work this way but need to explore
            # an alternative to below code once model is complete, maybe
            # read from a snapshot or read from TX_NONE etc.

            # the original data should still be there too
            #thedata5 = container.read_an_obj(thedatasize, dkey, akey,
            #                                 oid, transaction)
            #if thedata != thedata5.value:
            #    self.fail("Write data 3, read it back, didn't match\n")

            container.close()

            # wait a few seconds and then destroy
            time.sleep(5)
            container.destroy()

        except DaosApiError as excep:
            print(excep)
            print(traceback.format_exc())
            self.fail("Test was expected to pass but it failed.\n")
        finally:
            # cleanup the pool
            if pool is not None:
                pool.disconnect()
                pool.destroy(1)
Exemple #14
0
    def test_destroy_withdata(self):
        """
        Test destroy and recreate one right after the other multiple times
        Should fail.

        :avocado: tags=pool,pooldestroy,destroydata
        """
        try:
            # write out a hostfile and start the servers with it
            self.hostlist = self.params.get("test_machines1", '/run/hosts/')
            hostfile = WriteHostFile.WriteHostFile(self.hostlist, self.tmp)

            ServerUtils.runServer(hostfile, self.server_group, self.basepath)

            # parameters used in pool create
            createmode = self.params.get("mode", '/run/poolparams/createmode/')
            createuid = self.params.get("uid", '/run/poolparams/createuid/')
            creategid = self.params.get("gid", '/run/poolparams/creategid/')
            createsetid = self.params.get("setname",
                                          '/run/poolparams/createset/')
            createsize = self.params.get("size", '/run/poolparams/createsize/')

            # initialize a python pool object then create the underlying
            # daos storage
            POOL = DaosPool(self.Context)
            POOL.create(createmode, createuid, creategid, createsize,
                        createsetid, None)

            # need a connection to create container
            POOL.connect(1 << 1)

            # create a container
            CONTAINER = DaosContainer(self.Context)
            CONTAINER.create(POOL.handle)

            POOL.disconnect()

            daosctl = self.basepath + '/install/bin/daosctl'

            write_cmd = (
                '{0} write-pattern -i {1} -l 0 -c {2} -p sequential'.format(
                    daosctl, c_uuid_to_str(POOL.uuid),
                    c_uuid_to_str(CONTAINER.uuid)))

            process.system_output(write_cmd)

            # blow it away
            POOL.destroy(1)

        except DaosApiError as e:
            print(e)
            print(traceback.format_exc())
            self.fail("create/destroy/create/destroy test failed.\n")

        except Exception as e:
            self.fail("Daos code segfaulted most likely.  Error: %s" % e)

        # no matter what happens cleanup
        finally:
            ServerUtils.stopServer(hosts=self.hostlist)
            os.remove(hostfile)
Exemple #15
0
    def test_evict(self):
        """
        Test evicting a client from a pool.

        Test creates 2 pools on 4 target (pool_tgt [0,1,2,3])
        and 1 pool on 2 targets (pool_tgt_ut [0,1]).  The pools are connected
        to and a container with data is created on all 3.
        The evict is done on connection to the pool with 2 targets.
        The handle is removed.
        The test verifies that the other two pools were not affected
        by the evict
        :avocado: tags=all,pool,pr,full_regression,small,poolevict
        """
        pool = []
        container = []
        non_pool_servers = []
        # Target list is configured so that the pools are across all servers
        # except the pool under test is created on half of the servers
        pool_tgt = [num for num in range(len(self.hostlist_servers))]
        pool_tgt_ut = [num for num in range(int(len(self.hostlist_servers)/2))]
        tlist = [pool_tgt, pool_tgt, pool_tgt_ut]
        pool_servers = [self.hostlist_servers[:len(tgt)] for tgt in tlist]
        non_pool_servers = [self.hostlist_servers[len(tgt):] for tgt in tlist]
        # Create Connected TestPool
        for count, target_list in enumerate(tlist):
            pool.append(self.connected_pool(pool_servers[count], target_list))
            if len(non_pool_servers[count]) > 0:
                self.assertFalse(
                    pool[count].check_files(non_pool_servers[count]),
                    "Pool # {} data detected on non pool servers {} ".format(
                        count+1, non_pool_servers[count]))

            self.log.info("Pool # %s is connected with handle %s",
                          count+1, pool[count].pool.handle.value)

            # Create a container
            # container.append(get_container(
            #     self.context, pool[count].pool, self.log))
            # cont_uuid.append(container[count].get_uuid_str())
            # self.log.info("Pool # %s has container %s",
            #               count+1, cont_uuid[count])
            container.append(TestContainer(pool[count]))
            container[count].get_params(self)
            container[count].create()
            container[count].write_objects(target_list[-1])

        try:
            self.log.info(
                "Attempting to evict clients from pool with UUID: %s",
                pool[-1].uuid)
            # Evict the last pool in the list
            pool[-1].pool.evict()
        except DaosApiError as result:
            self.fail(
                "Detected exception while evicting a client {}".format(
                    str(result)))

        for count in range(len(tlist)):
            # Check that all pool files still exist
            if pool[count].check_files(pool_servers[count]):
                self.log.info(
                    "Pool # %s with UUID %s still exists",
                    count+1, pool[count].uuid)
            else:
                self.fail(
                    "Pool # {} with UUID {} does not exists".format(
                        count+1, pool[count].uuid))

            # Verify connection to pools with pool_query; pool that was evicted
            # should fail the pool query because the handle was removed
            try:
                # Call daos api directly to avoid connecting to pool
                pool_info = pool[count].pool.pool_query()
            except DaosApiError as error:
                # expected error for evicted pool
                if count == len(tlist) - 1 and "-1002" in str(error):
                    self.log.info(
                        "Pool # %s was unable to query pool info due to "
                        "expected invalid handle error (-1002):\n\t%s",
                        count+1, error)
                # unexpected error from pool_query
                else:
                    self.fail(
                        "Pool # {} failed pool query: {}".format(
                            count+1, error))

                pool_info = None
            # Check that UUID of valid pools still exists
            if pool_info:
                if c_uuid_to_str(pool_info.pi_uuid) == pool[count].uuid:
                    self.log.info(
                        "Pool # %s UUID matches pool_info.pi_uuid %s",
                        count+1, pool[count].uuid)
                else:
                    self.fail(
                        "Pool # {} UUID does not matches pool_info.pi_uuid:  "
                        "{} != {}".format(
                            count+1, pool[count].uuid, c_uuid_to_str(
                                pool_info.pi_uuid)))