Tracking the Progress of a Running Custom PGX Graph Algorithm

You can track the progress of a running custom graph algorithm using the AlgorithmProgress Java API.

The AlgorithmProgress object, which comprises the umberOfStepsCompleted and umberOfStepsEstimatedForCompletion attributes, is used to calculate the progress of the algorithm as a percentage.

In case of custom algorithms, the value of umberOfStepsEstimatedForCompletion is not automatically provided. You are therefore expected to provide the value by calling ControlFlow.setNumberOfStepsEstimatedForCompletion while implementing your algorithms. If no value is provided, or the provided value is negative, then umber_of_steps_estimated_for_completion uses the default ull` value.

The following example describes the steps for setting the umberOfStepsEstimatedForCompletion value in a custom graph algorithm followed by tracking and estimating the progress as a percentage of a running custom graph algorithm using the AlgorithmProgress` Java API.

  1. Set the value for umberOfStepsEstimatedForCompletion` in your custom graph algorithm.

    Note that you cannot estimate the progress as a percentage for algorithms that do not provide a value for umberOfStepsEstimatedForCompletion. However you can still access the value of the counter ( umberOfStepsCompleted).

    The value of umberOfStepsEstimatedForCompletion` should ideally be equal to the total number of execution steps that an algorithm will perform. An execution step is simply a loop iteration. If the exact value cannot be specified, you should provide an upper bound estimate of that value.

    Consider the following outDegreeCentrality algorithm:

    import oracle.pgx.algorithm.PgxGraph;
    import oracle.pgx.algorithm.VertexProperty;
    import oracle.pgx.algorithm.annotations.GraphAlgorithm;
    import oracle.pgx.algorithm.annotations.Out;
    import oracle.pgx.algorithm.ControlFlow;
    
    @GraphAlgorithm
    public class OutdegreeCentrality {
      public void outdegreeCentrality(PgxGraph g, @Out VertexProperty<Integer> outdegreeCentrality) {
        g.getVertices().forEach(n ->
            outdegreeCentrality.set(n, (int) n.getOutDegree())
        );
      }
    }

    The algorithm just iterates over all vertices of the graph and updates a property. Therefore, the total number of execution steps in this case is equal to the number of vertices of the graph:

    @GraphAlgorithm
    public class OutdegreeCentrality {
      public void outdegreeCentrality(PgxGraph g, @Out VertexProperty<Integer> outdegreeCentrality) {
    
        long totNbOfSteps = g.getNumVertices();
    
    ControlFlow.setNumberOfStepsEstimatedForCompletion(totNbOfSteps);
    
        g.getVertices().forEach(n ->
            outdegreeCentrality.set(n, (int) n.getOutDegree())
        );
      }
    }
  2. Run and track the progress of the custom Out-Degree Centrality algorithm as shown:

    opg4j> var myAlgorithm = session.compileProgram("/path/to/OutdegreeCentrality.java")
    myAlgorithm ==> CompiledProgram[name=outdegreeCentrality]
    opg4j> var graph = session.readGraphByName("BANK_TXN_GRAPH", GraphSource.PG_PGQL)
    graph ==> PgxGraph[name=BANK_TXN_GRAPH,N=1000,E=4993,created=1712307339271]
    opg4j> var future = analyst.outDegreeCentralityAsync(graph)
    future ==> oracle.pgx.api.PgxFuture@55fe9c2f[Not completed]
    opg4j> var futureProgress = future.getProgress()
    futureProgress ==> oracle.pgx.api.DefaultFutureProgress@637506d8
    opg4j> var algorithmProgress = futureProgress.asAlgorithmExecutionProgress()
    import oracle.pgx.algorithm.CompiledProgram;
    
    CompiledProgram myAlgorithm = session.compileProgram("/path/to/OutdegreeCentrality.java");
    PgxGraph graph = session.readGraphByName("BANK_TXN_GRAPH", GraphSource.PG_PGQL);
    PgxFuture<?> future = analyst.pagerankAsync(graph);
    FutureProgress futureProgress = future.getProgress();
    Optional<AlgorithmProgress> algorithmProgress = futureProgress.asAlgorithmExecutionProgress();
  3. Estimate the progress of the running algorithm as a percentage.

    •     if (algorithmProgress.isPresent()) {
            AlgorithmProgress progress = algorithmProgress.get();
            long completedSteps = progress.getNumberOfStepsCompleted();
            Long numberOfStepsEstimatedForCompletion = progress.getNumberOfStepsEstimatedForCompletion();
            long progressPercentage = completedSteps * 100 / numberOfStepsEstimatedForCompletion;
            System.out.println(completedSteps); // 153
            System.out.println(numberOfStepsEstimatedForCompletion); // 2343
            System.out.println(progressPercentage); // 6.53
          }
      <pre class="copy"><code>-</code></pre>
            if (algorithmProgress.isPresent()) {
              AlgorithmProgress progress = algorithmProgress.get();
              long completedSteps = progress.getNumberOfStepsCompleted();
              Long numberOfStepsEstimatedForCompletion = progress.getNumberOfStepsEstimatedForCompletion();
              long progressPercentage = completedSteps * 100 / numberOfStepsEstimatedForCompletion;
              System.out.println(completedSteps); // 153
              System.out.println(numberOfStepsEstimatedForCompletion); // 2343
              System.out.println(progressPercentage); // 6.53
            };
      

    The preceding code shows the progress as 6.53 % at that current moment. If you try to get the progress of the running algorithm after a while (for example, 1min), then you should get a larger value.

    See Also: Getting the Progress of a Running Algorithm