@Override
  public ProjectRelationshipFilter getChildFilter(final ProjectRelationship<?, ?> parent) {
    final DependencyScope nextScope = ScopeTransitivity.maven.getChildFor(scope);
    boolean construct = nextScope != scope;

    Set<ProjectRef> nextExcludes = excludes;

    if (parent instanceof DependencyRelationship) {
      final DependencyRelationship dr = (DependencyRelationship) parent;

      nextExcludes = dr.getExcludes();
      if (nextExcludes != null && !nextExcludes.isEmpty()) {
        construct = true;

        final Set<ProjectRef> ex = new HashSet<ProjectRef>();

        if (excludes != null) {
          ex.addAll(excludes);
        }

        for (final ProjectRef pr : dr.getExcludes()) {
          ex.add(pr.asProjectRef());
        }

        nextExcludes = ex;
      }
    }

    return construct ? new BetterDepFilter(nextScope, nextExcludes) : this;
  }
  @Test
  public void storeProjectAndRetrieveAllRelationshipsInOneGo() throws Exception {
    final ProjectVersionRef p =
        new SimpleProjectVersionRef("org.apache.maven", "maven-core", "3.0.3");

    final EProjectDirectRelationships.Builder prb =
        new EProjectDirectRelationships.Builder(sourceUri, p);

    final ProjectVersionRef parent =
        new SimpleProjectVersionRef("org.apache.maven", "maven", "3.0.3");

    int idx = 0;
    int pidx = 0;
    final DependencyRelationship papi =
        new SimpleDependencyRelationship(
            sourceUri,
            p,
            new SimpleArtifactRef(
                "org.apache.maven", "maven-plugin-api", "3.0.3", null, null, false),
            DependencyScope.compile,
            idx++,
            false,
            false);
    final DependencyRelationship art =
        new SimpleDependencyRelationship(
            sourceUri,
            p,
            new SimpleArtifactRef("org.apache.maven", "maven-artifact", "3.0.3", null, null, false),
            DependencyScope.compile,
            idx++,
            false,
            false);
    final PluginRelationship jarp =
        new SimplePluginRelationship(
            sourceUri,
            p,
            new SimpleProjectVersionRef("org.apache.maven.plugins", "maven-jar-plugin", "2.2"),
            pidx++,
            false,
            false);
    final PluginRelationship comp =
        new SimplePluginRelationship(
            sourceUri,
            p,
            new SimpleProjectVersionRef(
                "org.apache.maven.plugins", "maven-compiler-plugin", "2.3.2"),
            pidx++,
            false,
            false);
    final ExtensionRelationship wag =
        new SimpleExtensionRelationship(
            sourceUri,
            p,
            new SimpleProjectVersionRef("org.apache.maven.wagon", "wagon-provider-webdav", "1.0"),
            0,
            false);

    prb.withParent(parent);
    prb.withDependencies(papi, art);
    prb.withPlugins(jarp, comp);
    prb.withExtensions(wag);

    final EProjectDirectRelationships rels = prb.build();

    assertThat(rels.getAllRelationships().size(), equalTo(6));

    graph.storeRelationships(rels.getExactAllRelationships());

    final Set<ProjectRelationship<?, ?>> resulting =
        graph.findDirectRelationshipsFrom(rels.getProjectRef(), false, RelationshipType.values());

    final Set<ProjectVersionRef> targets = RelationshipUtils.targets(resulting);

    assertThat(targets.size(), equalTo(6));
    assertThat(targets.contains(parent), equalTo(true));
    assertThat(targets.contains(papi.getTarget()), equalTo(true));
    assertThat(targets.contains(art.getTarget()), equalTo(true));
    assertThat(targets.contains(jarp.getTarget()), equalTo(true));
    assertThat(targets.contains(comp.getTarget()), equalTo(true));
    assertThat(targets.contains(wag.getTarget()), equalTo(true));
  }
  private void calculateDependencyPluginPatch(
      final List<DependencyView> depArtifactItems,
      final Map<VersionlessArtifactRef, DependencyRelationship> concreteDeps,
      final ProjectVersionRef ref,
      final MavenPomView pomView,
      final DiscoveryResult result) {
    logger.debug(
        "Detected {} dependency-plugin artifactItems that need to be accounted for in dependencies...",
        depArtifactItems == null ? 0 : depArtifactItems.size());
    if (depArtifactItems != null && !depArtifactItems.isEmpty()) {
      final URI source = result.getSource();
      for (final DependencyView depView : depArtifactItems) {
        try {
          final URI pomLocation = RelationshipUtils.profileLocation(depView.getProfileId());
          final VersionlessArtifactRef depRef = depView.asVersionlessArtifactRef();
          logger.debug("Detected dependency-plugin usage with key: {}", depRef);

          final DependencyRelationship dep = concreteDeps.get(depRef);
          if (dep != null) {
            if (!DependencyScope.runtime.implies(dep.getScope())
                && (dep.getPomLocation().equals(pomLocation)
                    || dep.getPomLocation() == POM_ROOT_URI)) {
              logger.debug("Correcting scope for: {}", dep);

              if (!result.removeDiscoveredRelationship(dep)) {
                logger.error("Failed to remove: {}", dep);
              }

              final Set<ProjectRef> excludes = dep.getExcludes();
              final ProjectRef[] excludedRefs =
                  excludes == null
                      ? new ProjectRef[0]
                      : excludes.toArray(new ProjectRef[excludes.size()]);

              final DependencyRelationship replacement =
                  new SimpleDependencyRelationship(
                      dep.getSources(),
                      ref,
                      dep.getTargetArtifact(),
                      DependencyScope.embedded,
                      dep.getIndex(),
                      false,
                      depView.getOriginInfo().isInherited(),
                      depView.isOptional(),
                      excludedRefs);

              if (!result.addDiscoveredRelationship(replacement)) {
                logger.error("Failed to inject: {}", replacement);
              }
            }
          } else if (depView.getVersion() != null) {
            logger.debug("Injecting new dep: {}", depView.asArtifactRef());
            final DependencyRelationship injected =
                new SimpleDependencyRelationship(
                    source,
                    RelationshipUtils.profileLocation(depView.getProfileId()),
                    ref,
                    depView.asArtifactRef(),
                    DependencyScope.embedded,
                    concreteDeps.size(),
                    false,
                    depView.getOriginInfo().isInherited(),
                    depView.isOptional());

            if (!result.addDiscoveredRelationship(injected)) {
              logger.error("Failed to inject: {}", injected);
            }
          } else {
            logger.error(
                "Invalid dependency referenced in artifactItems of dependency plugin configuration: {}. "
                    + "No version was specified, and it does not reference an actual dependency.",
                depRef);
          }
        } catch (final GalleyMavenException e) {
          logger.error(
              String.format(
                  "Dependency is invalid: %s. Reason: %s. Skipping.",
                  depView.toXML(), e.getMessage()),
              e);
        } catch (final InvalidVersionSpecificationException e) {
          logger.error(
              String.format(
                  "Dependency is invalid: %s. Reason: %s. Skipping.",
                  depView.toXML(), e.getMessage()),
              e);
        } catch (final InvalidRefException e) {
          logger.error(
              String.format(
                  "Dependency is invalid: %s. Reason: %s. Skipping.",
                  depView.toXML(), e.getMessage()),
              e);
        }
      }
    }
  }