def _receive(self): logger.debug("Receiving data ... ") stream = QtCore.QDataStream(self.connection) stream.setVersion(QtCore.QDataStream.Qt_4_6) i = 0 while self.connection.bytesAvailable() > 0: if ( self._block_size == 0 and self.connection.bytesAvailable() >= INT32_SIZE ) or ( self._block_size > 0 and self.connection.bytesAvailable() >= self._block_size ): self._block_size = stream.readInt32() # logger.debug( # "Reading data size for request %s in queue: %s" # % (i, self._block_size) # ) if ( self._block_size > 0 and self.connection.bytesAvailable() >= self._block_size ): data = stream.readRawData(self._block_size) request = QtCore.QTextCodec.codecForMib(106).toUnicode(data) # logger.debug("About to process request %s in queue: %s" % (i, request)) self._process_request(request) self._block_size = 0 i += 1 return None
def _save_to_disk(self): """ Save the model to disk using QDataStream serialization. This all happens on the C++ side and is very fast. """ filename = self._cache_path # set umask to zero, store old umask old_umask = os.umask(0) try: # try to create the cache folder with as open permissions as # possible cache_dir = os.path.dirname(filename) # make sure the cache directory exists if not os.path.exists(cache_dir): try: os.makedirs(cache_dir, 0777) except OSError, e: # Race conditions are perfectly possible on some network # storage setups so make sure that we ignore any file # already exists errors, as they are not really errors! if e.errno != errno.EEXIST: # re-raise raise # write cache file fh = QtCore.QFile(filename) fh.open(QtCore.QIODevice.WriteOnly) try: out_stream = QtCore.QDataStream(fh) # write a header out_stream.writeInt64(self._FILE_MAGIC_NUMBER) out_stream.writeInt32(self._FILE_VERSION) # todo: if it turns out that there are ongoing issues with # md5 cache collisions, we could write the actual query # parameters to the header of the cache file here and compare # that against the desired query info just to be confident we # are getting a correct cache... # tell which serialization dialect to use out_stream.setVersion(QtCore.QDataStream.Qt_4_0) root = self.invisibleRootItem() self.__save_to_disk_r(out_stream, root, 0) finally: fh.close() # set mask back to previous value os.umask(old_umask) # and ensure the cache file has got open permissions os.chmod(filename, 0666)
def _send(self, request): # make sure we are connected if self.connection.state() in ( QtNetwork.QAbstractSocket.SocketState.UnconnectedState, ): self.connect_to_host() block = QtCore.QByteArray() outstr = QtCore.QDataStream(block, QtCore.QIODevice.WriteOnly) outstr.setVersion(QtCore.QDataStream.Qt_4_6) outstr.writeString(str(request)) self.connection.write(block) if not self.connection.waitForBytesWritten(MAX_WRITE_RESPONSE_TIME): logger.error("Could not write to socket: %s" % self.connection.errorString()) else: logger.debug("Sent data ok. %s" % self.connection.state())
def __load_from_disk(self): """ Load a serialized model from disk./ :returns: Number of items loaded """ num_items_loaded = 0 # open the data cache for reading fh = QtCore.QFile(self._cache_path) fh.open(QtCore.QIODevice.ReadOnly) try: in_stream = QtCore.QDataStream(fh) magic = in_stream.readInt64() if magic != self._FILE_MAGIC_NUMBER: raise Exception("Invalid file magic number!") version = in_stream.readInt32() if version != self._FILE_VERSION: raise CacheReadVersionMismatch( "Cache file version %s, expected version %s" % (version, self._FILE_VERSION) ) # tell which deserialization dialect to use in_stream.setVersion(QtCore.QDataStream.Qt_4_0) curr_parent = self.invisibleRootItem() prev_node = None curr_depth = 0 while not in_stream.atEnd(): # this is the item where the deserialized data will live item = self._SG_QUERY_MODEL_ITEM_CLASS() num_items_loaded += 1 # keep a reference to this object to make GC happy (pyside may # crash otherwise) self.__all_tree_items.append(item) item.read(in_stream) node_depth = in_stream.readInt32() # all nodes have a unique identifier stored in their metadata # the role data accessible via item.data() contains the # identifier for this item. sg_data = get_sg_data(item) if sg_data: # add the model item to our tree data dict keyed by the # unique identifier uid = sg_data.get(self._SG_DATA_UNIQUE_ID_FIELD) if uid: self.__tree_data[uid] = item # serialized items contain some sort of strange low-rez thumb # data which we cannot use. Make sure that is all cleared. item.setIcon(QtGui.QIcon()) # allow item customization prior to adding to model self._item_created(item) # serialized items do not contain a full high rez thumb, so # re-create that. First, set the default thumbnail self._populate_default_thumbnail(item) # run the finalize method so that subclasses can do any setup # they need self._finalize_item(item) if node_depth == curr_depth + 1: # this new node is a child of the previous node curr_parent = prev_node if prev_node is None: raise Exception("File integrity issues!") curr_depth = node_depth elif node_depth > curr_depth + 1: # something's wrong! raise Exception("File integrity issues!") elif node_depth < curr_depth: # we are going back up to parent level while curr_depth > node_depth: curr_depth -= 1 curr_parent = curr_parent.parent() if curr_parent is None: # we reached the root. special case curr_parent = self.invisibleRootItem() # get complete row containing all columns for the current item row = self._get_columns(item, bool(sg_data)) # and attach the node curr_parent.appendRow(row) prev_node = item finally: fh.close() return num_items_loaded