def actionGetFile(self):
        """
        Get file action.
        """
        idTestSet       = self.getIntParam(self.ksParamGetFileSetId,        iMin = 1);
        idFile          = self.getIntParam(self.ksParamGetFileId,           iMin = 0, iDefault = 0);
        fDownloadIt     = self.getBoolParam(self.ksParamGetFileDownloadIt,  fDefault = True);
        self._checkForUnknownParameters();

        #
        # Get the file info and open it.
        #
        oTestSet = TestSetData().initFromDbWithId(self._oDb, idTestSet);
        if idFile == 0:
            oTestFile = TestResultFileDataEx().initFakeMainLog(oTestSet);
        else:
            oTestFile = TestSetLogic(self._oDb).getFile(idTestSet, idFile);

        (oFile, oSizeOrError, _) = oTestSet.openFile(oTestFile.sFile, 'rb');
        if oFile is None:
            raise Exception(oSizeOrError);

        #
        # Send the file.
        #
        self._oSrvGlue.setHeaderField('Content-Type', oTestFile.getMimeWithEncoding());
        if fDownloadIt:
            self._oSrvGlue.setHeaderField('Content-Disposition', 'attachment; filename="TestSet-%d-%s"'
                                          % (idTestSet, oTestFile.sFile,));
        while True:
            abChunk = oFile.read(262144);
            if len(abChunk) == 0:
                break;
            self._oSrvGlue.writeRaw(abChunk);
        return self.ksDispatchRcAllDone;
    def _actionXmlResults(self):
        """ Implement submitting "XML" like test result stream. """
        #
        # Parameter validation.
        #
        sXml = self._getStringParam(constants.tbreq.XML_RESULT_PARAM_BODY,
                                    fStrip=False)
        self._checkForUnknownParameters()
        if not sXml:  # Used for link check by vboxinstaller.py on Windows.
            return self._resultResponse(constants.tbresp.STATUS_ACK)

        (oDb, oStatusData, _) = self._connectToDbAndValidateTb([
            TestBoxStatusData.ksTestBoxState_Testing,
            TestBoxStatusData.ksTestBoxState_GangTesting
        ])
        if oStatusData is None:
            return False

        #
        # Process the XML.
        #
        (sError, fUnforgivable) = TestResultLogic(oDb).processXmlStream(
            sXml, self._idTestSet)
        if sError is not None:
            oTestSet = TestSetData().initFromDbWithId(oDb,
                                                      oStatusData.idTestSet)
            self.writeToMainLog(oTestSet, '\n!!XML error: %s\n%s\n\n' % (
                sError,
                sXml,
            ))
            if fUnforgivable:
                return self._resultResponse(constants.tbresp.STATUS_NACK)
        return self._resultResponse(constants.tbresp.STATUS_ACK)
    def _actionLogMain(self):
        """ Implement submitting log entries to the main log file. """
        #
        # Parameter validation.
        #
        sBody = self._getStringParam(constants.tbreq.LOG_PARAM_BODY,
                                     fStrip=False)
        if not sBody:
            return self._resultResponse(constants.tbresp.STATUS_NACK)
        self._checkForUnknownParameters()

        (oDb, oStatusData, _) = self._connectToDbAndValidateTb([
            TestBoxStatusData.ksTestBoxState_Testing,
            TestBoxStatusData.ksTestBoxState_GangTesting
        ])
        if oStatusData is None:
            return False

        #
        # Write the text to the log file.
        #
        oTestSet = TestSetData().initFromDbWithId(oDb, oStatusData.idTestSet)
        self.writeToMainLog(oTestSet, sBody)
        ## @todo Overflow is a hanging offence, need to note it and fail whatever is going on...

        # Done.
        return self._resultResponse(constants.tbresp.STATUS_ACK)
Example #4
0
    def _doGangCleanup(self, oDb, oStatusData):
        """
        _doRequestCommand worker for handling a box in gang-cleanup.
        This will check if all testboxes has completed their run, pretending to
        be busy until that happens.  Once all are completed, resources will be
        freed and the testbox returns to idle state (we update oStatusData).
        """
        oStatusLogic = TestBoxStatusLogic(oDb)
        oTestSet = TestSetData().initFromDbWithId(oDb, oStatusData.idTestSet);
        if oStatusLogic.isWholeGangDoneTesting(oTestSet.idTestSetGangLeader):
            oDb.begin();

            GlobalResourceLogic(oDb).freeGlobalResourcesByTestBox(self._idTestBox, fCommit = False);
            TestBoxStatusLogic(oDb).updateState(self._idTestBox, TestBoxStatusData.ksTestBoxState_Idle, fCommit = False);

            oStatusData.tsUpdated = oDb.getCurrentTimestamp();
            oStatusData.enmState = TestBoxStatusData.ksTestBoxState_Idle;

            oDb.commit();
        return None;
    def _actionUpload(self):
        """ Implement uploading of files. """
        #
        # Parameter validation.
        #
        sName = self._getStringParam(constants.tbreq.UPLOAD_PARAM_NAME)
        sMime = self._getStringParam(constants.tbreq.UPLOAD_PARAM_MIME)
        sKind = self._getStringParam(constants.tbreq.UPLOAD_PARAM_KIND)
        sDesc = self._getStringParam(constants.tbreq.UPLOAD_PARAM_DESC)
        self._checkForUnknownParameters()

        (oDb, oStatusData, _) = self._connectToDbAndValidateTb([
            TestBoxStatusData.ksTestBoxState_Testing,
            TestBoxStatusData.ksTestBoxState_GangTesting
        ])
        if oStatusData is None:
            return False

        if len(sName) > 128 or len(sName) < 3:
            raise TestBoxControllerException('Invalid file name "%s"' %
                                             (sName, ))
        if re.match(r'^[a-zA-Z0-9_\-(){}#@+,.=]*$', sName) is None:
            raise TestBoxControllerException('Invalid file name "%s"' %
                                             (sName, ))

        if sMime not in [
                'text/plain',  #'text/html', 'text/xml',
                'application/octet-stream',
                'image/png',  #'image/gif', 'image/jpeg',
                #'video/webm', 'video/mpeg', 'video/mpeg4-generic',
        ]:
            raise TestBoxControllerException('Invalid MIME type "%s"' %
                                             (sMime, ))

        if sKind not in TestResultFileData.kasKinds:
            raise TestBoxControllerException('Invalid kind "%s"' % (sKind, ))

        if len(sDesc) > 256:
            raise TestBoxControllerException('Invalid description "%s"' %
                                             (sDesc, ))
        if not set(sDesc).issubset(set(string.printable)):
            raise TestBoxControllerException('Invalid description "%s"' %
                                             (sDesc, ))

        if ('application/octet-stream', {}) != self._oSrvGlue.getContentType():
            raise TestBoxControllerException(
                'Unexpected content type: %s; %s' %
                self._oSrvGlue.getContentType())

        cbFile = self._oSrvGlue.getContentLength()
        if cbFile <= 0:
            raise TestBoxControllerException(
                'File "%s" is empty or negative in size (%s)' %
                (sName, cbFile))
        if (cbFile + 1048575) / 1048576 > config.g_kcMbMaxUploadSingle:
            raise TestBoxControllerException(
                'File "%s" is too big %u bytes (max %u MiB)' % (
                    sName,
                    cbFile,
                    config.g_kcMbMaxUploadSingle,
                ))

        #
        # Write the text to the log file.
        #
        oTestSet = TestSetData().initFromDbWithId(oDb, oStatusData.idTestSet)
        oDstFile = TestSetLogic(oDb).createFile(oTestSet,
                                                sName=sName,
                                                sMime=sMime,
                                                sKind=sKind,
                                                sDesc=sDesc,
                                                cbFile=cbFile,
                                                fCommit=True)

        offFile = 0
        oSrcFile = self._oSrvGlue.getBodyIoStream()
        while offFile < cbFile:
            cbToRead = cbFile - offFile
            if cbToRead > 256 * 1024:
                cbToRead = 256 * 1024
            offFile += cbToRead

            abBuf = oSrcFile.read(cbToRead)
            oDstFile.write(abBuf)
            # pylint: disable=E1103
            del abBuf

        oDstFile.close()
        # pylint: disable=E1103

        # Done.
        return self._resultResponse(constants.tbresp.STATUS_ACK)