Ejemplo n.º 1
0
    def test_post_manifest_inprogress_ok(self):
        service = 'foo'
        manifest = 'blahblah'
        try:
            path = ServiceController.servicePath(service)
            if os.path.exists(path):
                if os.name == 'nt':
                    cmd = 'rm -r %s' % path
                    LOG.debug("running command %s" % cmd)
                    os.system(cmd)
                else:
                    shutil.rmtree(path)
            path = ServiceController.manifestPath(service)
            os.makedirs(path)
            path = ServiceController.installedPkgPath(service)
            os.makedirs(path)
            inProgressPath = ManifestCreate.inProgress(ManifestController.manifestPath(service, manifest))
            os.makedirs(inProgressPath)
            path = ServiceController.downloadedPkgPath(service)
            os.makedirs(path)
        except Exception as excep:
            LOG.warning('got an OS Exception - %s' % str(excep))

        createManifest(self, ["http://github.com/yubin154/cronusagent/blob/master/agent/agent/tests/unit/packages/pkgA-1.2.0.unix.cronus"], manifest = 'blahblah', createDirs = False)
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'blahblah'), 'pkgA')))
Ejemplo n.º 2
0
    def test_multiple_manifest_create(self):
        """ when a manifest creation is in progress for a service, another creation should block """
        packages = ["http://repository.qa.ebay.com/cronus/test-data/agent/pkgA-1.2.0.unix.cronus"]
        service = 'foo'
        manifest1 = 'bar'
        manifest2 = 'car'
        try:
            path = ServiceController.manifestPath(service)
            os.makedirs(path)
            path = ServiceController.installedPkgPath(service)
            os.makedirs(path)
        except Exception as excep:
            LOG.warning('got an OS Exception - %s' % str(excep))

        body = json.dumps({'package' : packages})
        response1 = self.app.post(url(controller = 'manifest', action = 'post', service = service, manifest = manifest1),
                                 headers = {'Content-Type' : 'application/json'},
                                 params = body)
        self.assertEquals(response1.status_int, 200, 'Manifest1 Post assert - should go through')

        try:
            response2 = self.app.post(url(controller = 'manifest', action = 'post', service = service, manifest = manifest2),
                                 headers = {'Content-Type' : 'application/json'},
                                 params = body)
            self.assertFalse(True, 'Expected an exception but did not get one!')
        except AppError:
            pass

        checkStatus(self, 'create manifest bar', response1, timeout = 25)
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'bar'), 'pkgA')))
        self.assertFalse(islink(os.path.join(ManifestController.manifestPath('foo', 'car'), 'pkgA')))
Ejemplo n.º 3
0
    def test_delete(self):
        createManifest(self)

        response = self.app.delete(url(controller = 'manifest', action = 'delete', service = "foo", manifest = "bar"),
                                   expect_errors = True)
        print '*************** = ' + response.body
        self.assertEquals(200, response.status_int)

        for _ in range(10):
            if not os.path.isdir(ManifestController.manifestPath('foo', 'bar')):
                break
            else:
                time.sleep(0.1)

        self.assertFalse(os.path.isdir(ManifestController.manifestPath('foo', 'bar')))
Ejemplo n.º 4
0
    def activatemanifest(self, service):
        """ activate manifest, if already active then skip """
        LOG.info('activateManifest for service(%s) with body: %s', service, request.body)
        try:
            appGlobal = config['pylons.app_globals']
            manifest = ''
            requestjson = json.loads(request.body)
            manifest = requestjson['manifest']
            force = asbool(requestjson['force']) if 'force' in requestjson else False
            
            if not force and manifestutil.getActiveManifest(service) == manifest:
                return doneResult(request, response, controller=self)
            
            else:
                mf_path = os.path.join(ManifestController.manifestPath(service, manifest))
                if (not os.path.exists(mf_path)):
                    return errorResult(request, response, Errors.ACTIVEMANIFEST_MANIFEST_MISSING,
                                   'Manifest(%s, %s) path missing' % (service, manifest),
                                   controller = self)
                LOG.debug('Manifest path exists: %s' % (mf_path))
                activateThread = ActivateManifest(appGlobal.threadMgr, service, manifest)
                self.injectJobCtx(activateThread)
                activateThread.start()
                activateThread.threadMgrEvent.wait()

            return statusResult(request, response, activateThread, controller = self)

        except Exception as excep:
            msg = 'Unknown error for activateManifest(%s/%s) - %s - %s' % (service, manifest, str(excep), traceback.format_exc(2))
            return errorResult(request, response, error = Errors.UNKNOWN_ERROR,
                               errorMsg = msg, controller = self)
Ejemplo n.º 5
0
    def reset(self, service):
        ''' Controller to reset service '''
        LOG.info('reset for service(%s)', service)

        try:
            appGlobal = config['pylons.app_globals']

            if not os.path.exists(
                    ManifestController.manifestPath(service, 'active')):
                return errorResult(request,
                                   response,
                                   Errors.ACTIVEMANIFEST_MANIFEST_MISSING,
                                   'Active Manifest(%s) path missing' %
                                   (service),
                                   controller=self)
            resetThread = ResetService(appGlobal.threadMgr, service)
            self.injectJobCtx(resetThread)
            resetThread.start()
            resetThread.threadMgrEvent.wait()

            return statusResult(request,
                                response,
                                resetThread,
                                controller=self)

        except Exception as excep:
            return errorResult(
                request,
                response,
                error=Errors.UNKNOWN_ERROR,
                errorMsg='Unknown error for restart service(%s) - %s - %s' %
                (service, str(excep), traceback.format_exc(2)),
                controller=self)
Ejemplo n.º 6
0
    def test_post2(self):
        # successful post
        createManifest(self)

        self.assertTrue(os.path.exists(os.path.join(PackageMgr.packagePath(), 'perlserver-1.0.0.unix.cronus')))
        self.assertTrue(os.path.exists(os.path.join(ServiceController.installedPkgPath('foo'), 'perlserver', '1.0.0.unix',
                                           'cronus', 'scripts', 'activate')))
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'bar'), 'perlserver')))
Ejemplo n.º 7
0
    def test_package_reuse(self):
        createManifest(self)
        body = json.dumps({'package' : ['/packages/perlserver']})
        body = self.app.post(url(controller = 'manifest', action = 'post', service = "foo", manifest = "baz"),
                                 headers = {'Content-Type' : 'application/json'},
                                 params = body, expect_errors = True)

        self.assertTrue(os.path.exists(os.path.join(PackageMgr.packagePath(), 'perlserver-1.0.0.unix.cronus')))
        self.assertTrue(os.path.exists(os.path.join(ServiceController.installedPkgPath('foo'), 'perlserver', '1.0.0.unix',
                                           'cronus', 'scripts', 'activate')))
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'bar'), 'perlserver')))

        for _ in range(10):
            if islink(os.path.join(ManifestController.manifestPath('foo', 'baz'), 'perlserver')):
                break
            time.sleep(1)

        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'baz'), 'perlserver')))
Ejemplo n.º 8
0
    def test_post3_pkg_already_installed(self):
        createManifest(self)

        # now lets remove the manifest path
        path = os.path.join(ManifestController.manifestPath('foo', 'bar'))
        if os.name == 'nt':
            cmd = 'rm -r %s' % path
            LOG.debug("running command %s" % cmd)
            os.system(cmd)
        else:
            shutil.rmtree(path)

        # now create the manifest again
        createManifest(self)

        self.assertTrue(os.path.exists(os.path.join(PackageMgr.packagePath(), 'perlserver-1.0.0.unix.cronus')))
        self.assertTrue(os.path.exists(os.path.join(ServiceController.installedPkgPath('foo'), 'perlserver', '1.0.0.unix',
                                           'cronus', 'scripts', 'activate')))
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'bar'), 'perlserver')))
Ejemplo n.º 9
0
    def test_post_without_service(self):

        body = json.dumps({'package' : ['http://github.com/yubin154/cronusagent/blob/master/agent/agent/tests/unit/packages/perlserver-1.0.0.unix.cronus']})
        response = self.app.post(url(controller = 'manifest', action = 'post', service = "foo", manifest = "bar"),
                                 headers = {'Content-Type' : 'application/json'},
                                 params = body)

        assert response.status_int == 200, 'Manifest Post assert'
        time.sleep(1)
        self.assertFalse(os.path.exists(ManifestController.manifestPath('foo', 'bar')))
Ejemplo n.º 10
0
 def __delAllExceptActiveManifests(self, service):
     '''
     Delete all manifests in the given service except active link and corresponding manifest (if one exists).
     Doesn't delete the corresponding dir in installed-packages (similar to 'delete manifest')
     '''
     manifests = ManifestController.getManifests(service)
     active = ManifestController.getActiveManifest(service)
     if active and len(active) != 0:  # 'active' can be none
         manifests.remove(active)
     for mft in manifests:
         mf_path = ManifestController.manifestPath(service, mft)
         ServiceDelete.deleteFolderContents(mf_path)
Ejemplo n.º 11
0
 def __delAllExceptActiveManifests(self, service):
     '''
     Delete all manifests in the given service except active link and corresponding manifest (if one exists).
     Doesn't delete the corresponding dir in installed-packages (similar to 'delete manifest')
     '''
     manifests = ManifestController.getManifests(service)
     active = ManifestController.getActiveManifest(service)
     if active and len(active) != 0: # 'active' can be none
         manifests.remove(active)
     for mft in manifests:
         mf_path = ManifestController.manifestPath(service, mft)
         ServiceDelete.deleteFolderContents(mf_path)
Ejemplo n.º 12
0
    def test_same_pkg_download_parallel(self):
        packages = ['http://repository.qa.ebay.com/cronus/test-data/agent/perlserver-1.0.0.unix.cronus']
        manifest1 = 'bar'
        manifest2 = 'blah'
        service1 = 'foo'
        service2 = 'lah'
        try:
            path = ServiceController.manifestPath(service1)
            os.makedirs(path)
            path = ServiceController.installedPkgPath(service1)
            os.makedirs(path)
            path = ServiceController.downloadedPkgPath(service1)
            os.makedirs(path)
            path = ServiceController.manifestPath(service2)
            os.makedirs(path)
            path = ServiceController.installedPkgPath(service2)
            os.makedirs(path)
            path = ServiceController.downloadedPkgPath(service2)
            os.makedirs(path)
        except Exception as excep:
            LOG.warning('got an OS Exception - %s' % str(excep))

        body = json.dumps({'package' : packages})
        response1 = self.app.post(url(controller = 'manifest', action = 'post', service = service1, manifest = manifest1),
                                 headers = {'Content-Type' : 'application/json'},
                                 params = body)
        assert response1.status_int == 200, 'Manifest Post assert'

        response2 = self.app.post(url(controller = 'manifest', action = 'post', service = service2, manifest = manifest2),
                                 headers = {'Content-Type' : 'application/json'},
                                 params = body)
        assert response2.status_int == 200, 'Manifest Post assert'

        checkStatus(self, 'create manifest bar', response1, timeout = 25)
        checkStatus(self, 'create manifest baz', response2, timeout = 25)

        self.assertTrue(os.path.exists(os.path.join(PackageMgr.packagePath(), 'perlserver-1.0.0.unix.cronus')))
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'bar'), 'perlserver')))
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('lah', 'blah'), 'perlserver')))
Ejemplo n.º 13
0
    def testGet(self):
        path = ManifestController.manifestPath('foo', 'bar')
        os.makedirs(path)

        path = ManifestController.manifestPath('foo', 'baz')
        os.makedirs(path)

        activePath = os.path.join(ServiceController.manifestPath('foo'),
                                  'active')
        symlink('bar', activePath)

        response = self.app.get(url(controller='service',
                                    service='foo',
                                    action='get'),
                                expect_errors=True)

        body = json.loads(response.body)
        print "************** response = %s" % body

        assert body['progress'] == 100
        assert body['result']['activemanifest'] == 'bar'
        assert body['result']['manifest'] == ['bar', 'baz']
Ejemplo n.º 14
0
    def _getBuiltThread(self, service, manifest, package, exeName):
        """ here """
        # figure out the path to the cronus scripts
        uname = pylons.config['app_user_account']
        execPath = os.path.join(ManifestController.manifestPath(service, manifest), package, 'cronus', 'scripts', exeName)
        if (isHigherPrivilegeService(service)):
            cmd = execPath
        else:
            cmd = utils.sudoCmd([execPath], uname)

        dummy = not os.path.exists(execPath)
        execThread = ExecThread(self._threadMgr, cmd)
        copycontexts(self, execThread, contextutils.CTX_NAMES)
        return execThread, dummy
Ejemplo n.º 15
0
    def test_post3_already_installed_manifest(self):
        createManifest(self)

        self.assertTrue(os.path.exists(os.path.join(PackageMgr.packagePath(), 'perlserver-1.0.0.unix.cronus')))
        self.assertTrue(os.path.exists(os.path.join(ServiceController.installedPkgPath('foo'), 'perlserver', '1.0.0.unix',
                                           'cronus', 'scripts', 'activate')))
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'bar'), 'perlserver')))


        body = json.dumps({'package' : ['http://github.com/yubin154/cronusagent/blob/master/agent/agent/tests/unit/packages/perlserver-1.0.0.unix.cronus']})
        response = self.app.post(url(controller = 'manifest', action = 'post', service = "foo", manifest = "bar"),
                                 headers = {'Content-Type' : 'application/json'},
                                 params = body, expect_errors = True)
        self.assertEquals(201, response.status_int, 'Manifest Post assert')
        body = json.loads(response.body)
        assert response.status_int == 201, 'Manifest Post assert'
Ejemplo n.º 16
0
    def _getBuiltThread(self, service, manifest, package, exeName):
        """ here """
        # figure out the path to the cronus scripts
        uname = pylons.config['app_user_account']
        execPath = os.path.join(
            ManifestController.manifestPath(service, manifest), package,
            'cronus', 'scripts', exeName)
        if (isHigherPrivilegeService(service)):
            cmd = execPath
        else:
            cmd = utils.sudoCmd([execPath], uname)

        dummy = not os.path.exists(execPath)
        execThread = ExecThread(self._threadMgr, cmd)
        copycontexts(self, execThread, contextutils.CTX_NAMES)
        return execThread, dummy
Ejemplo n.º 17
0
    def activatemanifest(self, service):
        """ activate manifest, if already active then skip """
        LOG.info('activateManifest for service(%s) with body: %s', service,
                 request.body)
        try:
            appGlobal = config['pylons.app_globals']
            manifest = ''
            requestjson = json.loads(request.body)
            manifest = requestjson['manifest']
            force = asbool(
                requestjson['force']) if 'force' in requestjson else False

            if not force and manifestutil.getActiveManifest(
                    service) == manifest:
                return doneResult(request, response, controller=self)

            else:
                mf_path = os.path.join(
                    ManifestController.manifestPath(service, manifest))
                if (not os.path.exists(mf_path)):
                    return errorResult(request,
                                       response,
                                       Errors.ACTIVEMANIFEST_MANIFEST_MISSING,
                                       'Manifest(%s, %s) path missing' %
                                       (service, manifest),
                                       controller=self)
                LOG.debug('Manifest path exists: %s' % (mf_path))
                activateThread = ActivateManifest(appGlobal.threadMgr, service,
                                                  manifest)
                self.injectJobCtx(activateThread)
                activateThread.start()
                activateThread.threadMgrEvent.wait()

            return statusResult(request,
                                response,
                                activateThread,
                                controller=self)

        except Exception as excep:
            msg = 'Unknown error for activateManifest(%s/%s) - %s - %s' % (
                service, manifest, str(excep), traceback.format_exc(2))
            return errorResult(request,
                               response,
                               error=Errors.UNKNOWN_ERROR,
                               errorMsg=msg,
                               controller=self)
Ejemplo n.º 18
0
    def test_inprogress_pkg_download(self):
        service = 'foo'
        try:
            path = ServiceController.manifestPath(service)
            os.makedirs(path)
            path = ServiceController.installedPkgPath(service)
            os.makedirs(path)
            path = ServiceController.downloadedPkgPath(service)
            os.makedirs(path)
            inprogressPath = os.path.join(PackageMgr.packagePath(), 'perlserver-1.0.0.unix.cronus.inprogress')
            inprogressFile = open(inprogressPath, 'w')
            inprogressFile.write('somegarbage')
            inprogressFile.close()
        except Exception as excep:
            LOG.warning('got an OS Exception - %s' % str(excep))

        createManifest(self)
        self.assertTrue(os.path.exists(os.path.join(PackageMgr.packagePath(), 'perlserver-1.0.0.unix.cronus')))
        self.assertTrue(islink(os.path.join(ManifestController.manifestPath('foo', 'bar'), 'perlserver')))
Ejemplo n.º 19
0
    def reset(self, service):
        ''' Controller to reset service '''
        LOG.info('reset for service(%s)', service)

        try:
            appGlobal = config['pylons.app_globals']

            if not os.path.exists(ManifestController.manifestPath(service, 'active')):
                return errorResult(request, response, Errors.ACTIVEMANIFEST_MANIFEST_MISSING,
                                   'Active Manifest(%s) path missing' % (service),
                                   controller = self)
            resetThread = ResetService(appGlobal.threadMgr, service)
            self.injectJobCtx(resetThread)
            resetThread.start()
            resetThread.threadMgrEvent.wait()

            return statusResult(request, response, resetThread, controller = self)

        except Exception as excep:
            return errorResult(request, response, error = Errors.UNKNOWN_ERROR,
                               errorMsg = 'Unknown error for restart service(%s) - %s - %s' %
                               (service, str(excep), traceback.format_exc(2)),
                               controller = self)
Ejemplo n.º 20
0
    def testDelete(self):
        def deleteTestDir(service):
            LOG.debug('************ service = %s' % service)
            response = self.app.delete(url(controller='service', service=service, action='delete'), expect_errors = True)
            # make sure the responses are correct
            LOG.debug('status = ' + str(response.status_int))
#            assert response.status_int == 500, "HTTP response != 500"

        def makeTestDir(path):
            os.makedirs(path)
            os.makedirs(os.path.join(path, 'manifests'))
            os.makedirs(os.path.join(path, 'installed-packages'))

        def createManifests(mf_path):
            os.makedirs(os.path.join(mf_path, 'm1.0', 'dummy_dir1.0'))
            os.makedirs(os.path.join(mf_path, 'm2.0', 'dummy_dir2.0'))
            latest = os.path.join(mf_path, 'm3.0')
            os.makedirs(os.path.join(latest, 'dummy_dir3.0'))

            utils.symlink(latest, os.path.join(mf_path, 'active'))

            return (['m1.0', 'm2.0', 'm3.0'], 'm3.0')

        def makePackageContent(path, pkgPath, pkgPropPath):
            pkgFile = file(pkgPath, 'w')
            for index in range(10):
                pkgFile.write(('%s%s') % (index, index))
            pkgFile.close()

            pkgFile = file(pkgPropPath, 'w')
            for index in range(10):
                pkgFile.write(('%s%s') % (index, index))
            pkgFile.close()
            uname = pylons.config['agent_user_account']
            TestCleanupController.rchown(path, uname)

        def createTestThread(serviceName):
            appGlobal = config['pylons.app_globals']
            testTh = WaitThread(appGlobal.threadMgr, ServiceController.serviceCat(serviceName))
            testTh.start()
            return testTh

        def startTestProcess():
            cmd = utils.sudoCmd(["sleep", "5"], pylons.config['app_user_account'])
            return Popen(cmd)

        if os.name == 'nt':
            LOG.warning('Services cleanup not supported on windows. Skipping test...')
            return

        path1 = os.path.join(pylons.config['agent_root'], 'service_nodes', 'foo')
        path2 = os.path.join(pylons.config['agent_root'], 'service_nodes', 'bar')
        path3 = os.path.join(pylons.config['agent_root'], 'service_nodes', 'agent')

        deleteTestDir('foo')
        deleteTestDir('bar')
        deleteTestDir('agent')

        # make dirs
        makeTestDir(path1)
        makeTestDir(path2)
        makeTestDir(path3)
        all_mf, active_mf = createManifests(ServiceController.manifestPath('agent'))

        uname = pylons.config['agent_user_account']
        TestCleanupController.rchown(ServiceController.serviceRootPath(), uname)

        pkgDir = PackageMgr.packagePath()
        pkgPath = os.path.join(pkgDir, "foo.cronus")
        pkgPropPath = os.path.join(pkgDir, "foo.cronus.prop")
        makePackageContent(pkgDir, pkgPath, pkgPropPath)

        # create threads
        testThFoo = createTestThread('foo')
        testThBar = createTestThread('bar')
        testThAgent = createTestThread('agent')

        # start process
        process = startTestProcess()

        # start testing
        LOG.debug('************ start cleanup')
        response = self.app.post(url(controller='cleanup', action='post'))
        LOG.debug ('Delete response body = ' + response.body)
        body = json.loads(response.body)

        tm = time.time()
        while (tm + 10 > time.time()):
            response = self.app.get(body['status'], expect_errors = True)
            LOG.debug ('Status response body = ' + response.body)
            body = json.loads(response.body)
            print body
            if (body['progress'] == 100):
                break
            time.sleep(0.1)

        # make sure the responses are correct
        LOG.debug('status = ' + str(response.status_int))
        assert response.status_int == 200, "HTTP response != 200"

        time.sleep(0.1)
        assert not os.path.exists(path1), 'service foo does exist or is not a directory'
        assert not os.path.exists(path2), 'service bar does exist or is not a directory'
        assert os.path.exists(path3), 'service agent does NOT exist or is not a directory'
        assert not testThFoo.isAlive(), 'thread Foo is still alive'
        assert not testThBar.isAlive(), 'thread Bar is still alive'
        assert not testThAgent.isAlive(), 'thread Agent is still alive'
        assert not os.path.exists(pkgPath), 'package foo exists'
        assert not os.path.exists(pkgPropPath), 'package prop foo exists'
        assert os.path.exists(pkgDir), 'package directory does not exist'
        # ensure agent cleanup is proper
        active_mf_path = ManifestController.manifestPath('agent', active_mf)
        active_link = os.path.join(ServiceController.manifestPath('agent'), 'active')
        all_mf.remove(active_mf)
        actual_active_mf_path = utils.readlink(active_link)

        self.assertTrue(os.path.exists(active_mf_path), 'active agent manifest got deleted but shouldn\t have')
        self.assertTrue(os.path.exists(active_link), 'agent active link missing')
        self.assertEqual(active_mf_path, actual_active_mf_path, 'agent active link pointing to some wrong manifest; link broken?')
        for mf in all_mf:
            agnt_mf_path = ManifestController.manifestPath('agent', mf)
            self.assertFalse(os.path.exists(agnt_mf_path), 'non active agent mf %s should have been deleted' % mf)
Ejemplo n.º 21
0
    def doRun(self):
        """ Main body of the thread

        Progress Info:
        Look at the list of packages this manifest has and figure out the progress of this manifest
        Progress 1 = manifest directory created
        Progress 2-80 = all packages downloaded
        Progress 81-99 = all packages untarred
        Progress 100 = all links done
        """
        inProgressPath = ManifestCreate.inProgress(ManifestController.manifestPath(self.__service, self.__manifest))
        try:
            if self.__service != 'agent':
                utils.checkDiskFull()

            installedPkgPath = ServiceController.installedPkgPath(self.__service)

            # This shouldn'trn happen but make sure there isn'trn already a manifest directory in progress
            if (os.path.isdir(inProgressPath)):
                # probably another manifest create thread died out half way.
                # Cleanup and reattempt manifest creation
                LOG.debug('Manifest inprogress found for service/manifest (%s/%s). Will cleanup and retry' % (self.__service, self.__manifest))
                shutil.rmtree(inProgressPath)

            # make sure that the service path and installed package path exists
            if (not os.path.isdir(ServiceController.manifestPath(self.__service)) or
                not os.path.isdir(ServiceController.installedPkgPath(self.__service))):
                errCode = Errors.SERVICE_NOT_FOUND
                msg = 'Service (%s) for manifest (%s) not found' % (self.__service, self.__manifest)
                self._updateStatus(httpStatus = 500, error = errCode, errorMsg = msg)
                return

            # ok create the manifest path
            os.mkdir(inProgressPath)

            self._updateProgress(1)

            # figure out which of the packages are already there
            remainingPackages = {}
            for pkgUri in self.__packages:
                pkgDict = PackageUtil.parseUri(pkgUri)
                pkgPath = os.path.join(installedPkgPath, pkgDict['packageName'], pkgDict['packageVersion'])
                pkgName = pkgDict['packageName']
                if (not os.path.exists(pkgPath)) or ((self.__forcePackages is not None) and pkgName in self.__forcePackages):
                    remainingPackages[pkgUri] = pkgDict
                else:
                    symlink(pkgPath, os.path.join(inProgressPath, pkgDict['packageName']))

            if self.__attemptDownload:
                # now make sure all the packages are downloaded
                try:
                    self._downloadPackages(remainingPackages.keys(), skipProp = self.__skipProp)
                except AgentException as exc:
                    # check if it is download error, then modify exception appropriately
                    if exc.getCode() == Errors.DC_FAILED_DOWNLOAD:
                        exc = AgentException(Errors.MANIFEST_PACKAGE_DOWNLOAD_FAILED,
                                            'Manifest (%s/%s) failed downloading package - %s'
                                            % (self.__service, self.__manifest, exc.getMsg()))
                    raise exc
            else:
                if len(remainingPackages) > 0:
                    raise AgentException(Errors.MANIFEST_PACKAGE_DOES_NOT_EXIST,
                                          'Create Manifest (%s/%s) failed since package is not present and download has been disabled'
                                          % (self.__service, self.__manifest))

            LOG.info('Completed download all packages for (%s/%s)' % (self.__service, self.__manifest))

            # now untar the packages
            import re
            pkgSuffix = '.%s' % re.sub(r"\W", "", self.__manifest)
            self._untarPackages(remainingPackages, self.__service, ServiceController.installedPkgPath(self.__service), 0, self.__forcePackages, pkgSuffix)
            LOG.info('Completed untar all packages for (%s/%s)' % (self.__service, self.__manifest))

            # now create the links
            for pkgDict in remainingPackages.itervalues():
                pkgPath = os.path.join(installedPkgPath, pkgDict['packageName'], pkgDict['packageVersion'])
                linkPath = os.path.join(inProgressPath, pkgDict['packageName'])
                # validate target folder does exist
                if not os.path.exists(pkgPath):
                    raise AgentException(Errors.PACKAGE_PATH_ERROR, 'invalid untarred package at %s' % pkgPath)
                symlink(pkgPath, linkPath)

            # now move the inProgressPath to the final path
            manifestContentPath = ManifestController.manifestContentPath(self.__service, self.__manifest)

            os.rename(inProgressPath, ManifestController.manifestPath(self.__service, self.__manifest))

            mfContentsFile = file(manifestContentPath, 'w')
            for pkgUri in self.__packages:
                mfContentsFile.write(('%s%s') % (pkgUri, os.linesep))
            mfContentsFile.close()
            LOG.info('Completed create manifest directories for (%s/%s)' % (self.__service, self.__manifest))

            LOG.info('Completed create manifest for (%s/%s)' % (self.__service, self.__manifest))
            self._updateStatus(progress = 100)

        except AgentException as exc:
            LOG.info(exc.getMsg())
            self._updateStatus(httpStatus = 500, error = exc.getCode(), errorMsg = exc.getMsg())
            
        except Exception as exc:
            errCode = Errors.UNKNOWN_ERROR
            msg = 'Unknown error for (%s/%s) - %s - %s' % (self.__service, self.__manifest,
                                                           str(exc), traceback.format_exc(2))
            LOG.info(msg)
            self._updateStatus(httpStatus = 500, error = errCode, errorMsg = msg)
        finally:
            # clean up intermediate progress
            try:
                shutil.rmtree(inProgressPath)
            except OSError:
                pass
Ejemplo n.º 22
0
    def testDelete(self):
        def deleteTestDir(service):
            LOG.debug('************ service = %s' % service)
            response = self.app.delete(url(controller='service',
                                           service=service,
                                           action='delete'),
                                       expect_errors=True)
            # make sure the responses are correct
            LOG.debug('status = ' + str(response.status_int))
#            assert response.status_int == 500, "HTTP response != 500"

        def makeTestDir(path):
            os.makedirs(path)
            os.makedirs(os.path.join(path, 'manifests'))
            os.makedirs(os.path.join(path, 'installed-packages'))

        def createManifests(mf_path):
            os.makedirs(os.path.join(mf_path, 'm1.0', 'dummy_dir1.0'))
            os.makedirs(os.path.join(mf_path, 'm2.0', 'dummy_dir2.0'))
            latest = os.path.join(mf_path, 'm3.0')
            os.makedirs(os.path.join(latest, 'dummy_dir3.0'))

            utils.symlink(latest, os.path.join(mf_path, 'active'))

            return (['m1.0', 'm2.0', 'm3.0'], 'm3.0')

        def makePackageContent(path, pkgPath, pkgPropPath):
            pkgFile = file(pkgPath, 'w')
            for index in range(10):
                pkgFile.write(('%s%s') % (index, index))
            pkgFile.close()

            pkgFile = file(pkgPropPath, 'w')
            for index in range(10):
                pkgFile.write(('%s%s') % (index, index))
            pkgFile.close()
            uname = pylons.config['agent_user_account']
            TestCleanupController.rchown(path, uname)

        def createTestThread(serviceName):
            appGlobal = config['pylons.app_globals']
            testTh = WaitThread(appGlobal.threadMgr,
                                ServiceController.serviceCat(serviceName))
            testTh.start()
            return testTh

        def startTestProcess():
            cmd = utils.sudoCmd(["sleep", "5"],
                                pylons.config['app_user_account'])
            return Popen(cmd)

        if os.name == 'nt':
            LOG.warning(
                'Services cleanup not supported on windows. Skipping test...')
            return

        path1 = os.path.join(pylons.config['agent_root'], 'service_nodes',
                             'foo')
        path2 = os.path.join(pylons.config['agent_root'], 'service_nodes',
                             'bar')
        path3 = os.path.join(pylons.config['agent_root'], 'service_nodes',
                             'agent')

        deleteTestDir('foo')
        deleteTestDir('bar')
        deleteTestDir('agent')

        # make dirs
        makeTestDir(path1)
        makeTestDir(path2)
        makeTestDir(path3)
        all_mf, active_mf = createManifests(
            ServiceController.manifestPath('agent'))

        uname = pylons.config['agent_user_account']
        TestCleanupController.rchown(ServiceController.serviceRootPath(),
                                     uname)

        pkgDir = PackageMgr.packagePath()
        pkgPath = os.path.join(pkgDir, "foo.cronus")
        pkgPropPath = os.path.join(pkgDir, "foo.cronus.prop")
        makePackageContent(pkgDir, pkgPath, pkgPropPath)

        # create threads
        testThFoo = createTestThread('foo')
        testThBar = createTestThread('bar')
        testThAgent = createTestThread('agent')

        # start process
        process = startTestProcess()

        # start testing
        LOG.debug('************ start cleanup')
        response = self.app.post(url(controller='cleanup', action='post'))
        LOG.debug('Delete response body = ' + response.body)
        body = json.loads(response.body)

        tm = time.time()
        while (tm + 10 > time.time()):
            response = self.app.get(body['status'], expect_errors=True)
            LOG.debug('Status response body = ' + response.body)
            body = json.loads(response.body)
            print body
            if (body['progress'] == 100):
                break
            time.sleep(0.1)

        # make sure the responses are correct
        LOG.debug('status = ' + str(response.status_int))
        assert response.status_int == 200, "HTTP response != 200"

        time.sleep(0.1)
        assert not os.path.exists(
            path1), 'service foo does exist or is not a directory'
        assert not os.path.exists(
            path2), 'service bar does exist or is not a directory'
        assert os.path.exists(
            path3), 'service agent does NOT exist or is not a directory'
        assert not testThFoo.isAlive(), 'thread Foo is still alive'
        assert not testThBar.isAlive(), 'thread Bar is still alive'
        assert not testThAgent.isAlive(), 'thread Agent is still alive'
        assert not os.path.exists(pkgPath), 'package foo exists'
        assert not os.path.exists(pkgPropPath), 'package prop foo exists'
        assert os.path.exists(pkgDir), 'package directory does not exist'
        # ensure agent cleanup is proper
        active_mf_path = ManifestController.manifestPath('agent', active_mf)
        active_link = os.path.join(ServiceController.manifestPath('agent'),
                                   'active')
        all_mf.remove(active_mf)
        actual_active_mf_path = utils.readlink(active_link)

        self.assertTrue(
            os.path.exists(active_mf_path),
            'active agent manifest got deleted but shouldn\t have')
        self.assertTrue(os.path.exists(active_link),
                        'agent active link missing')
        self.assertEqual(
            active_mf_path, actual_active_mf_path,
            'agent active link pointing to some wrong manifest; link broken?')
        for mf in all_mf:
            agnt_mf_path = ManifestController.manifestPath('agent', mf)
            self.assertFalse(
                os.path.exists(agnt_mf_path),
                'non active agent mf %s should have been deleted' % mf)