SENTRY-2419: Log where sentry stands in the process of persisting the snpashot (Arjun Mishra reviewed by Na Li and Sergio Pena)
Change-Id: I0fa1af7ab45a3a27d9c9984fa96634f89f28316c
diff --git a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryMetrics.java b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryMetrics.java
index d34340c..214d78c 100644
--- a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryMetrics.java
+++ b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryMetrics.java
@@ -175,8 +175,12 @@
sentryStore.getLastPathsSnapshotIdGauge());
addGauge(SentryStore.class, "hms.perm.change.id",
sentryStore.getPermChangeIdGauge());
- addGauge(SentryStore.class, "hms.psth.change.id",
+ addGauge(SentryStore.class, "hms.path.change.id",
sentryStore.getPathChangeIdGauge());
+ addGauge(SentryStore.class, "hms.authz_objects_count",
+ sentryStore.getAuthzObjectsCountGauge());
+ addGauge(SentryStore.class, "hms.authz_paths_count",
+ sentryStore.getAuthzPathsCountGauge());
gaugesAdded = true;
}
}
diff --git a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/HMSFollower.java b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/HMSFollower.java
index b6dca7a..e5cb5b0 100644
--- a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/HMSFollower.java
+++ b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/HMSFollower.java
@@ -419,7 +419,7 @@
}
try {
if (hdfsSyncEnabled) {
- String logMessage = String.format("Persisting full snapshot for notification Id = %d", snapshotInfo.getId());
+ String logMessage = String.format("Persisting full snapshot for notification Id = %d. Number of authorization objects = %d", snapshotInfo.getId(), snapshotInfo.getPathImage().size());
LOGGER.info(logMessage);
System.out.println(SentryServiceUtil.getCurrentTimeStampWithMessage(logMessage));
sentryStore.persistFullPathsImage(snapshotInfo.getPathImage(), snapshotInfo.getId());
diff --git a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java
index 7a736ca..29f83a8 100644
--- a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java
+++ b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java
@@ -189,6 +189,9 @@
*/
private final CounterWait counterWait;
+ // 5 min interval
+ private final long printSnapshotPersistTimeInterval = 300000;
+
private final boolean ownerPrivilegeWithGrant;
public static Properties getDataNucleusProperties(Configuration conf)
throws SentrySiteConfigurationException, IOException {
@@ -475,6 +478,34 @@
}
/**
+ * @return Number of authz objects persisted
+ */
+ public Gauge<Long> getAuthzObjectsCountGauge() {
+ return () -> {
+ try {
+ return getCount(MAuthzPathsMapping.class);
+ } catch (Exception e) {
+ LOGGER.error("Cannot read AUTHZ_PATHS_MAPPING table", e);
+ return NOTIFICATION_UNKNOWN;
+ }
+ };
+ }
+
+ /**
+ * @return Number of authz paths persisted
+ */
+ public Gauge<Long> getAuthzPathsCountGauge() {
+ return () -> {
+ try {
+ return getCount(MPath.class);
+ } catch (Exception e) {
+ LOGGER.error("Cannot read AUTHZ_PATH table", e);
+ return NOTIFICATION_UNKNOWN;
+ }
+ };
+ }
+
+ /**
* @return number of threads waiting for HMS notifications to be processed
*/
public Gauge<Integer> getHMSWaitersCountGauge() {
@@ -3390,6 +3421,14 @@
final long notificationID) throws Exception {
tm.executeTransactionWithRetry(
pm -> {
+
+ int totalNumberOfObjectsToPersist = authzPaths.size();
+ int totalNumberOfPathsToPersist = authzPaths.values().stream().mapToInt(Collection::size).sum();
+ int objectsPersistedCount = 0, pathsPersistedCount = 0;
+
+ logPersistingFullSnapshotState(totalNumberOfObjectsToPersist,
+ totalNumberOfPathsToPersist, objectsPersistedCount, pathsPersistedCount);
+
pm.setDetachAllOnCommit(false); // No need to detach objects
deleteNotificationsSince(pm, notificationID + 1);
@@ -3401,13 +3440,42 @@
long nextSnapshotID = snapshotID + 1;
pm.makePersistent(new MAuthzPathsSnapshotId(nextSnapshotID));
LOGGER.info("Attempting to commit new HMS snapshot with ID = {}", nextSnapshotID);
+
+ long lastProgressTime = System.currentTimeMillis();
+
for (Map.Entry<String, Collection<String>> authzPath : authzPaths.entrySet()) {
pm.makePersistent(new MAuthzPathsMapping(nextSnapshotID, authzPath.getKey(), authzPath.getValue()));
+
+ objectsPersistedCount++;
+ pathsPersistedCount = pathsPersistedCount + authzPath.getValue().size();
+
+ long currentTime = System.currentTimeMillis();
+ if ((currentTime - lastProgressTime) > printSnapshotPersistTimeInterval) {
+
+ logPersistingFullSnapshotState(totalNumberOfObjectsToPersist,
+ totalNumberOfPathsToPersist, objectsPersistedCount, pathsPersistedCount);
+
+ lastProgressTime = currentTime;
+ }
}
return null;
});
}
+ public void logPersistingFullSnapshotState(int totalNumberOfObjectsToPersist,
+ int totalNumberOfPathsToPersist, int objectsPersistedCount, int pathsPersistedCount) {
+
+ LOGGER.info(String.format("Persisting HMS Paths on Snapshot: "
+ + "authz_objs_persisted=%d(%.2f%%) authz_paths_persisted=%d(%.2f%%) "
+ + "authz_objs_total=%d authz_paths_total=%d",
+ objectsPersistedCount,
+ totalNumberOfObjectsToPersist > 0 ? 100 * ((double) objectsPersistedCount
+ / totalNumberOfObjectsToPersist) : 0,
+ pathsPersistedCount, totalNumberOfPathsToPersist > 0 ? 100 * ((double) pathsPersistedCount
+ / totalNumberOfPathsToPersist) : 0,
+ totalNumberOfObjectsToPersist, totalNumberOfPathsToPersist));
+ }
+
/**
* Get the last authorization path snapshot ID persisted.
* Always executed in the transaction context.
diff --git a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java
index 3a68eb6..6217719 100644
--- a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java
+++ b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java
@@ -473,6 +473,16 @@
Gauge<Long> getPathChangeIdGauge();
/**
+ * @return Number of objects persisted
+ */
+ Gauge<Long> getAuthzObjectsCountGauge();
+
+ /**
+ * @return Number of objects persisted
+ */
+ Gauge<Long> getAuthzPathsCountGauge();
+
+ /**
* Assign a given role to a set of groups. As well as persist the corresponding
* permission change to MSentryPermChange table in a single transaction.
*
diff --git a/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java b/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java
index 059621a..16ff79e 100644
--- a/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java
+++ b/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java
@@ -137,6 +137,18 @@
return 0L;
}
});
+ Mockito.when(sentryStore.getAuthzObjectsCountGauge()).thenReturn(new Gauge< Long >() {
+ @Override
+ public Long getValue() {
+ return 0L;
+ }
+ });
+ Mockito.when(sentryStore.getAuthzPathsCountGauge()).thenReturn(new Gauge< Long >() {
+ @Override
+ public Long getValue() {
+ return 0L;
+ }
+ });
Mockito.doAnswer((invocation) -> {
long id = (long) invocation.getArguments()[0];