docs: public synchronized void start() throws Exception {
          if (!isRunning()) {
              MetadataFinder.getInstance().addLifecycleListener(lifecycleListener);
              MetadataFinder.getInstance().start();
              MetadataFinder.getInstance().addTrackMetadataListener(metadataListener);
  
              WaveformFinder.getInstance().addLifecycleListener(lifecycleListener);
              WaveformFinder.getInstance().setFindDetails(true);
              WaveformFinder.getInstance().start();
              WaveformFinder.getInstance().addWaveformListener(waveformListener);
  
              BeatGridFinder.getInstance().addLifecycleListener(lifecycleListener);
              BeatGridFinder.getInstance().start();
              BeatGridFinder.getInstance().addBeatGridListener(beatGridListener);
  
              queueHandler = new Thread(new Runnable() {
                  @Override
                  public void run() {
                      while (isRunning()) {
                          try {
                              handleUpdate(pendingUpdates.take());
                          } catch (InterruptedException e) {
                              // Interrupted due to one of our finders shutting down, presumably.
                          } catch (Throwable t) {
                              logger.error("Problem processing track signature update", t);
                          }
                      }
                  }
              });
              running.set(true);
              queueHandler.start();
              deliverLifecycleAnnouncement(logger, true);
              checkExistingTracks();
          }
      }