Пример #1
0
    def __updateExistingItem(self, item, newSrcAbsPath, newDstRelPath,
                             userLogin):
        logger.info("__updateExistingItem with args={}".format(
            (item, newSrcAbsPath, newDstRelPath, userLogin)))

        if newSrcAbsPath is None:
            assert newDstRelPath is None, \
            "Both newSrcAbsPath and newDstRelPath args should be None."
        else:
            assert not hlp.is_none_or_empty(newSrcAbsPath)
            assert not hlp.is_none_or_empty(newDstRelPath), \
            "Both newSrcAbsPath and newDstRelPath args should be not empty."

        persistentItem = self._session.query(db.Item).get(item.id)

        self.__updatePlainDataMembers(item, persistentItem)
        self.__updateTags(item, persistentItem, userLogin)
        self.__updateFields(item, persistentItem, userLogin)
        self.__updateDataRefAndFilesystem(item, persistentItem, newSrcAbsPath,
                                          newDstRelPath, userLogin)
        self._session.commit()

        self._session.refresh(persistentItem)
        self._session.expunge(persistentItem)
        return persistentItem
Пример #2
0
    def buttonAddDataRef(self):

        file = QtGui.QFileDialog.getOpenFileName(self,
                                                 self.tr("Select a file to link with the Item."))
        if is_none_or_empty(file):
            return

        #Suggest a title for the Item, if it has not any title yet
        title = self.ui.lineEdit_title.text()
        if is_none_or_empty(title):
            self.ui.lineEdit_title.setText(os.path.basename(file))

        data_ref = DataRef(objType=DataRef.FILE, url=file)
        self.item.data_ref = data_ref

        assert(os.path.isabs(data_ref.url))
        self.ui.fileAbsPath.setText(data_ref.url)

        dstRelPath = None
        if is_internal(data_ref.url, self.repoBasePath):
            dstRelPath = os.path.relpath(data_ref.url, self.repoBasePath)
        else:
            dstRelPath = os.path.basename(data_ref.url)
        dstRelPath = os.path.join(".", dstRelPath)

        self.ui.fileRelPath.setText(dstRelPath)
Пример #3
0
    def buttonAddDataRef(self):

        file = QtGui.QFileDialog.getOpenFileName(
            self, self.tr("Select a file to link with the Item."))
        if is_none_or_empty(file):
            return

        #Suggest a title for the Item, if it has not any title yet
        title = self.ui.lineEdit_title.text()
        if is_none_or_empty(title):
            self.ui.lineEdit_title.setText(os.path.basename(file))

        data_ref = DataRef(objType=DataRef.FILE, url=file)
        self.item.data_ref = data_ref

        assert (os.path.isabs(data_ref.url))
        self.ui.fileAbsPath.setText(data_ref.url)

        dstRelPath = None
        if is_internal(data_ref.url, self.repoBasePath):
            dstRelPath = os.path.relpath(data_ref.url, self.repoBasePath)
        else:
            dstRelPath = os.path.basename(data_ref.url)
        dstRelPath = os.path.join(".", dstRelPath)

        self.ui.fileRelPath.setText(dstRelPath)
Пример #4
0
    def hash(self):
        '''
            Calculates and returns a hash of the Item instance state.
        '''
        text = ""

        if not is_none_or_empty(self.title):
            text += self.title

        if not is_none_or_empty(self.user_login):
            text += self.user_login

        if self.date_created is not None:
            text += str(self.date_created)

        tag_names = []
        for item_tag in self.item_tags:
            tag_names.append(item_tag.tag.name)
        tag_names.sort()

        for tag_name in tag_names:
            text += tag_name

        field_vals = []
        for item_field in self.item_fields:
            field_vals.append(item_field.field.name + str(item_field.field_value))
        field_vals.sort()

        for field_val in field_vals:
            text += field_val

        return hashlib.sha1(text.encode("utf-8")).hexdigest()
Пример #5
0
    def hash(self):
        '''
            Calculates and returns a hash of the Item instance state.
        '''
        text = ""

        if not is_none_or_empty(self.title):
            text += self.title

        if not is_none_or_empty(self.user_login):
            text += self.user_login

        if self.date_created is not None:
            text += str(self.date_created)

        tag_names = []
        for item_tag in self.item_tags:
            tag_names.append(item_tag.tag.name)
        tag_names.sort()

        for tag_name in tag_names:
            text += tag_name

        field_vals = []
        for item_field in self.item_fields:
            field_vals.append(item_field.field.name +
                              str(item_field.field_value))
        field_vals.sort()

        for field_val in field_vals:
            text += field_val

        return hashlib.sha1(text.encode("utf-8")).hexdigest()
Пример #6
0
    def __saveNewItem(self, item, srcAbsPath=None, dstRelPath=None):
        #We do not need any info, that can be in item.data_ref object at this point.
        #But if it is not None, it may break the creation of tags/fields.
        #Don't worry, item.data_ref will be assigned a new DataRef instance later (if required).
        item.data_ref = None

        user_login = item.user_login
        if hlp.is_none_or_empty(user_login):
            raise err.AccessError(
                "Argument user_login shouldn't be null or empty.")

        user = self._session.query(db.User).get(user_login)
        if user is None:
            raise err.AccessError(
                "User with login {} doesn't exist.".format(user_login))

        #Making copies of tags and fields
        item_tags_copy = item.item_tags[:]
        item_fields_copy = item.item_fields[:]

        # Storing the item without tags and fields (for now)
        del item.item_tags[:]
        del item.item_fields[:]
        self._session.add(item)
        self._session.flush()

        tagNamesToAdd = map(lambda itag: itag.tag.name, item_tags_copy)
        operations.ItemOperations.addTags(self._session, item, tagNamesToAdd,
                                          user_login)

        nameValuePairsToAdd = map(
            lambda ifield: (ifield.field.name, ifield.field_value),
            item_fields_copy)
        operations.ItemOperations.addOrUpdateFields(self._session, item,
                                                    nameValuePairsToAdd,
                                                    user_login)

        isDataRefRequired = not hlp.is_none_or_empty(srcAbsPath)
        if isDataRefRequired:
            operations.ItemOperations.addUntrackedFile(self._session, item,
                                                       self._repoBasePath,
                                                       srcAbsPath, dstRelPath,
                                                       user_login)

        self._session.commit()
        item_id = item.id
        self._session.expunge(item)
        return item_id
Пример #7
0
    def keyPressEvent(self, event):
        cursor = self.textCursor()
        cursor.select(QtGui.QTextCursor.WordUnderCursor)
        word = cursor.selectedText()
        word = word if not is_none_or_empty(word) else ""

        if self.completer is not None and \
        event.modifiers() == Qt.ControlModifier and event.key() == Qt.Key_Space:
            self.completer.filter(word)
            self.show_completer()
            super(TextEdit, self).keyPressEvent(event)
            #TODO When user press Ctrl+Space, completer is shown, but TextEdit cursor becomes hidden! Why?

        elif self.one_line and event.key() in [Qt.Key_Enter, Qt.Key_Return]:
            #This signal is for QLineEdit behaviour
            self.emit(QtCore.SIGNAL("returnPressed()"))

        elif event.key() in [
                Qt.Key_Backspace, Qt.Key_Delete, Qt.Key_Up, Qt.Key_Down,
                Qt.Key_Left, Qt.Key_Right, Qt.Key_End, Qt.Key_Home,
                Qt.Key_Shift, Qt.Key_Alt, Qt.Key_Control
        ]:
            super(TextEdit, self).keyPressEvent(event)

        elif len(word) > 0:
            self.completer.filter(word)
            if self.completer.count() > 0:
                self.show_completer()
            super(TextEdit, self).keyPressEvent(event)

        else:
            super(TextEdit, self).keyPressEvent(event)
Пример #8
0
    def buttonMoveFile(self):
        try:
            if self.item.data_ref is None:
                raise Exception(self.tr("You must add a file first."))

            directory = QtGui.QFileDialog.getExistingDirectory(
                self, self.tr("Select destination path within repository"),
                self.repoBasePath)
            if is_none_or_empty(directory):
                return

            if not is_internal(directory, self.repoBasePath):
                raise MsgException(
                    self.tr("Chosen directory is out of active repository."))

            new_dst_path = os.path.relpath(directory, self.repoBasePath)
            if not new_dst_path.startswith("."):
                new_dst_path = os.path.join(".", new_dst_path)

            newDstRelPath = os.path.join(
                new_dst_path, os.path.basename(self.item.data_ref.url))
            self.ui.fileRelPath.setText(newDstRelPath)

        except Exception as ex:
            show_exc_info(self, ex)
Пример #9
0
    def mouseMoveEvent(self, e):
        #Get current word under cursor
        cursor = self.cursorForPosition(e.pos())
        cursor.select(QtGui.QTextCursor.WordUnderCursor)
        word = cursor.selectedText()

        #print("pos={}".format(cursor.position()))
        if word == "ALL" and cursor.position() <= 3:
            self.keywordAll = True
        else:
            self.keywordAll = False

        # If current word has changed or cleared --- set default formatting
        if word != self.word or is_none_or_empty(word):
            cursor1 = self.textCursor()
            cursor1.select(QtGui.QTextCursor.Document)
            fmt = QtGui.QTextCharFormat()
            fmt.setForeground(QtGui.QBrush(QtGui.QColor(self.text_color)))
            cursor1.mergeCharFormat(fmt)
            self.word = None

        # If current word has changed --- highlight it
        if word != self.word:
            fmt = QtGui.QTextCharFormat()
            fmt.setForeground(QtGui.QBrush(QtGui.QColor(self.hl_text_color)))
            cursor.mergeCharFormat(fmt)
            self.word = word

        # NOTE: There is a problem when tag contains a spaces or dashes (and other special chars).
        # word is detected incorrectly in such a case.
        # TODO: Have to fix this problem
        return super(TagCloudTextEdit, self).mouseMoveEvent(e)
Пример #10
0
    def __onButtonNewCategoryClicked(self):
        try:
            categoriesCountBefore = self.ui.comboBoxCategory.count()

            text, isOk = self.__dialogs.execGetTextDialog(self,
                self.tr("Input Dialog"), self.tr("Enter the name for new category of files."),
                defaultText="Category_{}".format(categoriesCountBefore))
            if not isOk:
                return

            if helpers.is_none_or_empty(text):
                raise MsgException(self.tr("Category name should not be empty"))

            if self.__isCategoryExists(text):
                raise MsgException(self.tr("Category with given name already exists. Choose different name."))

            appDescription = ExtAppDescription(text, "<path to executable> %f", [".mp3", ".ogg"])
            self.__extAppMgrState.appDescriptions.append(appDescription)

            self.ui.comboBoxCategory.addItem(text)
            categoriesCountAfter = self.ui.comboBoxCategory.count()
            self.ui.comboBoxCategory.setCurrentIndex(categoriesCountAfter - 1)

        except Exception as ex:
            helpers.show_exc_info(self, ex)
Пример #11
0
    def mouseMoveEvent(self, e):
        #Get current word under cursor
        cursor = self.cursorForPosition(e.pos())
        cursor.select(QtGui.QTextCursor.WordUnderCursor)
        word = cursor.selectedText()

        #print("pos={}".format(cursor.position()))
        if word == "ALL" and cursor.position() <= 3:
            self.keywordAll = True
        else:
            self.keywordAll = False

        # If current word has changed or cleared --- set default formatting
        if word != self.word or is_none_or_empty(word):
            cursor1 = self.textCursor()
            cursor1.select(QtGui.QTextCursor.Document)
            fmt = QtGui.QTextCharFormat()
            fmt.setForeground(QtGui.QBrush(QtGui.QColor(self.text_color)))
            cursor1.mergeCharFormat(fmt)
            self.word = None

        # If current word has changed --- highlight it
        if word != self.word:
            fmt = QtGui.QTextCharFormat()
            fmt.setForeground(QtGui.QBrush(QtGui.QColor(self.hl_text_color)))
            cursor.mergeCharFormat(fmt)
            self.word = word

        # NOTE: There is a problem when tag contains a spaces or dashes (and other special chars).
        # word is detected incorrectly in such a case.
        # TODO: Have to fix this problem
        return super(TagCloudTextEdit, self).mouseMoveEvent(e)
Пример #12
0
def sendEvent(name):
    if not isSendStatisticsAllowed():
        return
    instanceId = reggataInstanceId()
    if hlp.is_none_or_empty(instanceId):
        return
    t = Thread(target=_sendEvent, args=(instanceId, name))
    t.start()
Пример #13
0
def sendIntValue(name, intValue):
    if not isSendStatisticsAllowed():
        return
    instanceId = reggataInstanceId()
    if hlp.is_none_or_empty(instanceId):
        return
    t = Thread(target=_sendIntValue, args=(instanceId, name, intValue))
    t.start()
Пример #14
0
    def __writeDataRef(self):
        assert (self.item.data_ref is not None)

        srcAbsPath = self.ui.fileAbsPath.text()
        dstRelPath = self.ui.fileRelPath.text()

        srcAbsPath = os.path.normpath(srcAbsPath)
        dstRelPath = os.path.normpath(dstRelPath)

        if helpers.is_none_or_empty(srcAbsPath):
            raise MsgException(self.tr("srcAbsPath should not be empty."))

        if helpers.is_none_or_empty(dstRelPath):
            raise MsgException(self.tr("dstRelPath should not be empty."))

        self.item.data_ref.srcAbsPath = srcAbsPath
        self.item.data_ref.dstRelPath = dstRelPath
Пример #15
0
    def __writeDataRef(self):
        assert(self.item.data_ref is not None)

        srcAbsPath = self.ui.fileAbsPath.text()
        dstRelPath = self.ui.fileRelPath.text()

        srcAbsPath = os.path.normpath(srcAbsPath)
        dstRelPath = os.path.normpath(dstRelPath)

        if helpers.is_none_or_empty(srcAbsPath):
            raise MsgException(self.tr("srcAbsPath should not be empty."))

        if helpers.is_none_or_empty(dstRelPath):
            raise MsgException(self.tr("dstRelPath should not be empty."))

        self.item.data_ref.srcAbsPath = srcAbsPath
        self.item.data_ref.dstRelPath = dstRelPath
Пример #16
0
    def __parseAndWriteFileExtentions(self):
        index = self.__currentCategoryIndex()
        if index < 0:
            return

        userText = self.ui.lineEditFileExtensions.text().strip()
        assert not helpers.is_none_or_empty(userText), "This is a sign of bug in FileExtentionsListValidator.."

        self.__extAppMgrState.appDescriptions[index].fileExtentions = userText.split()
Пример #17
0
    def is_image(self):
        supported = set([".bmp", ".gif", ".jpg", ".jpeg", ".png", ".pbm", ".pgm",
                         ".ppm", ".xbm", ".xpm"])
        if self.type and self.type == "FILE" and not is_none_or_empty(self.url):
            _root, ext = os.path.splitext(self.url.lower())
            if ext in supported:
                return True

        return False
Пример #18
0
def unquote(string):
    '''
        Removes quotes and unescapes all symbols of the string.
    Returns modified string.
    '''
    if not is_none_or_empty(string) and string.startswith('"') \
       and string.endswith('"') and not string.endswith(r'\"'):
        string = string[1:-1]
        return unescape(string)
Пример #19
0
 def __decodeFavoriteReposFromStr(self, favoriteReposPropValue):
     if helpers.is_none_or_empty(favoriteReposPropValue):
         return []
     try:
         repos = eval(favoriteReposPropValue)
     except SyntaxError:
         repos = []
         logger.warn("Could not parse '" + favoriteReposPropValue + "' " +
                     " Check the value of 'favorite_repos' property in your reggata.conf.")
     return repos
Пример #20
0
 def widget_text_changed(self):
     if self.widget is not None:
         cursor = self.widget.textCursor()
         cursor.select(QtGui.QTextCursor.WordUnderCursor)
         word = cursor.selectedText()
         if is_none_or_empty(word):
             self.hide()
         self.filter(word)
         if self.count() <= 0:
             self.hide()
Пример #21
0
    def __saveNewItem(self, item, srcAbsPath=None, dstRelPath=None):
        #We do not need any info, that can be in item.data_ref object at this point.
        #But if it is not None, it may break the creation of tags/fields.
        #Don't worry, item.data_ref will be assigned a new DataRef instance later (if required).
        item.data_ref = None

        user_login = item.user_login
        if hlp.is_none_or_empty(user_login):
            raise err.AccessError("Argument user_login shouldn't be null or empty.")

        user = self._session.query(db.User).get(user_login)
        if user is None:
            raise err.AccessError("User with login {} doesn't exist.".format(user_login))

        #Making copies of tags and fields
        item_tags_copy = item.item_tags[:]
        item_fields_copy = item.item_fields[:]

        # Storing the item without tags and fields (for now)
        del item.item_tags[:]
        del item.item_fields[:]
        self._session.add(item)
        self._session.flush()

        tagNamesToAdd = map(lambda itag: itag.tag.name, item_tags_copy)
        operations.ItemOperations.addTags(self._session, item, tagNamesToAdd, user_login)

        nameValuePairsToAdd = map(lambda ifield: (ifield.field.name, ifield.field_value),
                                  item_fields_copy)
        operations.ItemOperations.addOrUpdateFields(self._session, item, nameValuePairsToAdd,
                                                    user_login)

        isDataRefRequired = not hlp.is_none_or_empty(srcAbsPath)
        if isDataRefRequired:
            operations.ItemOperations.addUntrackedFile(self._session, item,
                                                   self._repoBasePath,
                                                   srcAbsPath, dstRelPath,
                                                   user_login)

        self._session.commit()
        item_id = item.id
        self._session.expunge(item)
        return item_id
Пример #22
0
 def widget_text_changed(self):
     if self.widget is not None:
         cursor = self.widget.textCursor()
         cursor.select(QtGui.QTextCursor.WordUnderCursor)
         word = cursor.selectedText()
         if is_none_or_empty(word):
             self.hide()
         self.filter(word)
         if self.count() <= 0:
             self.hide()
Пример #23
0
    def __writeDataRefs(self):
        if self.mode == ItemsDialog.EDIT_MODE:
            for item in self.items:
                if (item.data_ref is None) or (item.data_ref.type != DataRef.FILE):
                    continue

                item.data_ref.srcAbsPath = os.path.join(self.repoBasePath, item.data_ref.url)
                if is_none_or_empty(self.dstPath):
                    item.data_ref.dstRelPath = item.data_ref.url
                else:
                    item.data_ref.dstRelPath = os.path.join(self.dstPath,
                                                            os.path.basename(item.data_ref.url))


        elif self.mode == ItemsDialog.CREATE_MODE:
            # In CREATE_MODE item.data_ref.url for all items will be None at this point
            # We should use item.data_ref.srcAbsPath instead
            for item in self.items:
                if (item.data_ref is None) or (item.data_ref.type != DataRef.FILE):
                    continue

                if self.same_dst_path:
                    tmp = self.dstPath if not is_none_or_empty(self.dstPath) else ""
                    item.data_ref.dstRelPath = os.path.join(
                        tmp,
                        os.path.basename(item.data_ref.srcAbsPath))
                else:
                    if self.dstPath:
                        relPathToFile = os.path.relpath(item.data_ref.srcAbsPath,
                                                        item.data_ref.srcAbsPathToRoot)
                        item.data_ref.dstRelPath = os.path.join(
                            self.dstPath,
                            relPathToFile)
                    else:
                        if is_internal(item.data_ref.srcAbsPath, self.repoBasePath):
                            item.data_ref.dstRelPath = os.path.relpath(
                                item.data_ref.srcAbsPath,
                                self.repoBasePath)
                        else:
                            item.data_ref.dstRelPath = os.path.relpath(
                                item.data_ref.srcAbsPath,
                                item.data_ref.srcAbsPathToRoot)
Пример #24
0
    def __loginUser(self, login, password):
        if hlp.is_none_or_empty(login):
            raise err.LoginError("User login cannot be empty.")
        user = self._session.query(db.User).get(login)
        if user is None:
            raise err.LoginError("User {} doesn't exist.".format(login))
        if user.password != password:
            raise err.LoginError("Password incorrect.")

        self._session.expunge(user)
        return user
Пример #25
0
    def __loginUser(self, login, password):
        if hlp.is_none_or_empty(login):
            raise err.LoginError("User login cannot be empty.")
        user = self._session.query(db.User).get(login)
        if user is None:
            raise err.LoginError("User {} doesn't exist.".format(login))
        if user.password != password:
            raise err.LoginError("Password incorrect.")

        self._session.expunge(user)
        return user
Пример #26
0
    def __writeFileBrowserCommand(self):
        currentCmd = self.__extAppMgrState.extFileMgrCommandPattern
        try:
            userText = self.ui.lineEditExtFileBrowserCmd.text().strip()
            if helpers.is_none_or_empty(userText):
                raise MsgException(self.tr("File Browser command should not be empty."))

            self.__extAppMgrState.extFileMgrCommandPattern = userText

        except Exception as ex:
            helpers.show_exc_info(self, ex)
            self.ui.lineEditExtFileBrowserCmd.setText(currentCmd)
Пример #27
0
    def is_image(self):
        supported = set([
            ".bmp", ".gif", ".jpg", ".jpeg", ".png", ".pbm", ".pgm", ".ppm",
            ".xbm", ".xpm"
        ])
        if self.type and self.type == "FILE" and not is_none_or_empty(
                self.url):
            _root, ext = os.path.splitext(self.url.lower())
            if ext in supported:
                return True

        return False
Пример #28
0
 def __decodeFavoriteReposFromStr(self, favoriteReposPropValue):
     if helpers.is_none_or_empty(favoriteReposPropValue):
         return []
     try:
         repos = eval(favoriteReposPropValue)
     except SyntaxError:
         repos = []
         logger.warn(
             "Could not parse '" + favoriteReposPropValue + "' " +
             " Check the value of 'favorite_repos' property in your reggata.conf."
         )
     return repos
Пример #29
0
    def addUntrackedFile(session, item, repoBasePath, srcAbsPath, dstRelPath,
                         userLogin):
        assert not hlp.is_none_or_empty(srcAbsPath)
        assert dstRelPath is not None
        #NOTE: If dstRelPath is an empty string it means the root of repository

        srcAbsPath = os.path.normpath(srcAbsPath)
        if not os.path.isabs(srcAbsPath):
            raise ValueError(
                "srcAbsPath='{}' must be an absolute path.".format(srcAbsPath))

        if not os.path.exists(srcAbsPath):
            raise ValueError(
                "srcAbsPath='{}' must point to an existing file.".format(
                    srcAbsPath))

        if os.path.isabs(dstRelPath):
            raise ValueError(
                "dstRelPath='{}' must be a relative to repository root path, but it is absolute."
                .format(dstRelPath))

        dstRelPath = hlp.removeTrailingOsSeps(dstRelPath)
        dstRelPath = os.path.normpath(dstRelPath)
        dstAbsPath = os.path.abspath(os.path.join(repoBasePath, dstRelPath))
        dstAbsPath = os.path.normpath(dstAbsPath)
        if srcAbsPath != dstAbsPath and os.path.exists(dstAbsPath):
            raise ValueError(
                "{} should not point to an existing file.".format(dstAbsPath))

        dataRef = session.query(db.DataRef).filter(
            db.DataRef.url_raw == hlp.to_db_format(dstRelPath)).first()
        if dataRef is not None:
            raise err.DataRefAlreadyExistsError(
                "DataRef instance with url='{}' "
                "is already in database. ".format(dstRelPath))

        item.data_ref = db.DataRef(objType=db.DataRef.FILE, url=dstRelPath)
        item.data_ref.user_login = userLogin
        item.data_ref.size = os.path.getsize(srcAbsPath)
        item.data_ref.hash = hlp.computeFileHash(srcAbsPath)
        item.data_ref.date_hashed = datetime.datetime.today()
        session.add(item.data_ref)
        item.data_ref_id = item.data_ref.id
        session.flush()

        #Now it's time to COPY physical file to the repository
        if srcAbsPath != dstAbsPath:
            try:
                head, _tail = os.path.split(dstAbsPath)
                os.makedirs(head)
            except:
                pass
            shutil.copy(srcAbsPath, dstAbsPath)
Пример #30
0
    def __init__(self, path, objType=None, status=None):
        assert not hlp.is_none_or_empty(path)
        assert objType is not None or status is not None

        #remove trailing slashes in the path
        while path.endswith(os.sep):
            path = path[0:-1]

        self.path = path
        self.status = status
        self.type = objType
        self.tags = []
        self.fields = []
        self.itemIds = []
Пример #31
0
    def __updateExistingItem(self, item, newSrcAbsPath, newDstRelPath, userLogin):
        logger.info("__updateExistingItem with args={}"
                    .format((item, newSrcAbsPath, newDstRelPath, userLogin)))

        if newSrcAbsPath is None:
            assert newDstRelPath is None, \
            "Both newSrcAbsPath and newDstRelPath args should be None."
        else:
            assert not hlp.is_none_or_empty(newSrcAbsPath)
            assert not hlp.is_none_or_empty(newDstRelPath), \
            "Both newSrcAbsPath and newDstRelPath args should be not empty."

        persistentItem = self._session.query(db.Item).get(item.id)

        self.__updatePlainDataMembers(item, persistentItem)
        self.__updateTags(item, persistentItem, userLogin)
        self.__updateFields(item, persistentItem, userLogin)
        self.__updateDataRefAndFilesystem(item, persistentItem, newSrcAbsPath, newDstRelPath, userLogin)
        self._session.commit()

        self._session.refresh(persistentItem)
        self._session.expunge(persistentItem)
        return persistentItem
Пример #32
0
    def __init__(self, path, objType=None, status=None):
        assert not hlp.is_none_or_empty(path)
        assert objType is not None or status is not None

        #remove trailing slashes in the path
        while path.endswith(os.sep):
            path = path[0:-1]

        self.path = path
        self.status = status
        self.type = objType
        self.tags = []
        self.fields = []
        self.itemIds = []
Пример #33
0
    def write(self):
        '''
            Writes all data from dialog GUI elements to the self.item object.
        '''
        self.item.title = self.ui.lineEdit_title.text()

        #Processing Tags
        del self.item.item_tags[:]
        text = self.ui.plainTextEdit_tags.toPlainText()
        tags, _tmp = definition_parser.parse(text)
        for t in tags:
            tag = Tag(name=t)
            item_tag = Item_Tag(tag)
            item_tag.user_login = self.item.user_login
            self.item.item_tags.append(item_tag)

        #Processing Fields
        del self.item.item_fields[:]
        text = self.ui.plainTextEdit_fields.toPlainText()
        _tmp, fields = definition_parser.parse(text)
        for (f, v) in fields:
            if f in consts.RESERVED_FIELDS:
                raise MsgException(
                    self.tr("Field name '{}' is reserved.").format(f))
            field = Field(name=f)
            item_field = Item_Field(field, v)
            item_field.user_login = self.item.user_login
            self.item.item_fields.append(item_field)

        #Processing reserved field NOTES_FIELD
        notes = self.ui.plainTextEdit_notes.toPlainText()
        if not is_none_or_empty(notes):
            field = Field(name=consts.NOTES_FIELD)
            item_field = Item_Field(field, notes)
            item_field.user_login = self.item.user_login
            self.item.item_fields.append(item_field)

        #Processing reserved field RATING_FIELD
        rating = self.ui.spinBox_rating.value()
        if rating > 0:
            field = Field(name=consts.RATING_FIELD)
            item_field = Item_Field(field, rating)
            item_field.user_login = self.item.user_login
            self.item.item_fields.append(item_field)

        #Processing DataRef object
        if self.item.data_ref is not None:
            self.__writeDataRef()
Пример #34
0
    def __writeApplicationCommand(self):
        index = self.__currentCategoryIndex()
        if index < 0:
            return
        currentAppCmd = self.__extAppMgrState.appDescriptions[index].appCommandPattern

        try:
            userText = self.ui.lineEditAppCmd.text().strip()
            if helpers.is_none_or_empty(userText):
                raise MsgException(self.tr("Application command should not be empty."))

            self.__extAppMgrState.appDescriptions[index].appCommandPattern = userText

        except Exception as ex:
            helpers.show_exc_info(self, ex)
            self.ui.lineEditAppCmd.setText(currentAppCmd)
Пример #35
0
    def write(self):
        '''
            Writes all data from dialog GUI elements to the self.item object.
        '''
        self.item.title = self.ui.lineEdit_title.text()

        #Processing Tags
        del self.item.item_tags[:]
        text = self.ui.plainTextEdit_tags.toPlainText()
        tags, _tmp = definition_parser.parse(text)
        for t in tags:
            tag = Tag(name=t)
            item_tag = Item_Tag(tag)
            item_tag.user_login = self.item.user_login
            self.item.item_tags.append(item_tag)

        #Processing Fields
        del self.item.item_fields[:]
        text = self.ui.plainTextEdit_fields.toPlainText()
        _tmp, fields = definition_parser.parse(text)
        for (f, v) in fields:
            if f in consts.RESERVED_FIELDS:
                raise MsgException(self.tr("Field name '{}' is reserved.").format(f))
            field = Field(name=f)
            item_field = Item_Field(field, v)
            item_field.user_login = self.item.user_login
            self.item.item_fields.append(item_field)

        #Processing reserved field NOTES_FIELD
        notes = self.ui.plainTextEdit_notes.toPlainText()
        if not is_none_or_empty(notes):
            field = Field(name=consts.NOTES_FIELD)
            item_field = Item_Field(field, notes)
            item_field.user_login = self.item.user_login
            self.item.item_fields.append(item_field)

        #Processing reserved field RATING_FIELD
        rating = self.ui.spinBox_rating.value()
        if rating > 0:
            field = Field(name=consts.RATING_FIELD)
            item_field = Item_Field(field, rating)
            item_field.user_login = self.item.user_login
            self.item.item_fields.append(item_field)

        #Processing DataRef object
        if self.item.data_ref is not None:
            self.__writeDataRef()
Пример #36
0
    def addUntrackedFile(session, item, repoBasePath, srcAbsPath, dstRelPath, userLogin):
        assert not hlp.is_none_or_empty(srcAbsPath)
        assert dstRelPath is not None
        #NOTE: If dstRelPath is an empty string it means the root of repository

        srcAbsPath = os.path.normpath(srcAbsPath)
        if not os.path.isabs(srcAbsPath):
            raise ValueError("srcAbsPath='{}' must be an absolute path.".format(srcAbsPath))

        if not os.path.exists(srcAbsPath):
            raise ValueError("srcAbsPath='{}' must point to an existing file.".format(srcAbsPath))

        if os.path.isabs(dstRelPath):
            raise ValueError("dstRelPath='{}' must be a relative to repository root path, but it is absolute."
                             .format(dstRelPath))

        dstRelPath = hlp.removeTrailingOsSeps(dstRelPath)
        dstRelPath = os.path.normpath(dstRelPath)
        dstAbsPath = os.path.abspath(os.path.join(repoBasePath, dstRelPath))
        dstAbsPath = os.path.normpath(dstAbsPath)
        if srcAbsPath != dstAbsPath and os.path.exists(dstAbsPath):
            raise ValueError("{} should not point to an existing file.".format(dstAbsPath))

        dataRef = session.query(db.DataRef).filter(
            db.DataRef.url_raw==hlp.to_db_format(dstRelPath)).first()
        if dataRef is not None:
            raise err.DataRefAlreadyExistsError("DataRef instance with url='{}' "
                                               "is already in database. ".format(dstRelPath))

        item.data_ref = db.DataRef(objType=db.DataRef.FILE, url=dstRelPath)
        item.data_ref.user_login = userLogin
        item.data_ref.size = os.path.getsize(srcAbsPath)
        item.data_ref.hash = hlp.computeFileHash(srcAbsPath)
        item.data_ref.date_hashed = datetime.datetime.today()
        session.add(item.data_ref)
        item.data_ref_id = item.data_ref.id
        session.flush()

        #Now it's time to COPY physical file to the repository
        if srcAbsPath != dstAbsPath:
            try:
                head, _tail = os.path.split(dstAbsPath)
                os.makedirs(head)
            except:
                pass
            shutil.copy(srcAbsPath, dstAbsPath)
Пример #37
0
    def execMessageBox(self, parent, text, title="Reggata", buttons=[QMessageBox.Ok], detailedText=None):
        '''
            Shows modal QtGui.QMessageBox and returns code of the clicked button.
        '''
        mb = QMessageBox(parent)
        mb.setText(text)
        mb.setWindowTitle(title)

        buttonsCode = QMessageBox.NoButton
        for button in buttons:
            buttonsCode = buttonsCode | button
        mb.setStandardButtons(buttonsCode)

        if not helpers.is_none_or_empty(detailedText):
            mb.setDetailedText(detailedText)

        return mb.exec_()
Пример #38
0
    def __addStoredOrUntrackedFile(self, persistentItem, newSrcAbsPath, newDstRelPath, userLogin):
        assert not hlp.is_none_or_empty(newDstRelPath)

        # Check if a newSrcAbsPath points to an already stored file
        newSrcRelPath = os.path.relpath(newSrcAbsPath, self._repoBasePath)
        existingDataRef = self._session.query(db.DataRef).filter(
            db.DataRef.url_raw==hlp.to_db_format(newSrcRelPath)).first()
        isNewFileStored = existingDataRef is not None

        if isNewFileStored:
            # NOTE: newDstRelPath is ignored in this case...
            operations.ItemOperations.addStoredFile(self._session, persistentItem,
                                                    self._repoBasePath,
                                                    existingDataRef)
        else:
            operations.ItemOperations.addUntrackedFile(self._session, persistentItem,
                                                       self._repoBasePath,
                                                       newSrcAbsPath, newDstRelPath,
                                                       userLogin)
Пример #39
0
    def __initFavoriteReposMenu(self):
        assert len(self.__favoriteReposDynamicQActions) == 0

        if self._model.user is None:
            return

        actionToInsertBefore =  self.ui.menuFavoriteRepos.insertSeparator(self.ui.actionAdd_current_repository)

        login = self._model.user.login
        favoriteReposInfo = self._model.favoriteRepos(login)
        for repoBasePath, repoAlias in favoriteReposInfo:
            if helpers.is_none_or_empty(repoBasePath):
                continue
            action = QtGui.QAction(self)
            action.setText(repoAlias)
            action.repoBasePath = repoBasePath
            self._model.connectOpenFavoriteRepoAction(action)
            self.ui.menuFavoriteRepos.insertAction(actionToInsertBefore, action)
            self.__favoriteReposDynamicQActions.append(action)
    def handle(self):
        logger.info("RenameFileActionHandler.handle invoked")
        try:
            self._tool.checkActiveRepoIsNotNone()
            self._tool.checkActiveUserIsNotNone()

            selFiles = self._tool.gui.selectedFiles()
            if len(selFiles) != 1:
                raise err.MsgException(
                    self.tr("Please select one file or directory"))

            selFile = selFiles[0]

            newName, isOk = self._dialogs.execGetTextDialog(
                self._tool.gui, self.tr("Rename File"),
                self.tr("Enter new file name:"), os.path.basename(selFile))

            if not isOk or newName == os.path.basename(selFile):
                return

            if is_none_or_empty(newName.strip()):
                raise err.MsgException(
                    self.tr("Wrong input, file name cannot be empty."))

            if os.path.isdir(selFile):
                self.__renameDir(selFile, newName)
            elif os.path.isfile(selFile):
                self.__renameFile(selFile, newName)
            else:
                raise err.MsgException(
                    self.
                    tr("Cannot rename '{}' because it is not a file or directory."
                       .format(selFile)))

            self._emitHandlerSignal(HandlerSignals.STATUS_BAR_MESSAGE,
                                    self.tr("Done."), consts.STATUSBAR_TIMEOUT)
            self._emitHandlerSignal(HandlerSignals.ITEM_CHANGED)

            stats.sendEvent("file_browser.rename_file")

        except Exception as ex:
            show_exc_info(self._tool.gui, ex)
Пример #41
0
    def __addStoredOrUntrackedFile(self, persistentItem, newSrcAbsPath,
                                   newDstRelPath, userLogin):
        assert not hlp.is_none_or_empty(newDstRelPath)

        # Check if a newSrcAbsPath points to an already stored file
        newSrcRelPath = os.path.relpath(newSrcAbsPath, self._repoBasePath)
        existingDataRef = self._session.query(db.DataRef).filter(
            db.DataRef.url_raw == hlp.to_db_format(newSrcRelPath)).first()
        isNewFileStored = existingDataRef is not None

        if isNewFileStored:
            # NOTE: newDstRelPath is ignored in this case...
            operations.ItemOperations.addStoredFile(self._session,
                                                    persistentItem,
                                                    self._repoBasePath,
                                                    existingDataRef)
        else:
            operations.ItemOperations.addUntrackedFile(
                self._session, persistentItem, self._repoBasePath,
                newSrcAbsPath, newDstRelPath, userLogin)
Пример #42
0
    def mouseDoubleClickEvent(self, e):
        if self.keywordAll:
            self.emit(QtCore.SIGNAL("selectedKeywordAll"))
            self.refresh()
            stats.sendEvent("tag_cloud.all_clicked")
            return

        if not is_none_or_empty(self.word):
            word = self.word
            if parsers.query_tokens.needs_quote(word):
                word = parsers.util.quote(word)

            if e.modifiers() == Qt.ControlModifier:
                self.not_tags.add(word)
            else:
                self.tags.add(word)
            self.emit(QtCore.SIGNAL("selectedTagsChanged"), self.tags, self.not_tags)
            self.refresh()
            stats.sendEvent("tag_cloud.tag_clicked")
            return
Пример #43
0
    def mouseDoubleClickEvent(self, e):
        if self.keywordAll:
            self.emit(QtCore.SIGNAL("selectedKeywordAll"))
            self.refresh()
            stats.sendEvent("tag_cloud.all_clicked")
            return

        if not is_none_or_empty(self.word):
            word = self.word
            if parsers.query_tokens.needs_quote(word):
                word = parsers.util.quote(word)

            if e.modifiers() == Qt.ControlModifier:
                self.not_tags.add(word)
            else:
                self.tags.add(word)
            self.emit(QtCore.SIGNAL("selectedTagsChanged"), self.tags,
                      self.not_tags)
            self.refresh()
            stats.sendEvent("tag_cloud.tag_clicked")
            return
Пример #44
0
    def __initFavoriteReposMenu(self):
        assert len(self.__favoriteReposDynamicQActions) == 0

        if self._model.user is None:
            return

        actionToInsertBefore = self.ui.menuFavoriteRepos.insertSeparator(
            self.ui.actionAdd_current_repository)

        login = self._model.user.login
        favoriteReposInfo = self._model.favoriteRepos(login)
        for repoBasePath, repoAlias in favoriteReposInfo:
            if helpers.is_none_or_empty(repoBasePath):
                continue
            action = QtGui.QAction(self)
            action.setText(repoAlias)
            action.repoBasePath = repoBasePath
            self._model.connectOpenFavoriteRepoAction(action)
            self.ui.menuFavoriteRepos.insertAction(actionToInsertBefore,
                                                   action)
            self.__favoriteReposDynamicQActions.append(action)
Пример #45
0
    def addSingleItem(tool, dialogs, file=None):
        '''
            Creates and saves in repo an Item linked with a given file (or without file).
        Returns id of saved Item, or raises an exception.
        '''
        savedItemId = None

        item = db.Item(user_login=tool.user.login)
        if not hlp.is_none_or_empty(file):
            file = os.path.normpath(file)
            item.title, _ = os.path.splitext(os.path.basename(file))
            item.data_ref = db.DataRef(objType=db.DataRef.FILE, url=file)

        if not dialogs.execItemDialog(item=item,
                                      gui=tool.gui,
                                      repo=tool.repo,
                                      dialogMode=ItemDialog.CREATE_MODE):
            raise err.CancelOperationError("User cancelled operation.")

        uow = tool.repo.createUnitOfWork()
        try:
            srcAbsPath = None
            dstRelPath = None
            if item.data_ref is not None:
                srcAbsPath = item.data_ref.srcAbsPath
                dstRelPath = item.data_ref.dstRelPath

            cmd = cmds.SaveNewItemCommand(item, srcAbsPath, dstRelPath)
            thread = BackgrThread(tool.gui, uow.executeCommand, cmd)

            dialogs.startThreadWithWaitDialog(thread,
                                              tool.gui,
                                              indeterminate=True)

            savedItemId = thread.result

        finally:
            uow.close()

        return savedItemId
Пример #46
0
    def keyPressEvent(self, event):
        cursor = self.textCursor()
        cursor.select(QtGui.QTextCursor.WordUnderCursor)
        word = cursor.selectedText()
        word = word if not is_none_or_empty(word) else ""

        if self.completer is not None and event.modifiers() == Qt.ControlModifier and event.key() == Qt.Key_Space:
            self.completer.filter(word)
            self.show_completer()
            super(TextEdit, self).keyPressEvent(event)
            # TODO When user press Ctrl+Space, completer is shown, but TextEdit cursor becomes hidden! Why?

        elif self.one_line and event.key() in [Qt.Key_Enter, Qt.Key_Return]:
            # This signal is for QLineEdit behaviour
            self.emit(QtCore.SIGNAL("returnPressed()"))

        elif event.key() in [
            Qt.Key_Backspace,
            Qt.Key_Delete,
            Qt.Key_Up,
            Qt.Key_Down,
            Qt.Key_Left,
            Qt.Key_Right,
            Qt.Key_End,
            Qt.Key_Home,
            Qt.Key_Shift,
            Qt.Key_Alt,
            Qt.Key_Control,
        ]:
            super(TextEdit, self).keyPressEvent(event)

        elif len(word) > 0:
            self.completer.filter(word)
            if self.completer.count() > 0:
                self.show_completer()
            super(TextEdit, self).keyPressEvent(event)

        else:
            super(TextEdit, self).keyPressEvent(event)
Пример #47
0
    def handle(self):
        logger.info("RenameFileActionHandler.handle invoked")
        try:
            self._tool.checkActiveRepoIsNotNone()
            self._tool.checkActiveUserIsNotNone()

            selFiles = self._tool.gui.selectedFiles()
            if len(selFiles) != 1:
                raise err.MsgException(self.tr("Please select one file or directory"))

            selFile = selFiles[0]

            newName, isOk = self._dialogs.execGetTextDialog(
                self._tool.gui, self.tr("Rename File"), self.tr("Enter new file name:"),
                os.path.basename(selFile))

            if not isOk or newName == os.path.basename(selFile):
                return

            if is_none_or_empty(newName.strip()):
                raise err.MsgException(self.tr("Wrong input, file name cannot be empty."))

            if os.path.isdir(selFile):
                self.__renameDir(selFile, newName)
            elif os.path.isfile(selFile):
                self.__renameFile(selFile, newName)
            else:
                raise err.MsgException(self.tr(
                    "Cannot rename '{}' because it is not a file or directory."
                    .format(selFile)))

            self._emitHandlerSignal(HandlerSignals.STATUS_BAR_MESSAGE, self.tr("Done."),
                                    consts.STATUSBAR_TIMEOUT)
            self._emitHandlerSignal(HandlerSignals.ITEM_CHANGED)

            stats.sendEvent("file_browser.rename_file")

        except Exception as ex:
            show_exc_info(self._tool.gui, ex)
Пример #48
0
    def buttonMoveFile(self):
        try:
            if self.item.data_ref is None:
                raise Exception(self.tr("You must add a file first."))

            directory = QtGui.QFileDialog.getExistingDirectory(
                self, self.tr("Select destination path within repository"),
                self.repoBasePath)
            if is_none_or_empty(directory):
                return

            if not is_internal(directory, self.repoBasePath):
                raise MsgException(self.tr("Chosen directory is out of active repository."))

            new_dst_path = os.path.relpath(directory, self.repoBasePath)
            if not new_dst_path.startswith("."):
                new_dst_path = os.path.join(".", new_dst_path)

            newDstRelPath = os.path.join(new_dst_path, os.path.basename(self.item.data_ref.url))
            self.ui.fileRelPath.setText(newDstRelPath)

        except Exception as ex:
            show_exc_info(self, ex)
Пример #49
0
    def addSingleItem(tool, dialogs, file=None):
        '''
            Creates and saves in repo an Item linked with a given file (or without file).
        Returns id of saved Item, or raises an exception.
        '''
        savedItemId = None

        item = db.Item(user_login=tool.user.login)
        if not hlp.is_none_or_empty(file):
            file = os.path.normpath(file)
            item.title, _ = os.path.splitext(os.path.basename(file))
            item.data_ref = db.DataRef(objType=db.DataRef.FILE, url=file)

        if not dialogs.execItemDialog(
            item=item, gui=tool.gui, repo=tool.repo, dialogMode=ItemDialog.CREATE_MODE):
            raise err.CancelOperationError("User cancelled operation.")

        uow = tool.repo.createUnitOfWork()
        try:
            srcAbsPath = None
            dstRelPath = None
            if item.data_ref is not None:
                srcAbsPath = item.data_ref.srcAbsPath
                dstRelPath = item.data_ref.dstRelPath

            cmd = cmds.SaveNewItemCommand(item, srcAbsPath, dstRelPath)
            thread = BackgrThread(tool.gui, uow.executeCommand, cmd)

            dialogs.startThreadWithWaitDialog(
                thread, tool.gui, indeterminate=True)

            savedItemId = thread.result

        finally:
            uow.close()

        return savedItemId
Пример #50
0
 def test_isNoneOrEmpty_nonEmptyStr(self):
     nonEmptyStr = "Reggata"
     self.assertFalse(helpers.is_none_or_empty(nonEmptyStr))
Пример #51
0
 def test_isNoneOrEmpty_none(self):
     noneObj = None
     self.assertTrue(helpers.is_none_or_empty(noneObj))
Пример #52
0
 def _set_data_ref_url(self, value):
     if not is_none_or_empty(self.data_ref_hash):
         self.data_ref_url_raw = helpers.to_db_format(value)
     else:
         self.data_ref_url_raw = value
Пример #53
0
 def test_isNoneOrEmpty_empty(self):
     emptyStr = ""
     self.assertTrue(helpers.is_none_or_empty(emptyStr))
Пример #54
0
def isUserGaveTheAnswerAboutSendStatistics():
    sendStatistics = UserConfig().get("send_statistics")
    return False if hlp.is_none_or_empty(sendStatistics) else True
Пример #55
0
 def registerColumn(self, col, isVisible=True):
     assert not helpers.is_none_or_empty(col.id)
     assert not self.isColumnIdRegistered(col.id)
     self._allColumns.append(col)
     if isVisible:
         self._visibleColumns.append(col)
Пример #56
0
def isReggataInstanceRegistered():
    instanceId = reggataInstanceId()
    return False if hlp.is_none_or_empty(instanceId) else True