diff --git a/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/UnprocessedCommitsWalker.java b/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/CommitsWalker.java
similarity index 72%
rename from src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/UnprocessedCommitsWalker.java
rename to src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/CommitsWalker.java
index 1ddd0e2..1c9a609 100644
--- a/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/UnprocessedCommitsWalker.java
+++ b/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/CommitsWalker.java
@@ -29,6 +29,7 @@
 import com.googlesource.gerrit.plugins.eventseiffel.cache.EiffelEventIdLookupException;
 import com.googlesource.gerrit.plugins.eventseiffel.eiffel.SourceChangeEventKey;
 import java.io.IOException;
+import java.util.Arrays;
 import java.util.List;
 import java.util.Optional;
 import java.util.UUID;
@@ -42,7 +43,7 @@
 import org.eclipse.jgit.revwalk.RevSort;
 import org.eclipse.jgit.revwalk.RevWalk;
 
-public abstract class UnprocessedCommitsWalker implements AutoCloseable {
+public abstract class CommitsWalker implements AutoCloseable {
   @Singleton
   public static class Factory {
     private final EiffelEventHub eventHub;
@@ -59,6 +60,16 @@
       return new SccWalker(eventKey, eventHub, repoManager);
     }
 
+    public CommitsWalker childWalker(SourceChangeEventKey eventKey)
+        throws RepositoryNotFoundException, IOException, EiffelEventIdLookupException {
+      return new ChildWalker(eventKey, eventHub, repoManager, Optional.empty());
+    }
+
+    public CommitsWalker childWalker(SourceChangeEventKey eventKey, SourceChangeEventKey parentKey)
+        throws RepositoryNotFoundException, IOException, EiffelEventIdLookupException {
+      return new ChildWalker(eventKey, eventHub, repoManager, Optional.of(parentKey));
+    }
+
     public ScsWalker scsWalker(
         SourceChangeEventKey eventKey,
         String commitSha1TransactionEnd,
@@ -70,8 +81,6 @@
     }
   }
 
-  private static final FluentLogger logger = FluentLogger.forEnclosingClass();
-
   private static void flagWithParents(RevCommit commit, RevFlag flag) {
     commit.add(flag);
     for (RevCommit parent : commit.getParents()) {
@@ -79,22 +88,23 @@
     }
   }
 
+  private static final FluentLogger logger = FluentLogger.forEnclosingClass();
+
   protected final SourceChangeEventKey eventKey;
   protected final EiffelEventHub eventHub;
   protected final Repository repo;
   protected final RevWalk rw;
-  protected final boolean hasEvents;
   protected final List<AutoCloseable> toClose = Lists.newArrayList();
   protected EventCreate next;
 
-  UnprocessedCommitsWalker(
+  CommitsWalker(
       SourceChangeEventKey eventKey, EiffelEventHub eventHub, GitRepositoryManager repoManager)
       throws RepositoryNotFoundException, IOException, EiffelEventIdLookupException {
     this(eventKey, eventHub, repoManager.openRepository(Project.nameKey(eventKey.repo())));
     this.toClose.add(this.repo);
   }
 
-  UnprocessedCommitsWalker(SourceChangeEventKey eventKey, EiffelEventHub eventHub, Repository repo)
+  CommitsWalker(SourceChangeEventKey eventKey, EiffelEventHub eventHub, Repository repo)
       throws RepositoryNotFoundException, IOException, EiffelEventIdLookupException {
     this.eventKey = eventKey;
     this.eventHub = eventHub;
@@ -102,7 +112,6 @@
     this.rw = new RevWalk(repo);
     this.toClose.add(rw);
     rw.setRetainBody(false);
-    this.hasEvents = hasEvents();
   }
 
   @Override
@@ -133,35 +142,6 @@
     return eventKey.copy(commit.getName());
   }
 
-  protected boolean isAlreadyHandled(
-      RevFlag hasEventFlag, RevCommit commit, SourceChangeEventKey key)
-      throws EiffelEventIdLookupException {
-    logger.atFine().log("%s has event flag: %b", key.copy(commit), commit.has(hasEventFlag));
-    return commit.has(hasEventFlag) || eventHub.getExistingId(key).isPresent();
-  }
-
-  /* Returns true if an event has been created for key.branch from any commits reachable from
-   * key.commit (i.e. initial commit) */
-  private boolean hasEvents()
-      throws MissingObjectException, IncorrectObjectTypeException, IOException,
-          EiffelEventIdLookupException {
-    rw.sort(RevSort.REVERSE);
-    rw.markStart(rw.parseCommit(ObjectId.fromString(eventKey.commit())));
-    RevCommit initialCommit = rw.next();
-    if (initialCommit == null) {
-      logger.atWarning().log("Unable to find initial commit for: %s", eventKey);
-      return false;
-    }
-    logger.atFine().log("Found initial commit: \"%s\" of %s.", initialCommit.name(), eventKey);
-
-    /* Reset RevWalk. */
-    rw.reset();
-
-    Optional<UUID> eventId = eventHub.getExistingId(toKey(initialCommit));
-    eventId.ifPresent(id -> logger.atFine().log("%s has events", eventKey));
-    return eventId.isPresent();
-  }
-
   public class EventCreate {
     SourceChangeEventKey key;
     RevCommit commit;
@@ -182,6 +162,53 @@
     }
   }
 
+  public abstract static class UnprocessedCommitsWalker extends CommitsWalker {
+    protected final boolean hasEvents;
+
+    UnprocessedCommitsWalker(
+        SourceChangeEventKey eventKey, EiffelEventHub eventHub, GitRepositoryManager repoManager)
+        throws RepositoryNotFoundException, IOException, EiffelEventIdLookupException {
+      this(eventKey, eventHub, repoManager.openRepository(Project.nameKey(eventKey.repo())));
+      this.toClose.add(this.repo);
+    }
+
+    UnprocessedCommitsWalker(
+        SourceChangeEventKey eventKey, EiffelEventHub eventHub, Repository repo)
+        throws RepositoryNotFoundException, IOException, EiffelEventIdLookupException {
+      super(eventKey, eventHub, repo);
+      this.hasEvents = hasEvents();
+    }
+
+    protected boolean isAlreadyHandled(
+        RevFlag hasEventFlag, RevCommit commit, SourceChangeEventKey key)
+        throws EiffelEventIdLookupException {
+      logger.atFine().log("%s has event flag: %b", key.copy(commit), commit.has(hasEventFlag));
+      return commit.has(hasEventFlag) || eventHub.getExistingId(key).isPresent();
+    }
+
+    /* Returns true if an event has been created for key.branch from any commits reachable from
+     * key.commit (i.e. initial commit) */
+    private boolean hasEvents()
+        throws MissingObjectException, IncorrectObjectTypeException, IOException,
+            EiffelEventIdLookupException {
+      rw.sort(RevSort.REVERSE);
+      rw.markStart(rw.parseCommit(ObjectId.fromString(eventKey.commit())));
+      RevCommit initialCommit = rw.next();
+      if (initialCommit == null) {
+        logger.atWarning().log("Unable to find initial commit for: %s", eventKey);
+        return false;
+      }
+      logger.atFine().log("Found initial commit: \"%s\" of %s.", initialCommit.name(), eventKey);
+
+      /* Reset RevWalk. */
+      rw.reset();
+
+      Optional<UUID> eventId = eventHub.getExistingId(toKey(initialCommit));
+      eventId.ifPresent(id -> logger.atFine().log("%s has events", eventKey));
+      return eventId.isPresent();
+    }
+  }
+
   static class SccWalker extends UnprocessedCommitsWalker {
     private RevFlag hasSccEventFlag;
 
@@ -328,4 +355,52 @@
       }
     }
   }
+
+  static class ChildWalker extends CommitsWalker {
+    private Optional<SourceChangeEventKey> parentKey;
+
+    ChildWalker(
+        SourceChangeEventKey eventKey,
+        EiffelEventHub eventHub,
+        GitRepositoryManager repoManager,
+        Optional<SourceChangeEventKey> parentKey)
+        throws RepositoryNotFoundException, IOException, EiffelEventIdLookupException {
+      super(eventKey, eventHub, repoManager);
+      this.parentKey = parentKey;
+      checkState(
+          eventKey.type().equals(SCC) || eventKey.type().equals(SCS),
+          "EventKey must have type SCC or SCS for ChildWalker.");
+      rw.markStart(rw.parseCommit(ObjectId.fromString(eventKey.commit())));
+      rw.sort(RevSort.TOPO);
+      rw.sort(RevSort.REVERSE, true);
+      setNext();
+    }
+
+    @Override
+    protected void setNext()
+        throws MissingObjectException, EiffelEventIdLookupException, IOException {
+      next = null;
+      RevCommit commit = rw.next();
+
+      if (parentKey.isPresent()) {
+        while (commit != null) {
+          if (isDirectChild(commit)) {
+            rw.markUninteresting(commit);
+            break;
+          }
+          commit = rw.next();
+        }
+      }
+      if (commit == null) {
+        return;
+      }
+      next = new EventCreate(commit);
+    }
+
+    private boolean isDirectChild(RevCommit commit) {
+      return Arrays.asList(commit.getParents()).stream()
+          .map(RevCommit::getName)
+          .anyMatch(parent -> parent.equals(parentKey.get().commit()));
+    }
+  }
 }
diff --git a/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParser.java b/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParser.java
index 3285993..0c39152 100644
--- a/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParser.java
+++ b/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParser.java
@@ -51,6 +51,35 @@
       throws EventParsingException;
 
   /**
+   * Recreates missing SCC events that are referenced by other, existing, events.
+   *
+   * @param repoName - Name of the repository were the commits exists.
+   * @param branchRef - Ref of the branch to create events for.
+   * @throws EventParsingException - When event-creation fails.
+   */
+  void fillGapsForSccFromBranch(String repoName, String branchRef) throws EventParsingException;
+
+  /**
+   * Recreates missing SCC events that are referenced by other, existing, events.
+   *
+   * @param repoName - Name of the repository were the commits exists.
+   * @param branchRef - Ref of the branch to create events for.
+   * @param commit - Creates missing events for all commits reachable from commit.
+   * @throws EventParsingException - When event-creation fails.
+   */
+  void fillGapsForSccFromCommit(String repoName, String branchRef, String commit)
+      throws EventParsingException;
+
+  /**
+   * Recreates missing SCS events that are referenced by other, existing, events.
+   *
+   * @param repoName - Name of the repository were the commits exists.
+   * @param branchRef - Ref of the branch to create events for.
+   * @throws EventParsingException - When event-creation fails.
+   */
+  void fillGapsForScsFromBranch(String repoName, String branchRef) throws EventParsingException;
+
+  /**
    * Creates missing SCS events for repoName, branch.
    *
    * @param repoName - Name of the repository where the branch exists.
diff --git a/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserImpl.java b/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserImpl.java
index 64a370b..d0e5267 100644
--- a/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserImpl.java
+++ b/src/main/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserImpl.java
@@ -15,6 +15,7 @@
 package com.googlesource.gerrit.plugins.eventseiffel.parsing;
 
 import static com.googlesource.gerrit.plugins.eventseiffel.eiffel.dto.EiffelEventType.SCC;
+import static com.googlesource.gerrit.plugins.eventseiffel.eiffel.dto.EiffelEventType.SCS;
 
 import com.github.rholder.retry.RetryException;
 import com.github.rholder.retry.Retryer;
@@ -39,11 +40,14 @@
 import com.googlesource.gerrit.plugins.eventseiffel.eiffel.SourceChangeEventKey;
 import com.googlesource.gerrit.plugins.eventseiffel.eiffel.dto.EiffelEvent;
 import com.googlesource.gerrit.plugins.eventseiffel.mapping.EiffelEventMapper;
-import com.googlesource.gerrit.plugins.eventseiffel.parsing.UnprocessedCommitsWalker.EventCreate;
-import com.googlesource.gerrit.plugins.eventseiffel.parsing.UnprocessedCommitsWalker.ScsWalker;
+import com.googlesource.gerrit.plugins.eventseiffel.parsing.CommitsWalker.EventCreate;
+import com.googlesource.gerrit.plugins.eventseiffel.parsing.CommitsWalker.ScsWalker;
+import com.googlesource.gerrit.plugins.eventseiffel.parsing.CommitsWalker.UnprocessedCommitsWalker;
 import java.io.IOException;
+import java.util.HashSet;
 import java.util.List;
 import java.util.Optional;
+import java.util.Set;
 import java.util.UUID;
 import java.util.concurrent.ExecutionException;
 import java.util.concurrent.TimeUnit;
@@ -68,7 +72,7 @@
 
   private final EiffelEventHub eventHub;
   private final GitRepositoryManager repoManager;
-  private final UnprocessedCommitsWalker.Factory walkerFactory;
+  private final CommitsWalker.Factory walkerFactory;
   private final EiffelEventMapper mapper;
   private final Provider<EventsFilter> eventsFilter;
 
@@ -77,7 +81,7 @@
       EiffelEventHub eventQueue,
       GitRepositoryManager repoManager,
       EiffelEventMapper mapper,
-      UnprocessedCommitsWalker.Factory walkerFactory,
+      CommitsWalker.Factory walkerFactory,
       Provider<EventsFilter> eventsFilter) {
     this.eventHub = eventQueue;
     this.repoManager = repoManager;
@@ -160,6 +164,49 @@
     }
   }
 
+  @Override
+  public void fillGapsForScsFromBranch(String repoName, String branchRef)
+      throws EventParsingException {
+    ObjectId tip = getTipOf(repoName, branchRef);
+    if (tip == null) {
+      return;
+    }
+    SourceChangeEventKey scs = SourceChangeEventKey.scsKey(repoName, branchRef, tip.getName());
+    fillGapsForSc(scs);
+  }
+
+  @Override
+  public void fillGapsForSccFromBranch(String repoName, String branchRef)
+      throws EventParsingException {
+    ObjectId tip = getTipOf(repoName, branchRef);
+    if (tip == null) {
+      return;
+    }
+    fillGapsForSccFromCommit(repoName, branchRef, tip.getName());
+  }
+
+  @Override
+  public void fillGapsForSccFromCommit(String repoName, String branchRef, String commit)
+      throws EventParsingException {
+    SourceChangeEventKey scc = SourceChangeEventKey.sccKey(repoName, branchRef, commit);
+    fillGapsForSc(scc);
+  }
+
+  @VisibleForTesting
+  private void fillGapsForSc(SourceChangeEventKey key) throws EventParsingException {
+    logger.atFine().log("Start publishing missing events starting from: %s", key);
+    try (CommitsWalker commitFinder = walkerFactory.childWalker(key)) {
+      fillGapsForSc(key, commitFinder);
+    } catch (IOException
+        | EiffelEventIdLookupException
+        | NoSuchEntityException
+        | ConfigInvalidException
+        | InterruptedException e) {
+      throw new EventParsingException(e, "Event creation failed for: %s", key);
+    }
+    logger.atFine().log("Done publishing missing events for starting from: %s", key);
+  }
+
   /* (non-Javadoc)
    * @see com.googlesource.gerrit.plugins.eventseiffel.parsing.EiffelEventParser#createAndScheduleMissingScssFromBranch(java.lang.String, java.lang.String)
    */
@@ -407,6 +454,46 @@
     }
   }
 
+  /* Callers are responsible for closing commitFinder. */
+  private void fillGapsForSc(SourceChangeEventKey tip, CommitsWalker commitFinder)
+      throws MissingObjectException, EiffelEventIdLookupException, IOException,
+          NoSuchEntityException, ConfigInvalidException, InterruptedException,
+          EventParsingException {
+
+    while (commitFinder.hasNext()) {
+      CommitsWalker.EventCreate job = commitFinder.next();
+      RevCommit commit = job.commit;
+      SourceChangeEventKey key = job.key;
+      logger.atFine().log("Processing event-creation for missing event: %s", key);
+
+      Optional<UUID> id = eventHub.getExistingId(key);
+      if (id.isEmpty()) {
+        id = findUuid(tip, key);
+        try {
+          EiffelEvent event;
+          if (key.type() == SCC) {
+            event = mapper.toScc(commit, key.repo(), key.branch(), getParentUuids(key, commit), id);
+          } else {
+            event =
+                mapper.toScs(
+                    commit,
+                    key.repo(),
+                    key.branch(),
+                    null,
+                    null,
+                    getParentUuids(key, commit),
+                    getSccUuid(key),
+                    id);
+          }
+          pushToHub(event);
+        } catch (InterruptedException e) {
+          logger.atSevere().log("Interrupted while pushing %s to EventHub.", key);
+          throw e;
+        }
+      }
+    }
+  }
+
   @VisibleForTesting
   void createAndScheduleMissingSccs(SourceChangeEventKey scc)
       throws MissingObjectException, IncorrectObjectTypeException, IOException,
@@ -472,6 +559,74 @@
     return parentIds;
   }
 
+  private UUID getSccUuid(SourceChangeEventKey key)
+      throws NoSuchEntityException, EiffelEventIdLookupException {
+    SourceChangeEventKey siblingKey = key.copy(SCC);
+    Optional<UUID> id = eventHub.getExistingId(siblingKey);
+    if (id.isPresent()) {
+      return id.get();
+    } else {
+      throw new NoSuchEntityException(
+          String.format(
+              "Unable to lookup SCC (%s) event UUID for %s even though it should exist.",
+              key.commit(), key));
+    }
+  }
+
+  /* Attempt to determine which UUID is used by other events that links to THIS event. */
+  private Optional<UUID> findUuid(SourceChangeEventKey tip, SourceChangeEventKey key)
+      throws EventParsingException, EiffelEventIdLookupException {
+    Optional<UUID> id = getUuidFromScsChangeLink(key);
+    if (id.isPresent()) {
+      return id;
+    }
+    Set<UUID> uuids = null;
+    /* Check which UUID the children of this event(commit) use to point to THIS event. */
+    try (CommitsWalker commitFinder = walkerFactory.childWalker(tip, key)) {
+      while (commitFinder.hasNext()) {
+        SourceChangeEventKey childKey = commitFinder.next().key;
+
+        Optional<List<UUID>> ids = eventHub.getParentLinks(childKey);
+        if (ids.isEmpty()) {
+          logger.atFine().log("Eiffel-event is missing for child: %s", childKey);
+          continue;
+        }
+
+        if (uuids == null) {
+          uuids = new HashSet<>(ids.get());
+        } else {
+          /* Do intersection between the set of parents for each child to determine the UUID for THIS event. */
+          uuids.retainAll(ids.get());
+        }
+        if (uuids.size() == 1) { // Found one UUID that all the processed children points to.
+          return Optional.of((UUID) uuids.toArray()[0]);
+        }
+      }
+    } catch (IOException e) {
+      throw new EventParsingException(e, "Unable to get reachable UUID for children of: %s", key);
+    }
+    if (uuids == null) {
+      /* Occur if event/s of child/s commit is missing or if the commmit of the event does not have
+      a child. In this situation we can generate a new UUID. */
+      logger.atFine().log("Could not find an event that reference: %s", key);
+      return Optional.empty();
+    }
+    /* If we found several potential UUID:s we can not generate a new UUID so we need to throw an
+    exception to prevent the creation of the event. */
+    String potentialUUID =
+        String.join(", ", uuids.stream().map(uuid -> uuid.toString()).collect(Collectors.toList()));
+    throw new EventParsingException(
+        "Found several potential UUID for %s potential UUID: %s", key, potentialUUID);
+  }
+
+  private Optional<UUID> getUuidFromScsChangeLink(SourceChangeEventKey key)
+      throws EiffelEventIdLookupException {
+    if (key.type().equals(SCC)) {
+      return eventHub.getSccEventLink(key.copy(SCS));
+    }
+    return Optional.empty();
+  }
+
   private void exceptionForMissingParent(SourceChangeEventKey key, RevCommit parent)
       throws NoSuchEntityException {
     throw new NoSuchEntityException(
diff --git a/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserIT.java b/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserIT.java
index e11ee3d..f30fe3a 100644
--- a/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserIT.java
+++ b/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/EiffelEventParserIT.java
@@ -19,7 +19,9 @@
 import static com.googlesource.gerrit.plugins.eventseiffel.eiffel.dto.EiffelEventType.SCC;
 import static com.googlesource.gerrit.plugins.eventseiffel.eiffel.dto.EiffelEventType.SCS;
 import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotEquals;
 
+import com.google.common.collect.ImmutableList;
 import com.google.gerrit.acceptance.PushOneCommit;
 import com.google.gerrit.acceptance.TestPlugin;
 import com.google.gerrit.acceptance.UseLocalDisk;
@@ -31,8 +33,13 @@
 import com.googlesource.gerrit.plugins.eventseiffel.eiffel.ArtifactEventKey;
 import com.googlesource.gerrit.plugins.eventseiffel.eiffel.CompositionDefinedEventKey;
 import com.googlesource.gerrit.plugins.eventseiffel.eiffel.SourceChangeEventKey;
+import com.googlesource.gerrit.plugins.eventseiffel.eiffel.dto.EiffelEvent;
 import com.googlesource.gerrit.plugins.eventseiffel.eiffel.dto.EiffelSourceChangeSubmittedEventInfo;
 import java.time.Instant;
+import java.util.Arrays;
+import java.util.UUID;
+import java.util.regex.Pattern;
+import java.util.stream.Collectors;
 import org.eclipse.jgit.lib.Constants;
 import org.eclipse.jgit.revwalk.RevCommit;
 import org.junit.Before;
@@ -330,6 +337,463 @@
     assertArtcQueuedScsHandled(false, NAMESPACE);
   }
 
+  @Test
+  public void missingSucceedingSccs() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle1 = pushTo(getHead()).getCommit();
+    RevCommit middle2 = pushTo(getHead()).getCommit();
+    RevCommit tip = pushTo(getHead()).getCommit();
+
+    SourceChangeEventKey scsInitial = SourceChangeEventKey.scsKey(project.get(), "master", initial);
+    SourceChangeEventKey sccInitial = scsInitial.copy(SCC);
+    SourceChangeEventKey scsMiddle1 = SourceChangeEventKey.scsKey(project.get(), "master", middle1);
+    SourceChangeEventKey sccMiddle1 = scsMiddle1.copy(SCC);
+    SourceChangeEventKey scsMiddle2 = SourceChangeEventKey.scsKey(project.get(), "master", middle2);
+    SourceChangeEventKey sccMiddle2 = scsMiddle2.copy(SCC);
+    SourceChangeEventKey scsTip = SourceChangeEventKey.scsKey(project.get(), "master", tip);
+    SourceChangeEventKey sccTip = scsTip.copy(SCC);
+    eventParser.createAndScheduleMissingScssFromBranch(project.get(), getHead());
+
+    assertEquals(8, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccTip);
+    assertCorrectEvent(4, scsInitial);
+    assertCorrectEvent(5, scsMiddle1);
+    assertCorrectEvent(6, scsMiddle2);
+    assertCorrectEvent(7, scsTip);
+
+    EiffelEvent eventSccTip = TestEventHub.EVENTS.remove(3);
+    EiffelEvent eventSccMiddle2 = TestEventHub.EVENTS.remove(2);
+    EiffelEvent eventSccMiddle1 = TestEventHub.EVENTS.remove(1);
+    EiffelEvent eventSccInitial = TestEventHub.EVENTS.remove(0);
+
+    eventParser.fillGapsForSccFromCommit(project.get(), getHead(), tip.getName());
+
+    assertEquals(8, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, scsInitial);
+    assertCorrectEvent(1, scsMiddle1);
+    assertCorrectEvent(2, scsMiddle2);
+    assertCorrectEvent(3, scsTip);
+    assertCorrectEvent(4, sccInitial);
+    assertCorrectEvent(5, sccMiddle1);
+    assertCorrectEvent(6, sccMiddle2);
+    assertCorrectEvent(7, sccTip);
+    assertEquals(eventSccInitial.meta.id, TestEventHub.EVENTS.get(4).meta.id);
+    assertEquals(eventSccMiddle1.meta.id, TestEventHub.EVENTS.get(5).meta.id);
+    assertEquals(eventSccMiddle2.meta.id, TestEventHub.EVENTS.get(6).meta.id);
+    assertEquals(eventSccTip.meta.id, TestEventHub.EVENTS.get(7).meta.id);
+    assertParentReferences(TestEventHub.EVENTS.get(5), TestEventHub.EVENTS.get(4));
+    assertParentReferences(TestEventHub.EVENTS.get(6), TestEventHub.EVENTS.get(5));
+    assertParentReferences(TestEventHub.EVENTS.get(7), TestEventHub.EVENTS.get(6));
+  }
+
+  @Test
+  public void missingSccWithNoScs() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle = pushTo(getHead()).getCommit();
+    RevCommit tip = pushTo(getHead()).getCommit();
+
+    SourceChangeEventKey scsInitial = SourceChangeEventKey.scsKey(project.get(), "master", initial);
+    SourceChangeEventKey sccInitial = scsInitial.copy(SCC);
+    SourceChangeEventKey scsMiddle = SourceChangeEventKey.scsKey(project.get(), "master", middle);
+    SourceChangeEventKey sccMiddle = scsMiddle.copy(SCC);
+    SourceChangeEventKey scsTip = SourceChangeEventKey.scsKey(project.get(), "master", tip);
+    SourceChangeEventKey sccTip = scsTip.copy(SCC);
+    eventParser.createAndScheduleMissingScssFromBranch(project.get(), getHead());
+
+    assertEquals(6, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle);
+    assertCorrectEvent(2, sccTip);
+    assertCorrectEvent(3, scsInitial);
+    assertCorrectEvent(4, scsMiddle);
+    assertCorrectEvent(5, scsTip);
+
+    TestEventHub.EVENTS.remove(3);
+    EiffelEvent eventSccMiddle = TestEventHub.EVENTS.remove(1);
+    EiffelEvent eventSccInitial = TestEventHub.EVENTS.remove(0);
+
+    eventParser.fillGapsForSccFromCommit(project.get(), getHead(), tip.getName());
+
+    assertEquals(5, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccTip);
+    assertCorrectEvent(1, scsMiddle);
+    assertCorrectEvent(2, scsTip);
+    assertCorrectEvent(3, sccInitial);
+    assertCorrectEvent(4, sccMiddle);
+
+    assertNotEquals(eventSccInitial.meta.id, TestEventHub.EVENTS.get(3).meta.id);
+    assertEquals(eventSccMiddle.meta.id, TestEventHub.EVENTS.get(4).meta.id);
+    assertParentReferences(TestEventHub.EVENTS.get(4), TestEventHub.EVENTS.get(3));
+    assertParentReferences(TestEventHub.EVENTS.get(0), TestEventHub.EVENTS.get(4));
+  }
+
+  @Test
+  public void missingAllSccs() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle = pushTo(getHead()).getCommit();
+    RevCommit tip = pushTo(getHead()).getCommit();
+
+    SourceChangeEventKey sccInitial = SourceChangeEventKey.sccKey(project.get(), "master", initial);
+    SourceChangeEventKey sccMiddle = SourceChangeEventKey.sccKey(project.get(), "master", middle);
+    SourceChangeEventKey sccTip = SourceChangeEventKey.sccKey(project.get(), "master", tip);
+
+    eventParser.fillGapsForSccFromCommit(project.get(), getHead(), tip.getName());
+
+    assertEquals(3, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle);
+    assertCorrectEvent(2, sccTip);
+    assertParentReferences(TestEventHub.EVENTS.get(1), TestEventHub.EVENTS.get(0));
+    assertParentReferences(TestEventHub.EVENTS.get(2), TestEventHub.EVENTS.get(1));
+  }
+
+  @Test
+  public void missingSucceedingScss() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle1 = pushTo(getHead()).getCommit();
+    RevCommit middle2 = pushTo(getHead()).getCommit();
+    RevCommit tip = pushTo(getHead()).getCommit();
+
+    SourceChangeEventKey scsInitial = SourceChangeEventKey.scsKey(project.get(), "master", initial);
+    SourceChangeEventKey sccInitial = scsInitial.copy(SCC);
+    SourceChangeEventKey scsMiddle1 = SourceChangeEventKey.scsKey(project.get(), "master", middle1);
+    SourceChangeEventKey sccMiddle1 = scsMiddle1.copy(SCC);
+    SourceChangeEventKey scsMiddle2 = SourceChangeEventKey.scsKey(project.get(), "master", middle2);
+    SourceChangeEventKey sccMiddle2 = scsMiddle2.copy(SCC);
+    SourceChangeEventKey scsTip = SourceChangeEventKey.scsKey(project.get(), "master", tip);
+    SourceChangeEventKey sccTip = scsTip.copy(SCC);
+    eventParser.createAndScheduleMissingScssFromBranch(project.get(), getHead());
+
+    assertEquals(8, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccTip);
+    assertCorrectEvent(4, scsInitial);
+    assertCorrectEvent(5, scsMiddle1);
+    assertCorrectEvent(6, scsMiddle2);
+    assertCorrectEvent(7, scsTip);
+
+    EiffelEvent eventScsTip = TestEventHub.EVENTS.remove(7);
+    EiffelEvent eventScsMiddle2 = TestEventHub.EVENTS.remove(6);
+    EiffelEvent eventScsMiddle1 = TestEventHub.EVENTS.remove(5);
+    EiffelEvent eventScsInitial = TestEventHub.EVENTS.remove(4);
+
+    eventParser.fillGapsForScsFromBranch(project.get(), getHead());
+
+    assertEquals(8, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccTip);
+    assertCorrectEvent(4, scsInitial);
+    assertCorrectEvent(5, scsMiddle1);
+    assertCorrectEvent(6, scsMiddle2);
+    assertCorrectEvent(7, scsTip);
+    assertNotEquals(eventScsInitial.meta.id, TestEventHub.EVENTS.get(4).meta.id);
+    assertNotEquals(eventScsMiddle1.meta.id, TestEventHub.EVENTS.get(5).meta.id);
+    assertNotEquals(eventScsMiddle2.meta.id, TestEventHub.EVENTS.get(6).meta.id);
+    assertNotEquals(eventScsTip.meta.id, TestEventHub.EVENTS.get(7).meta.id);
+    assertParentReferences(TestEventHub.EVENTS.get(5), TestEventHub.EVENTS.get(4));
+    assertParentReferences(TestEventHub.EVENTS.get(6), TestEventHub.EVENTS.get(5));
+    assertParentReferences(TestEventHub.EVENTS.get(7), TestEventHub.EVENTS.get(6));
+  }
+
+  @Test
+  public void missingScsWithMergeCommit() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle1 = pushTo(getHead()).getCommit();
+    // reset HEAD in order to create a sibling of the first change
+    testRepo.reset(initial);
+    RevCommit middle2 = pushTo(getHead()).getCommit();
+
+    PushOneCommit m = pushFactory.create(admin.newIdent(), testRepo);
+    m.setParents(ImmutableList.of(middle1, middle2));
+    PushOneCommit.Result result = m.to(getHead());
+    result.assertOkStatus();
+    RevCommit tip = result.getCommit();
+
+    SourceChangeEventKey scsInitial = SourceChangeEventKey.scsKey(project.get(), "master", initial);
+    SourceChangeEventKey sccInitial = scsInitial.copy(SCC);
+    SourceChangeEventKey scsMiddle1 = SourceChangeEventKey.scsKey(project.get(), "master", middle1);
+    SourceChangeEventKey sccMiddle1 = scsMiddle1.copy(SCC);
+    SourceChangeEventKey scsMiddle2 = SourceChangeEventKey.scsKey(project.get(), "master", middle2);
+    SourceChangeEventKey sccMiddle2 = scsMiddle2.copy(SCC);
+    SourceChangeEventKey scsTip = SourceChangeEventKey.scsKey(project.get(), "master", tip);
+    SourceChangeEventKey sccTip = scsTip.copy(SCC);
+    eventParser.createAndScheduleMissingScssFromBranch(project.get(), getHead());
+
+    assertEquals(8, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccTip);
+    assertCorrectEvent(4, scsInitial);
+    assertCorrectEvent(5, scsMiddle1);
+    assertCorrectEvent(6, scsMiddle2);
+    assertCorrectEvent(7, scsTip);
+
+    EiffelEvent eventScsTip = TestEventHub.EVENTS.remove(7);
+    EiffelEvent eventScsMiddle2 = TestEventHub.EVENTS.remove(6);
+    EiffelEvent eventScsMiddle1 = TestEventHub.EVENTS.remove(5);
+    EiffelEvent eventScsInitial = TestEventHub.EVENTS.remove(4);
+
+    eventParser.fillGapsForScsFromBranch(project.get(), getHead());
+
+    assertEquals(8, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccTip);
+    assertCorrectEvent(4, scsInitial);
+    assertCorrectEvent(5, scsMiddle1);
+    assertCorrectEvent(6, scsMiddle2);
+    assertCorrectEvent(7, scsTip);
+    assertNotEquals(eventScsInitial.meta.id, TestEventHub.EVENTS.get(4).meta.id);
+    assertNotEquals(eventScsMiddle1.meta.id, TestEventHub.EVENTS.get(5).meta.id);
+    assertNotEquals(eventScsMiddle2.meta.id, TestEventHub.EVENTS.get(6).meta.id);
+    assertNotEquals(eventScsTip.meta.id, TestEventHub.EVENTS.get(7).meta.id);
+    assertParentReferences(TestEventHub.EVENTS.get(5), TestEventHub.EVENTS.get(4));
+    assertParentReferences(TestEventHub.EVENTS.get(6), TestEventHub.EVENTS.get(4));
+    assertParentReferences(
+        TestEventHub.EVENTS.get(7), TestEventHub.EVENTS.get(5), TestEventHub.EVENTS.get(6));
+  }
+
+  @Test
+  public void missingScsWithMergeCommit3Parents() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle1 = testRepo.commit().parent(initial).create();
+    RevCommit middle2 = testRepo.commit().parent(initial).create();
+    RevCommit middle3 = testRepo.commit().parent(initial).create();
+
+    PushOneCommit m = pushFactory.create(admin.newIdent(), testRepo);
+    m.setParents(ImmutableList.of(middle1, middle2, middle3));
+    PushOneCommit.Result result = m.to(getHead());
+    result.assertOkStatus();
+    RevCommit tip = result.getCommit();
+
+    SourceChangeEventKey scsInitial = SourceChangeEventKey.scsKey(project.get(), "master", initial);
+    SourceChangeEventKey sccInitial = scsInitial.copy(SCC);
+    SourceChangeEventKey scsMiddle1 = SourceChangeEventKey.scsKey(project.get(), "master", middle1);
+    SourceChangeEventKey sccMiddle1 = scsMiddle1.copy(SCC);
+    SourceChangeEventKey scsMiddle2 = SourceChangeEventKey.scsKey(project.get(), "master", middle2);
+    SourceChangeEventKey sccMiddle2 = scsMiddle2.copy(SCC);
+    SourceChangeEventKey scsMiddle3 = SourceChangeEventKey.scsKey(project.get(), "master", middle3);
+    SourceChangeEventKey sccMiddle3 = scsMiddle3.copy(SCC);
+    SourceChangeEventKey scsTip = SourceChangeEventKey.scsKey(project.get(), "master", tip);
+    SourceChangeEventKey sccTip = scsTip.copy(SCC);
+    eventParser.createAndScheduleMissingScssFromBranch(project.get(), getHead());
+
+    assertEquals(10, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccMiddle3);
+    assertCorrectEvent(4, sccTip);
+    assertCorrectEvent(5, scsInitial);
+    assertCorrectEvent(6, scsMiddle1);
+    assertCorrectEvent(7, scsMiddle2);
+    assertCorrectEvent(8, scsMiddle3);
+    assertCorrectEvent(9, scsTip);
+
+    EiffelEvent eventScsTip = TestEventHub.EVENTS.remove(9);
+    EiffelEvent eventScsMiddle3 = TestEventHub.EVENTS.remove(8);
+    EiffelEvent eventScsMiddle2 = TestEventHub.EVENTS.remove(7);
+    EiffelEvent eventScsMiddle1 = TestEventHub.EVENTS.remove(6);
+    EiffelEvent eventScsInitial = TestEventHub.EVENTS.remove(5);
+
+    eventParser.fillGapsForScsFromBranch(project.get(), getHead());
+
+    assertEquals(10, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccMiddle3);
+    assertCorrectEvent(4, sccTip);
+    assertCorrectEvent(5, scsInitial);
+    assertCorrectEvent(6, scsMiddle1);
+    assertCorrectEvent(7, scsMiddle2);
+    assertCorrectEvent(8, scsMiddle3);
+    assertCorrectEvent(9, scsTip);
+    assertNotEquals(eventScsInitial.meta.id, TestEventHub.EVENTS.get(5).meta.id);
+    assertNotEquals(eventScsMiddle1.meta.id, TestEventHub.EVENTS.get(6).meta.id);
+    assertNotEquals(eventScsMiddle2.meta.id, TestEventHub.EVENTS.get(7).meta.id);
+    assertNotEquals(eventScsMiddle3.meta.id, TestEventHub.EVENTS.get(8).meta.id);
+    assertNotEquals(eventScsTip.meta.id, TestEventHub.EVENTS.get(9).meta.id);
+    assertParentReferences(TestEventHub.EVENTS.get(6), TestEventHub.EVENTS.get(5));
+    assertParentReferences(TestEventHub.EVENTS.get(7), TestEventHub.EVENTS.get(5));
+    assertParentReferences(TestEventHub.EVENTS.get(8), TestEventHub.EVENTS.get(5));
+    assertParentReferences(
+        TestEventHub.EVENTS.get(9),
+        TestEventHub.EVENTS.get(6),
+        TestEventHub.EVENTS.get(7),
+        TestEventHub.EVENTS.get(8));
+  }
+
+  @Test
+  public void missingScsWithCommonParents() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle1 = testRepo.commit().parent(initial).create();
+    RevCommit middle2 = testRepo.commit().parent(initial).create();
+    RevCommit middle3 = testRepo.commit().parent(middle1).parent(middle2).create();
+    RevCommit middle4 = testRepo.commit().parent(middle1).parent(middle2).create();
+
+    PushOneCommit m = pushFactory.create(admin.newIdent(), testRepo);
+    m.setParents(ImmutableList.of(middle3, middle4));
+    PushOneCommit.Result result = m.to(getHead());
+    result.assertOkStatus();
+    RevCommit tip = result.getCommit();
+
+    SourceChangeEventKey scsInitial = SourceChangeEventKey.scsKey(project.get(), "master", initial);
+    SourceChangeEventKey sccInitial = scsInitial.copy(SCC);
+    SourceChangeEventKey scsMiddle1 = SourceChangeEventKey.scsKey(project.get(), "master", middle1);
+    SourceChangeEventKey sccMiddle1 = scsMiddle1.copy(SCC);
+    SourceChangeEventKey scsMiddle2 = SourceChangeEventKey.scsKey(project.get(), "master", middle2);
+    SourceChangeEventKey sccMiddle2 = scsMiddle2.copy(SCC);
+    SourceChangeEventKey scsMiddle3 = SourceChangeEventKey.scsKey(project.get(), "master", middle3);
+    SourceChangeEventKey sccMiddle3 = scsMiddle3.copy(SCC);
+    SourceChangeEventKey scsMiddle4 = SourceChangeEventKey.scsKey(project.get(), "master", middle4);
+    SourceChangeEventKey sccMiddle4 = scsMiddle4.copy(SCC);
+    SourceChangeEventKey scsTip = SourceChangeEventKey.scsKey(project.get(), "master", tip);
+    SourceChangeEventKey sccTip = scsTip.copy(SCC);
+    eventParser.createAndScheduleMissingScssFromBranch(project.get(), getHead());
+
+    assertEquals(12, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccMiddle3);
+    assertCorrectEvent(4, sccMiddle4);
+    assertCorrectEvent(5, sccTip);
+    assertCorrectEvent(6, scsInitial);
+    assertCorrectEvent(7, scsMiddle1);
+    assertCorrectEvent(8, scsMiddle2);
+    assertCorrectEvent(9, scsMiddle3);
+    assertCorrectEvent(10, scsMiddle4);
+    assertCorrectEvent(11, scsTip);
+
+    EiffelEvent eventScsMiddle1 = TestEventHub.EVENTS.remove(7);
+
+    EventParsingException thrown =
+        assertThrows(
+            EventParsingException.class,
+            () -> eventParser.fillGapsForScsFromBranch(project.get(), getHead()));
+    UUID id1 = eventScsMiddle1.meta.id;
+    UUID id2 = TestEventHub.EVENTS.get(7).meta.id;
+    String expectedMessage =
+        String.format(
+            "Found several potential UUID for %s potential UUID: (%2$s, %3$s|%3$s, %2$s)$",
+            Pattern.quote(scsMiddle1.toString()), id1, id2);
+    assertThat(thrown).hasMessageThat().matches(expectedMessage);
+
+    assertEquals(11, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccMiddle3);
+    assertCorrectEvent(4, sccMiddle4);
+    assertCorrectEvent(5, sccTip);
+    assertCorrectEvent(6, scsInitial);
+    assertCorrectEvent(7, scsMiddle2);
+    assertCorrectEvent(8, scsMiddle3);
+    assertCorrectEvent(9, scsMiddle4);
+    assertCorrectEvent(10, scsTip);
+  }
+
+  @Test
+  public void missingScsWithCircularCommonParents() throws Exception {
+    RevCommit initial = getHead(repo(), "HEAD");
+    RevCommit middle1 = testRepo.commit().parent(initial).create();
+    RevCommit middle2 = testRepo.commit().parent(initial).create();
+    RevCommit middle3 = testRepo.commit().parent(initial).create();
+    RevCommit middle4 = testRepo.commit().parent(initial).create();
+    RevCommit middle5 = testRepo.commit().parent(middle1).parent(middle2).parent(middle3).create();
+    RevCommit middle6 = testRepo.commit().parent(middle2).parent(middle3).parent(middle4).create();
+    RevCommit middle7 = testRepo.commit().parent(middle3).parent(middle4).parent(middle1).create();
+
+    PushOneCommit m = pushFactory.create(admin.newIdent(), testRepo);
+    m.setParents(ImmutableList.of(middle5, middle6, middle7));
+    PushOneCommit.Result result = m.to(getHead());
+    result.assertOkStatus();
+    RevCommit tip = result.getCommit();
+
+    SourceChangeEventKey scsInitial = SourceChangeEventKey.scsKey(project.get(), "master", initial);
+    SourceChangeEventKey sccInitial = scsInitial.copy(SCC);
+    SourceChangeEventKey scsMiddle1 = SourceChangeEventKey.scsKey(project.get(), "master", middle1);
+    SourceChangeEventKey sccMiddle1 = scsMiddle1.copy(SCC);
+    SourceChangeEventKey scsMiddle2 = SourceChangeEventKey.scsKey(project.get(), "master", middle2);
+    SourceChangeEventKey sccMiddle2 = scsMiddle2.copy(SCC);
+    SourceChangeEventKey scsMiddle3 = SourceChangeEventKey.scsKey(project.get(), "master", middle3);
+    SourceChangeEventKey sccMiddle3 = scsMiddle3.copy(SCC);
+    SourceChangeEventKey scsMiddle4 = SourceChangeEventKey.scsKey(project.get(), "master", middle4);
+    SourceChangeEventKey sccMiddle4 = scsMiddle4.copy(SCC);
+    SourceChangeEventKey scsMiddle5 = SourceChangeEventKey.scsKey(project.get(), "master", middle5);
+    SourceChangeEventKey sccMiddle5 = scsMiddle5.copy(SCC);
+    SourceChangeEventKey scsMiddle6 = SourceChangeEventKey.scsKey(project.get(), "master", middle6);
+    SourceChangeEventKey sccMiddle6 = scsMiddle6.copy(SCC);
+    SourceChangeEventKey scsMiddle7 = SourceChangeEventKey.scsKey(project.get(), "master", middle7);
+    SourceChangeEventKey sccMiddle7 = scsMiddle7.copy(SCC);
+    SourceChangeEventKey scsTip = SourceChangeEventKey.scsKey(project.get(), "master", tip);
+    SourceChangeEventKey sccTip = scsTip.copy(SCC);
+    eventParser.createAndScheduleMissingScssFromBranch(project.get(), getHead());
+
+    assertEquals(18, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccMiddle3);
+    assertCorrectEvent(4, sccMiddle4);
+    assertCorrectEvent(5, sccMiddle5);
+    assertCorrectEvent(6, sccMiddle6);
+    assertCorrectEvent(7, sccMiddle7);
+    assertCorrectEvent(8, sccTip);
+    assertCorrectEvent(9, scsInitial);
+    assertCorrectEvent(10, scsMiddle1);
+    assertCorrectEvent(11, scsMiddle2);
+    assertCorrectEvent(12, scsMiddle3);
+    assertCorrectEvent(13, scsMiddle4);
+    assertCorrectEvent(14, scsMiddle5);
+    assertCorrectEvent(15, scsMiddle6);
+    assertCorrectEvent(16, scsMiddle7);
+    assertCorrectEvent(17, scsTip);
+
+    EiffelEvent eventScsMiddle3 = TestEventHub.EVENTS.remove(12);
+
+    eventParser.fillGapsForScsFromBranch(project.get(), getHead());
+
+    assertEquals(18, TestEventHub.EVENTS.size());
+    assertCorrectEvent(0, sccInitial);
+    assertCorrectEvent(1, sccMiddle1);
+    assertCorrectEvent(2, sccMiddle2);
+    assertCorrectEvent(3, sccMiddle3);
+    assertCorrectEvent(4, sccMiddle4);
+    assertCorrectEvent(5, sccMiddle5);
+    assertCorrectEvent(6, sccMiddle6);
+    assertCorrectEvent(7, sccMiddle7);
+    assertCorrectEvent(8, sccTip);
+    assertCorrectEvent(9, scsInitial);
+    assertCorrectEvent(10, scsMiddle1);
+    assertCorrectEvent(11, scsMiddle2);
+    assertCorrectEvent(12, scsMiddle4);
+    assertCorrectEvent(13, scsMiddle5);
+    assertCorrectEvent(14, scsMiddle6);
+    assertCorrectEvent(15, scsMiddle7);
+    assertCorrectEvent(16, scsTip);
+    assertCorrectEvent(17, scsMiddle3);
+    assertEquals(eventScsMiddle3.meta.id, TestEventHub.EVENTS.get(17).meta.id);
+    assertParentReferences(TestEventHub.EVENTS.get(17), TestEventHub.EVENTS.get(9));
+  }
+
+  private void assertParentReferences(EiffelEvent child, EiffelEvent... parents) {
+    for (EiffelEvent parent : parents) {
+      assertThat(Arrays.stream(child.links).map(link -> link.target).collect(Collectors.toList()))
+          .contains(parent.meta.id);
+    }
+  }
+
   private void assertArtcQueuedScsHandled(boolean annotated) throws Exception {
     assertArtcQueuedScsHandled(annotated, "localhost");
   }
diff --git a/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/ParsingQueuePersistenceIT.java b/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/ParsingQueuePersistenceIT.java
index 8c9ed72..a5a2cc8 100644
--- a/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/ParsingQueuePersistenceIT.java
+++ b/src/test/java/com/googlesource/gerrit/plugins/eventseiffel/parsing/ParsingQueuePersistenceIT.java
@@ -198,6 +198,15 @@
     public void createAndScheduleSccFromCommit(String repoName, String branchRef, String commit) {}
 
     @Override
+    public void fillGapsForSccFromBranch(String repoName, String branchRef) {}
+
+    @Override
+    public void fillGapsForSccFromCommit(String repoName, String branchRef, String commit) {}
+
+    @Override
+    public void fillGapsForScsFromBranch(String repoName, String branchRef) {}
+
+    @Override
     public void createAndScheduleMissingScssFromBranch(String repoName, String branchRef) {}
 
     @Override
