예제 #1
0
 def getAllLocalSubtitles(self):
     '''
     Returns a structure containing all the subtitleInfos that are pointing
     to a local path
     
     @return a dictionary like this:
             { ...
               channel1 : { infohash1 : [ SubtitleInfo1, ...] }
               ...
             }
     '''
     query = QUERIES["SELECT SUBTITLES WITH PATH"]
     res = self._db.fetchall(query)
     
     result = {}
     
     for entry in res:
         # fk = entry[0]
         path = entry[1]
         lang = entry[2]
         checksum = str2bin(entry[3])
         channel = str2bin(entry[4])
         infohash = str2bin(entry[5])
         
         s = SubtitleInfo(lang, path, checksum)
         
         if channel not in result:
             result[channel] = {}
         if infohash not in result[channel]:
             result[channel][infohash] = []
         
         result[channel][infohash].append(s)
         
     return result
예제 #2
0
 def getSubtitle(self, channel, infohash, lang):
     """
     Get a subtitle for a language for a given item in a given channel.
     
     Returns the details reguarding a subtitles in a given language for a
     given item in a given channel, if it exists. Otherwise it returns
     None.
     
     @param channel: a perm_id identifying the owner of the channel.
     @param infohash: the infohash of an item, as announced in channelcast
                      messages.
     @param lang: a 3 characters ISO 639-2 language code, identifying
                  the desired subtitle langugage
     @return: a SubtitleInfo instance
     """
     query = QUERIES["SELECT SUBS JOIN HASH ONE"]
     
     infohash = bin2str(infohash)
     channel = bin2str(channel)
       
       
     res = self._db.fetchall(query, (infohash, channel, lang))
     if len(res) == 0 :
         return None
     elif len(res) == 1 :
         checksum = str2bin(res[0][3])
         return SubtitleInfo(res[0][1], res[0][2], checksum)
     else : 
         # This should be not possible to database constraints
         raise MetadataDBException("Metadata DB Constraint violeted!")
예제 #3
0
 def getLocalSubtitles(self, channel, infohash):
     '''
     Returns a dictionary containing all the subtitles pointing
     to a local pathm for the given channel, infohash
     @param channel: binary channel_id(permid)
     @param infohash: binary infohash
     
     @rtype: dict
     @return: a dictionary like this:
             {
              ...
              langCode : SubtitleInfo,
              ...
             }
             The dictionary will be empty if no local subtitle
             is available.
     '''
     query = QUERIES["SELECT SUBTITLES WITH PATH BY CHN INFO"]
     
     channel = bin2str(channel)
     infohash = bin2str(infohash)
     res = self._db.fetchall(query,(channel,infohash))
     
     result  = {}
     
     for entry in res:
         location = entry[0]
         language = entry[1]
         checksum = str2bin(entry[2])
         subInfo = SubtitleInfo(language, location, checksum)
         result[language] = subInfo
     
     return result
예제 #4
0
 def getMetadata(self, channel, infohash):
     """
     Returns a MetadataDTO instance for channel/infohash if available in DB
     
     Given a channel/infhash couple returns a MetadataDTO instance, built
     with the values retrieved from the Metadata and Subtitles DB. If
     no result returns None
     
     @param channel: the permid of the channel's owner (binary)
     @param infohash: the infohash of the item the metadata refers to
                      (binary)
     @return: a MetadataDTO instance comprehensive of subtitles if any
              metadata is found in the DB. None otherwise.
     """
     
     query = QUERIES["SELECT METADATA"]
     
     infohash = bin2str(infohash)
     channel = bin2str(channel)
     
     res = self._db.fetchall(query, (infohash, channel))
     
     if len(res) == 0:
         return None
     if len(res) > 1:
         raise MetadataDBException("Metadata DB Constraint violated")
     
     metaTuple = res[0]
     
     subsDictionary = self._getAllSubtitlesByKey(metaTuple[0])
     
     publisher = str2bin(metaTuple[1])
     infohash =  str2bin(metaTuple[2])
     timestamp = int(metaTuple[4])
     description = unicode(metaTuple[3])
     signature = str2bin(metaTuple[5])
     
     toReturn = MetadataDTO(publisher, infohash,
                            timestamp, description, None,
                            signature)
     
     for sub in subsDictionary.itervalues():
         toReturn.addSubtitle(sub)
     
     return toReturn
예제 #5
0
 def testDesrialize(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     dto.description = u"Sample Description"
     dto.sign(test_keypair)
     
     serialized = dto.serialize()
     newDto = MDUtil.deserialize(serialized)
     self.assertEquals(dto,newDto)
예제 #6
0
 def testSignature(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     
     dto.sign(test_keypair)
     self.assertTrue(dto.verifySignature())
     dto.timestamp = 2
     ok = dto.verifySignature()
     self.assertFalse(ok)
예제 #7
0
 def testSerialize(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     dto.description = u"Sample Description"
     dto.sign(test_keypair)
     
     serialized = dto.serialize()
     self.assertEquals(7, len(serialized))
     signature = serialized[6]
     self.assertEquals(dto.signature,signature)
예제 #8
0
 def testMetadataDTOInit(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     self.assertFalse(dto is None)
     self.assertEqual(test_perm_id,dto.channel)
     self.assertEquals(badInfohash,dto.infohash)
     current = time.time()
     self.assertTrue(current -1 <= int(dto.timestamp) <= current)
     self.assertEquals("",dto.description)
     self.assertEquals({}, dto._subtitles)
     self.assertTrue(dto.signature is None)
예제 #9
0
 def testDeserializeWithSubs(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     
     subtitles = [SubtitleInfo(lang,path) for lang,path in self._srtSubs.iteritems()]
     
     for sub in subtitles :
         sub.computeChecksum()
         dto.addSubtitle(sub)
     dto.sign(test_keypair)
     
     serial = dto.serialize()
     newDto = MDUtil.deserialize(serial)
     self.assertEquals(dto,newDto)
예제 #10
0
 def testSerializeWithSubs(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     
     subtitles = [SubtitleInfo(lang,path) for lang,path in self._srtSubs.iteritems()]
     
     for sub in subtitles :
         sub.computeChecksum()
         dto.addSubtitle(sub)
     dto.sign(test_keypair)
     
     serial = dto.serialize()
     decoded = serial
     self.assertEquals(7, len(decoded))
     signature = decoded[6]
     self.assertEquals(dto.signature,signature)
예제 #11
0
 def getHaveEntries(self, channel, infohash):
     '''
     Return a list of have entries for subtitles for a torrent
     in a channel.
     
     This method returns a list of tuple, like:
     [ 
       ...
       (peer_id, haveMask, timestamp),
       ...
     ]
     
     (peer_id) is the perm_id of a Tribler
     Peer, haveMask is an integer value representing a 
     bitmask of subtitles owned by that peer. 
     Timestamp is the timestamp at the time the havemask
     was received. 
     The results are ordered by descending timestamp.
     If there are no
     entris for the givenn channel,infohash pair, the returned
     list will be empty
     
     @type channel: str
     @param channel: channel_id (binary)
     
     @type infohash: str
     @param infohash: the infohash of a torrent (binary)
     
     @rtype: list
     @return: see description
     
     '''
     query = QUERIES["GET ALL HAVE MASK"]
     
     channel = bin2str(channel)
     infohash = bin2str(infohash)
     
     res = self._db.fetchall(query,(channel,infohash))
     returnlist = list()
     
     for entry in res:
         peer_id = str2bin(entry[0])
         haveMask = entry[1]
         timestamp = entry[2]
         returnlist.append((peer_id, haveMask, timestamp))
         
     return returnlist
예제 #12
0
 def testSignatureOnChecksums(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     
     subtitles = [SubtitleInfo(lang,path) for lang,path in self._srtSubs.iteritems()]
     
     for sub in subtitles :
         sub.computeChecksum()
         dto.addSubtitle(sub)
     
     
     dto.sign(test_keypair)
     self.assertTrue(dto.verifySignature())
     
     dto.getSubtitle("rus").checksum = "ABCDEFGHILMOPQRS"
     
     self.assertFalse(dto.verifySignature())
예제 #13
0
 def _getAllSubtitlesByKey(self, metadataKey):
     '''
     Retrieves every subtitles given a Metadata table key
     
     Given an instance of the Metadata table artificial key, retrieves
     every subtitle instance associated to that key
     
     @param metadataKey: a value of an artificial key in the Metadata table
     @return : a dictionary of type {lang : SubtitleInfo}, empty if no results
     '''
     query = QUERIES["SELECT SUBS FK ALL"]
     
       
     results = self._db.fetchall(query, (metadataKey,))
     subsDict = {}
     for entry in results:
         subsDict[entry[1]] = SubtitleInfo(entry[1], entry[2], str2bin(entry[3]))
  
     return subsDict
예제 #14
0
 def test_packData(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     dto.description = u"Sample Description\u041f"
     
     bla = dto._packData()
     decoded = bdecode(bla)
     
     self.assertTrue(len(decoded) == 6)
     decodedChannelId = decoded[0]
     decodedInfohash = decoded[1]
     decodedDescription = decoded[2].decode("utf-8")
     decodedTimestamp = decoded[3]
     bin_decodedBitmask = decoded[4]
     decodedBitmask = binaryStringToUint(bin_decodedBitmask)
     self.assertEquals(dto.channel, decodedChannelId)
     self.assertEquals(dto.infohash, decodedInfohash)
     self.assertEquals(dto.description,decodedDescription)
     self.assertAlmostEquals(dto.timestamp,decodedTimestamp)
     self.assertEquals(0,decodedBitmask)
     self.assertEquals(0,len(decoded[5]))
예제 #15
0
 def getAllMetadataForInfohash(self, infohash):
     """
     Returns a list of MetadataDTO instances for a given infohash
     
     Given a torrent infohash returns a list of MetadataDTO instances for
     that infohash. Each one of the MetadataDTO refers to a different
     channel.
     
     @param infohash: the infohash for the torrent (binary)
     @return: a list of MetadataDTO isntances (or empty list if nothing
              is found)
     """
     
     assert infohash is not None
     
     strinfohash = bin2str(infohash)
     
     query = QUERIES["SELECT PUBLISHERS FROM INFOHASH"]
     
     channels = self._db.fetchall(query, (strinfohash,))
     
     return [self.getMetadata(str2bin(entry[0]), infohash) for entry in channels]
예제 #16
0
 def test_packDataWithSubs(self):
     badInfohash = str2bin("GEh/o8rtTLB1wZJzFcSZSS4u9qo=")
     dto = MetadataDTO(test_perm_id, badInfohash)
     
     subtitles = [SubtitleInfo(lang,path) for lang,path in self._srtSubs.iteritems()]
     
     for sub in subtitles :
         sub.computeChecksum()
         dto.addSubtitle(sub)
     
     packed = dto._packData()
     decoded = bdecode(packed)
     
     self.assertTrue(len(decoded) == 6)
     decodedChannelId = decoded[0]
     decodedInfohash = decoded[1]
     decodedDescription = decoded[2]
     decodedTimestamp = decoded[3]
     decodedBitmask = decoded[4]
     checksums = decoded[5]
     
     expectedMask = \
       LanguagesProvider.getLanguagesInstance().langCodesToMask(self._srtSubs.keys())
       
     binaryExpexted = uintToBinaryString(expectedMask)
     
     self.assertEquals(dto.channel, decodedChannelId)
     self.assertEquals(dto.infohash, decodedInfohash)
     self.assertEquals(dto.description,decodedDescription)
     self.assertAlmostEquals(dto.timestamp,decodedTimestamp)
     self.assertEquals(binaryExpexted,decodedBitmask)
     self.assertEquals(3,len(checksums))
     
     subs = dto.getAllSubtitles()
     i=0
     for key in sorted(subs.iterkeys()):
         self.assertEquals(subs[key].checksum, checksums[i])
         i += 1
예제 #17
0
 def _getSubtitleByKey(self, metadata_fk, lang):
     """
     Return a subtitle in a given language for a key of the Metadata table.
     
     Given an instance of the artificial key in the metadata table,
     retrieves a SubtitleInfo instance for that key and the language passed in.
     
     @param metadata_fk: a key in the metadata table
     @param lang: a language code for the subtitle to be retrieved
     
     @return: a SubtitleInfo instance, or None
     """
     query = QUERIES["SELECT SUBS FK ONE"]
       
       
     res = self._db.fetchall(query, (metadata_fk, lang))
     if len(res) == 0 :
         return None
     elif len(res) == 1 :
         checksum = str2bin(res[0][3])
         return SubtitleInfo(res[0][1], res[0][2], checksum)
     else : 
         # This should be not possible to database constraints
         raise MetadataDBException("Metadata DB Constraint violeted!")