Question

We need to calculate a hash of a mp3 file to uniquely identify it. The problem is that Traktor software modifies file's tags and there is no chance to change it.

We use id3lib library, so I thought maybe there is some way to get a prepended and appended size of tags of various versions and just read only media content between them to calculate hash of it. I've been searching in id3lib docs and the only thing I have found is ID3_Tag::GetPrependedBytes() and ID3_Tag::GetAppendedBytes(), like that:

const std::size_t prepend = tagOpener.GetPrependedBytes();
const std::size_t append = tagOpener.GetAppendedBytes();
const std::size_t overall = tagOpener.Size();

but they merely return 0.

If that can help, we are developing in C++ along with Qt, so maybe there can be some things to help with the snag.

Was it helpful?

Solution

I have solved the issue with the below code. Maybe it will help someone.

/** Return QString hash for the given path */
inline QString GetHash( const QString& filePath )
{
   /// Determine positions of ID3 tags
   ID3_Tag tagOpener( filePath.toLocal8Bit() );
   const std::size_t prepend = tagOpener.GetPrependedBytes();
   const std::size_t append = tagOpener.GetAppendedBytes();

   /// Calculate a hash
   QString hashValueString;
   QFile file( filePath );
   QCryptographicHash hash( QCryptographicHash::Md5 );
   if( file.open(QIODevice::ReadOnly) )
   {
      /// Read only useful media data and skip tags
      const bool seekRes = file.seek( prepend ); // skip prepend tags info
      const qint64 mediaDataSize = file.size() - append - prepend;
      hash.addData( file.read(mediaDataSize) );

      /// Set hash md5 for current file
      hashValueString =  hash.result().toHex().data();
      file.close();
   }

   tagOpener.Clear();
   return hashValueString;
}

It's a solution using Qt and ID3Lib. You can merely use a value returned by the hash.result() code to get a numerical representation.

OTHER TIPS

An alternative solution might be to use a hash of the audio payloads to identify an mp3 file. Can you use a library for parsing an mpeg audio file instead of id3lib?

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top