/**
   * Deserializes the snapshot contained in the {@link WaveletSnapshot} into an {@link
   * ObservableWaveletData}.
   *
   * @param snapshot the {@link WaveletSnapshot} to deserialize.
   * @throws OperationException if the ops in the snapshot can not be applied.
   * @throws InvalidParticipantAddress
   * @throws InvalidIdException
   */
  public static ObservableWaveletData deserializeWavelet(WaveletSnapshot snapshot, WaveId waveId)
      throws OperationException, InvalidParticipantAddress, InvalidIdException {
    ObservableWaveletData.Factory<? extends ObservableWaveletData> factory =
        WaveletDataImpl.Factory.create(
            ObservablePluggableMutableDocument.createFactory(SchemaCollection.empty()));

    ParticipantId author = ParticipantId.of(snapshot.getCreator());
    WaveletId waveletId = ModernIdSerialiser.INSTANCE.deserialiseWaveletId(snapshot.getWaveletId());
    long creationTime = snapshot.getCreationTime();

    ObservableWaveletData wavelet =
        factory.create(
            new EmptyWaveletSnapshot(
                waveId,
                waveletId,
                author,
                CoreWaveletOperationSerializer.deserialize(snapshot.getVersion()),
                creationTime));

    for (String participant : snapshot.getParticipantIdList()) {
      wavelet.addParticipant(getParticipantId(participant));
    }

    for (DocumentSnapshot document : snapshot.getDocumentList()) {
      addDocumentSnapshotToWavelet(document, wavelet);
    }

    wavelet.setVersion(snapshot.getVersion().getVersion());
    wavelet.setLastModifiedTime(snapshot.getLastModifiedTime());
    // The creator and creation time are set when the empty wavelet template is
    // created above.

    return wavelet;
  }
  private static void addDocumentSnapshotToWavelet(DocumentSnapshot snapshot, WaveletData container)
      throws InvalidParticipantAddress {
    DocOp op = CoreWaveletOperationSerializer.deserialize(snapshot.getDocumentOperation());
    DocInitialization docInit = DocOpUtil.asInitialization(op);

    Collection<ParticipantId> contributors = CollectionUtils.newArrayList();
    for (String p : snapshot.getContributorList()) {
      contributors.add(getParticipantId(p));
    }
    container.createDocument(
        snapshot.getDocumentId(),
        getParticipantId(snapshot.getAuthor()),
        contributors,
        docInit,
        snapshot.getLastModifiedTime(),
        snapshot.getLastModifiedVersion());
  }