You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

LeaderSnapshot.java 3.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153
  1. /*
  2. * Copyright (C) 2016, Google Inc. and others
  3. *
  4. * This program and the accompanying materials are made available under the
  5. * terms of the Eclipse Distribution License v. 1.0 which is available at
  6. * https://www.eclipse.org/org/documents/edl-v10.php.
  7. *
  8. * SPDX-License-Identifier: BSD-3-Clause
  9. */
  10. package org.eclipse.jgit.internal.ketch;
  11. import static org.eclipse.jgit.internal.ketch.KetchReplica.State.OFFLINE;
  12. import java.util.ArrayList;
  13. import java.util.Collection;
  14. import java.util.Collections;
  15. import java.util.List;
  16. import org.eclipse.jgit.annotations.Nullable;
  17. import org.eclipse.jgit.lib.ObjectId;
  18. /**
  19. * A snapshot of a leader and its view of the world.
  20. */
  21. public class LeaderSnapshot {
  22. final List<ReplicaSnapshot> replicas = new ArrayList<>();
  23. KetchLeader.State state;
  24. long term;
  25. LogIndex headIndex;
  26. LogIndex committedIndex;
  27. boolean idle;
  28. LeaderSnapshot() {
  29. }
  30. /**
  31. * Get unmodifiable view of configured replicas.
  32. *
  33. * @return unmodifiable view of configured replicas.
  34. */
  35. public Collection<ReplicaSnapshot> getReplicas() {
  36. return Collections.unmodifiableList(replicas);
  37. }
  38. /**
  39. * Get current state of the leader.
  40. *
  41. * @return current state of the leader.
  42. */
  43. public KetchLeader.State getState() {
  44. return state;
  45. }
  46. /**
  47. * Whether the leader is not running a round to reach consensus, and has no
  48. * rounds queued.
  49. *
  50. * @return {@code true} if the leader is not running a round to reach
  51. * consensus, and has no rounds queued.
  52. */
  53. public boolean isIdle() {
  54. return idle;
  55. }
  56. /**
  57. * Get term of this leader
  58. *
  59. * @return term of this leader. Valid only if {@link #getState()} is
  60. * currently
  61. * {@link org.eclipse.jgit.internal.ketch.KetchLeader.State#LEADER}.
  62. */
  63. public long getTerm() {
  64. return term;
  65. }
  66. /**
  67. * Get end of the leader's log
  68. *
  69. * @return end of the leader's log; null if leader hasn't started up enough
  70. * to begin its own election.
  71. */
  72. @Nullable
  73. public LogIndex getHead() {
  74. return headIndex;
  75. }
  76. /**
  77. * Get state the leader knows is committed on a majority of participant
  78. * replicas
  79. *
  80. * @return state the leader knows is committed on a majority of participant
  81. * replicas. Null until the leader instance has committed a log
  82. * index within its own term.
  83. */
  84. @Nullable
  85. public LogIndex getCommitted() {
  86. return committedIndex;
  87. }
  88. /** {@inheritDoc} */
  89. @Override
  90. public String toString() {
  91. StringBuilder s = new StringBuilder();
  92. s.append(isIdle() ? "IDLE" : "RUNNING"); //$NON-NLS-1$ //$NON-NLS-2$
  93. s.append(" state ").append(getState()); //$NON-NLS-1$
  94. if (getTerm() > 0) {
  95. s.append(" term ").append(getTerm()); //$NON-NLS-1$
  96. }
  97. s.append('\n');
  98. s.append(String.format(
  99. "%-10s %12s %12s\n", //$NON-NLS-1$
  100. "Replica", "Accepted", "Committed")); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
  101. s.append("------------------------------------\n"); //$NON-NLS-1$
  102. debug(s, "(leader)", getHead(), getCommitted()); //$NON-NLS-1$
  103. s.append('\n');
  104. for (ReplicaSnapshot r : getReplicas()) {
  105. debug(s, r);
  106. s.append('\n');
  107. }
  108. s.append('\n');
  109. return s.toString();
  110. }
  111. private static void debug(StringBuilder b, ReplicaSnapshot s) {
  112. KetchReplica replica = s.getReplica();
  113. debug(b, replica.getName(), s.getAccepted(), s.getCommitted());
  114. b.append(String.format(" %-8s %s", //$NON-NLS-1$
  115. replica.getParticipation(), s.getState()));
  116. if (s.getState() == OFFLINE) {
  117. String err = s.getErrorMessage();
  118. if (err != null) {
  119. b.append(" (").append(err).append(')'); //$NON-NLS-1$
  120. }
  121. }
  122. }
  123. private static void debug(StringBuilder s, String name,
  124. ObjectId accepted, ObjectId committed) {
  125. s.append(String.format(
  126. "%-10s %-12s %-12s", //$NON-NLS-1$
  127. name, str(accepted), str(committed)));
  128. }
  129. static String str(ObjectId c) {
  130. if (c instanceof LogIndex) {
  131. return ((LogIndex) c).describeForLog();
  132. } else if (c != null) {
  133. return c.abbreviate(8).name();
  134. }
  135. return "-"; //$NON-NLS-1$
  136. }
  137. }