From f352f2b6372cc879c63ff535c684cbaea9e0f152 Mon Sep 17 00:00:00 2001 From: Maxim Muzafarov Date: Wed, 29 Mar 2023 06:24:34 -0500 Subject: [PATCH 1/3] Notify the corresponding JIRA issue as soon as the PR is raised Patch by Maxim Muzafarov; reviewed by brandonwilliams and smiklosovic for CASSANDRA-18372 --- .asf.yaml | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 .asf.yaml diff --git a/.asf.yaml b/.asf.yaml new file mode 100644 index 0000000000..c701eeec8c --- /dev/null +++ b/.asf.yaml @@ -0,0 +1,8 @@ +github: + enabled_merge_buttons: + squash: false + merge: false + rebase: true + +notifications: + jira_options: link worklog From 2f8d11335ee2e997c803554e3cd58274ccd462c7 Mon Sep 17 00:00:00 2001 From: Brandon Williams Date: Wed, 29 Mar 2023 06:32:05 -0500 Subject: [PATCH 2/3] Remove asf.yaml from non-trunk branches --- .asf.yaml | 8 -------- 1 file changed, 8 deletions(-) delete mode 100644 .asf.yaml diff --git a/.asf.yaml b/.asf.yaml deleted file mode 100644 index c701eeec8c..0000000000 --- a/.asf.yaml +++ /dev/null @@ -1,8 +0,0 @@ -github: - enabled_merge_buttons: - squash: false - merge: false - rebase: true - -notifications: - jira_options: link worklog From f96659c5306e62666e21c371c2ded646dd51672b Mon Sep 17 00:00:00 2001 From: Jacek Lewandowski Date: Tue, 14 Mar 2023 14:29:39 +0100 Subject: [PATCH 3/3] Save host id to system.local and flush immediately after startup patch by Adriano Bonacin and Jacek Lewandowski; reviewed by Stefan Miklosovic and Sam Tunnicliffe for CASSANDRA-18153 --- CHANGES.txt | 1 + .../apache/cassandra/db/SystemKeyspace.java | 75 ++++++++-- .../cassandra/db/commitlog/CommitLog.java | 60 +++++--- .../cassandra/service/StorageService.java | 139 +++++++++++++++--- .../tools/SSTableMetadataViewer.java | 8 +- .../cassandra/distributed/impl/Instance.java | 12 +- 6 files changed, 237 insertions(+), 58 deletions(-) diff --git a/CHANGES.txt b/CHANGES.txt index cd519fc59f..ae0ec5795b 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -1,4 +1,5 @@ 3.0.29 + * Save host id to system.local and flush immediately after startup (CASSANDRA-18153) * Fix RepairJob unnecessarily reporting cancellation error (CASSANDRA-17701) * Fix the ordering of sstables when running sstableupgrade tool (CASSANDRA-18143) * Fix default file system error handler for disk_failure_policy die (CASSANDRA-18294) diff --git a/src/java/org/apache/cassandra/db/SystemKeyspace.java b/src/java/org/apache/cassandra/db/SystemKeyspace.java index dc550dfdc7..c0bf31779b 100644 --- a/src/java/org/apache/cassandra/db/SystemKeyspace.java +++ b/src/java/org/apache/cassandra/db/SystemKeyspace.java @@ -22,47 +22,81 @@ import java.io.IOError; import java.io.IOException; import java.net.InetAddress; import java.nio.ByteBuffer; -import java.util.*; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collection; +import java.util.Collections; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; +import java.util.Map; +import java.util.Set; +import java.util.UUID; import java.util.concurrent.ExecutorService; +import java.util.concurrent.Future; import java.util.concurrent.TimeUnit; +import java.util.function.Supplier; import java.util.stream.Collectors; import java.util.stream.StreamSupport; import javax.management.openmbean.OpenDataException; import javax.management.openmbean.TabularData; -import java.util.concurrent.Future; +import com.google.common.annotations.VisibleForTesting; import com.google.common.collect.HashMultimap; import com.google.common.collect.ImmutableSet; import com.google.common.collect.SetMultimap; import com.google.common.io.ByteStreams; +import com.google.common.util.concurrent.Futures; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import com.google.common.util.concurrent.Futures; - import org.apache.cassandra.config.CFMetaData; import org.apache.cassandra.config.DatabaseDescriptor; import org.apache.cassandra.cql3.QueryProcessor; import org.apache.cassandra.cql3.UntypedResultSet; -import org.apache.cassandra.cql3.functions.*; +import org.apache.cassandra.cql3.functions.AggregateFcts; +import org.apache.cassandra.cql3.functions.BytesConversionFcts; +import org.apache.cassandra.cql3.functions.TimeFcts; +import org.apache.cassandra.cql3.functions.UuidFcts; +import org.apache.cassandra.db.commitlog.CommitLog; import org.apache.cassandra.db.commitlog.ReplayPosition; import org.apache.cassandra.db.compaction.CompactionHistoryTabularData; -import org.apache.cassandra.db.marshal.*; +import org.apache.cassandra.db.marshal.BytesType; +import org.apache.cassandra.db.marshal.TimeUUIDType; +import org.apache.cassandra.db.marshal.UTF8Type; +import org.apache.cassandra.db.marshal.UUIDType; import org.apache.cassandra.db.partitions.PartitionUpdate; -import org.apache.cassandra.dht.*; +import org.apache.cassandra.dht.IPartitioner; +import org.apache.cassandra.dht.LocalPartitioner; +import org.apache.cassandra.dht.Range; +import org.apache.cassandra.dht.Token; import org.apache.cassandra.exceptions.ConfigurationException; import org.apache.cassandra.io.sstable.Descriptor; -import org.apache.cassandra.io.util.*; +import org.apache.cassandra.io.util.DataInputBuffer; +import org.apache.cassandra.io.util.DataOutputBuffer; +import org.apache.cassandra.io.util.FileUtils; +import org.apache.cassandra.io.util.RebufferingInputStream; import org.apache.cassandra.locator.IEndpointSnitch; import org.apache.cassandra.metrics.RestorableMeter; import org.apache.cassandra.net.MessagingService; -import org.apache.cassandra.schema.*; +import org.apache.cassandra.schema.CompactionParams; +import org.apache.cassandra.schema.Functions; +import org.apache.cassandra.schema.KeyspaceMetadata; +import org.apache.cassandra.schema.KeyspaceParams; +import org.apache.cassandra.schema.SchemaKeyspace; +import org.apache.cassandra.schema.Tables; +import org.apache.cassandra.schema.Types; +import org.apache.cassandra.schema.Views; import org.apache.cassandra.service.StorageService; import org.apache.cassandra.service.paxos.Commit; import org.apache.cassandra.service.paxos.PaxosState; import org.apache.cassandra.thrift.cassandraConstants; import org.apache.cassandra.transport.Server; -import org.apache.cassandra.utils.*; +import org.apache.cassandra.utils.ByteBufferUtil; +import org.apache.cassandra.utils.CassandraVersion; +import org.apache.cassandra.utils.FBUtilities; +import org.apache.cassandra.utils.Pair; +import org.apache.cassandra.utils.UUIDGen; import static java.util.Collections.emptyMap; import static java.util.Collections.singletonMap; @@ -474,6 +508,12 @@ public final class SystemKeyspace } public static void persistLocalMetadata() + { + persistLocalMetadata(UUID::randomUUID); + } + + @VisibleForTesting + public static void persistLocalMetadata(Supplier nodeIdSupplier) { String req = "INSERT INTO system.%s (" + "key," + @@ -503,6 +543,13 @@ public final class SystemKeyspace DatabaseDescriptor.getRpcAddress(), FBUtilities.getBroadcastAddress(), FBUtilities.getLocalAddress()); + + // We should store host ID as soon as possible in the system.local table and flush that table to disk so that + // we can be sure that those changes are stored in sstable and not in the commit log (see CASSANDRA-18153). + // It is very unlikely that when upgrading the host id is not flushed to disk, but if that's the case, we limit + // this change only to the new installations or the user should just flush system.local table. + if (!CommitLog.instance.hasFilesToReplay()) + SystemKeyspace.getOrInitializeLocalHostId(nodeIdSupplier); } public static void updateCompactionHistory(String ksname, @@ -1091,13 +1138,18 @@ public final class SystemKeyspace * none exists. */ public static synchronized UUID getOrInitializeLocalHostId() + { + return getOrInitializeLocalHostId(UUID::randomUUID); + } + + private static synchronized UUID getOrInitializeLocalHostId(Supplier nodeIdSupplier) { UUID hostId = getLocalHostId(); if (hostId != null) return hostId; // ID not found, generate a new one, persist, and then return it. - hostId = UUID.randomUUID(); + hostId = nodeIdSupplier.get(); logger.warn("No host ID found, created {} (Note: This should happen exactly once per node).", hostId); return setLocalHostId(hostId); } @@ -1109,6 +1161,7 @@ public final class SystemKeyspace { String req = "INSERT INTO system.%s (key, host_id) VALUES ('%s', ?)"; executeInternal(String.format(req, LOCAL, LOCAL), hostId); + forceBlockingFlush(LOCAL); return hostId; } diff --git a/src/java/org/apache/cassandra/db/commitlog/CommitLog.java b/src/java/org/apache/cassandra/db/commitlog/CommitLog.java index ae10ffa99d..cac2d0f38f 100644 --- a/src/java/org/apache/cassandra/db/commitlog/CommitLog.java +++ b/src/java/org/apache/cassandra/db/commitlog/CommitLog.java @@ -17,35 +17,44 @@ */ package org.apache.cassandra.db.commitlog; -import java.io.*; +import java.io.File; +import java.io.FilenameFilter; +import java.io.IOException; import java.nio.ByteBuffer; -import java.util.*; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import java.util.Iterator; +import java.util.List; +import java.util.Map; +import java.util.TreeMap; +import java.util.UUID; import java.util.zip.CRC32; import com.google.common.annotations.VisibleForTesting; - +import org.apache.commons.lang3.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import org.apache.commons.lang3.StringUtils; - import org.apache.cassandra.config.Config; import org.apache.cassandra.config.DatabaseDescriptor; import org.apache.cassandra.config.ParameterizedClass; -import org.apache.cassandra.db.*; +import org.apache.cassandra.db.Mutation; import org.apache.cassandra.io.FSWriteError; -import org.apache.cassandra.schema.CompressionParams; import org.apache.cassandra.io.compress.ICompressor; import org.apache.cassandra.io.util.BufferedDataOutputStreamPlus; import org.apache.cassandra.io.util.DataOutputBufferFixed; import org.apache.cassandra.io.util.FileUtils; import org.apache.cassandra.metrics.CommitLogMetrics; import org.apache.cassandra.net.MessagingService; +import org.apache.cassandra.schema.CompressionParams; import org.apache.cassandra.service.StorageService; import org.apache.cassandra.utils.JVMStabilityInspector; import org.apache.cassandra.utils.MBeanWrapper; -import static org.apache.cassandra.db.commitlog.CommitLogSegment.*; +import static org.apache.cassandra.db.commitlog.CommitLogSegment.Allocation; +import static org.apache.cassandra.db.commitlog.CommitLogSegment.CommitLogSegmentFileComparator; +import static org.apache.cassandra.db.commitlog.CommitLogSegment.ENTRY_OVERHEAD_SIZE; import static org.apache.cassandra.utils.FBUtilities.updateChecksum; import static org.apache.cassandra.utils.FBUtilities.updateChecksumInt; @@ -59,6 +68,11 @@ public class CommitLog implements CommitLogMBean public static final CommitLog instance = CommitLog.construct(); + // we used to try to avoid instantiating commitlog (thus creating an empty segment ready for writes) + // until after recover was finished. this turns out to be fragile; it is less error-prone to go + // ahead and allow writes before recover(), and just skip active segments when we do. + private static final FilenameFilter unmanagedFilesFilter = (dir, name) -> CommitLogDescriptor.isValid(name) && CommitLogSegment.shouldReplay(name); + // we only permit records HALF the size of a commit log, to ensure we don't spin allocating many mostly // empty segments when writing large records private final long MAX_MUTATION_SIZE = DatabaseDescriptor.getMaxMutationSize(); @@ -106,6 +120,19 @@ public class CommitLog implements CommitLogMBean return this; } + public boolean hasFilesToReplay() + { + return getUnmanagedFiles().length > 0; + } + + private File[] getUnmanagedFiles() + { + File[] files = new File(DatabaseDescriptor.getCommitLogLocation()).listFiles(unmanagedFilesFilter); + if (files == null) + return new File[0]; + return files; + } + /** * Perform recovery on commit logs located in the directory specified by the config file. * @@ -117,19 +144,8 @@ public class CommitLog implements CommitLogMBean if (allocator.createReserveSegments) return 0; - FilenameFilter unmanagedFilesFilter = new FilenameFilter() - { - public boolean accept(File dir, String name) - { - // we used to try to avoid instantiating commitlog (thus creating an empty segment ready for writes) - // until after recover was finished. this turns out to be fragile; it is less error-prone to go - // ahead and allow writes before recover(), and just skip active segments when we do. - return CommitLogDescriptor.isValid(name) && CommitLogSegment.shouldReplay(name); - } - }; - // submit all existing files in the commit log dir for archiving prior to recovery - CASSANDRA-6904 - for (File file : new File(DatabaseDescriptor.getCommitLogLocation()).listFiles(unmanagedFilesFilter)) + for (File file : getUnmanagedFiles()) { archiver.maybeArchive(file.getPath(), file.getName()); archiver.maybeWaitForArchiving(file.getName()); @@ -138,7 +154,7 @@ public class CommitLog implements CommitLogMBean assert archiver.archivePending.isEmpty() : "Not all commit log archive tasks were completed before restore"; archiver.maybeRestoreArchive(); - File[] files = new File(DatabaseDescriptor.getCommitLogLocation()).listFiles(unmanagedFilesFilter); + File[] files = getUnmanagedFiles(); int replayed = 0; allocator.enableReserveSegmentCreation(); if (files.length == 0) @@ -174,7 +190,7 @@ public class CommitLog implements CommitLogMBean private static UUID getLocalHostId() { - return Optional.ofNullable(StorageService.instance.getLocalHostUUID()).orElseGet(SystemKeyspace::getLocalHostId); + return StorageService.instance.getLocalHostUUID(); } /** diff --git a/src/java/org/apache/cassandra/service/StorageService.java b/src/java/org/apache/cassandra/service/StorageService.java index 180a4ef6d0..90c1fde3af 100644 --- a/src/java/org/apache/cassandra/service/StorageService.java +++ b/src/java/org/apache/cassandra/service/StorageService.java @@ -17,27 +17,69 @@ */ package org.apache.cassandra.service; -import java.io.*; +import java.io.ByteArrayInputStream; +import java.io.DataInputStream; +import java.io.File; +import java.io.IOError; +import java.io.IOException; import java.lang.management.ManagementFactory; import java.net.InetAddress; import java.net.UnknownHostException; import java.nio.ByteBuffer; -import java.util.*; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collection; +import java.util.Collections; +import java.util.EnumMap; +import java.util.HashMap; +import java.util.HashSet; +import java.util.Iterator; +import java.util.LinkedHashMap; +import java.util.LinkedList; +import java.util.List; +import java.util.Map; import java.util.Map.Entry; -import java.util.concurrent.*; +import java.util.Optional; +import java.util.Set; +import java.util.SortedMap; +import java.util.TreeMap; +import java.util.TreeSet; +import java.util.UUID; +import java.util.concurrent.CopyOnWriteArrayList; +import java.util.concurrent.ExecutionException; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; +import java.util.concurrent.FutureTask; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.TimeoutException; import java.util.concurrent.atomic.AtomicBoolean; import java.util.concurrent.atomic.AtomicInteger; import java.util.stream.Collectors; import javax.annotation.Nullable; -import javax.management.*; +import javax.management.JMX; +import javax.management.NotificationBroadcasterSupport; +import javax.management.ObjectName; import javax.management.openmbean.TabularData; import javax.management.openmbean.TabularDataSupport; import com.google.common.annotations.VisibleForTesting; import com.google.common.base.Preconditions; import com.google.common.base.Predicate; -import com.google.common.collect.*; -import com.google.common.util.concurrent.*; +import com.google.common.collect.ArrayListMultimap; +import com.google.common.collect.Collections2; +import com.google.common.collect.HashMultimap; +import com.google.common.collect.ImmutableSet; +import com.google.common.collect.Iterables; +import com.google.common.collect.Lists; +import com.google.common.collect.Maps; +import com.google.common.collect.Multimap; +import com.google.common.collect.SetMultimap; +import com.google.common.collect.Sets; +import com.google.common.util.concurrent.FutureCallback; +import com.google.common.util.concurrent.Futures; +import com.google.common.util.concurrent.ListenableFuture; +import com.google.common.util.concurrent.Uninterruptibles; import org.apache.commons.lang3.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -61,36 +103,90 @@ import org.apache.cassandra.config.Config; import org.apache.cassandra.config.DatabaseDescriptor; import org.apache.cassandra.config.Schema; import org.apache.cassandra.config.ViewDefinition; -import org.apache.cassandra.db.*; +import org.apache.cassandra.db.ColumnFamilyStore; +import org.apache.cassandra.db.CounterMutationVerbHandler; +import org.apache.cassandra.db.DecoratedKey; +import org.apache.cassandra.db.DefinitionsUpdateVerbHandler; +import org.apache.cassandra.db.Keyspace; +import org.apache.cassandra.db.MigrationRequestVerbHandler; +import org.apache.cassandra.db.Mutation; +import org.apache.cassandra.db.MutationVerbHandler; +import org.apache.cassandra.db.RangeSliceVerbHandler; +import org.apache.cassandra.db.ReadCommandVerbHandler; +import org.apache.cassandra.db.ReadRepairVerbHandler; +import org.apache.cassandra.db.SchemaCheckVerbHandler; +import org.apache.cassandra.db.SizeEstimatesRecorder; +import org.apache.cassandra.db.SnapshotDetailsTabularData; +import org.apache.cassandra.db.SystemKeyspace; +import org.apache.cassandra.db.TruncateVerbHandler; import org.apache.cassandra.db.commitlog.CommitLog; import org.apache.cassandra.db.compaction.CompactionManager; import org.apache.cassandra.db.lifecycle.LifecycleTransaction; -import org.apache.cassandra.dht.*; +import org.apache.cassandra.dht.BootStrapper; +import org.apache.cassandra.dht.IPartitioner; import org.apache.cassandra.dht.Range; +import org.apache.cassandra.dht.RangeStreamer; +import org.apache.cassandra.dht.RingPosition; +import org.apache.cassandra.dht.StreamStateStore; +import org.apache.cassandra.dht.Token; import org.apache.cassandra.dht.Token.TokenFactory; -import org.apache.cassandra.exceptions.*; -import org.apache.cassandra.gms.*; +import org.apache.cassandra.exceptions.ConfigurationException; +import org.apache.cassandra.exceptions.InvalidRequestException; +import org.apache.cassandra.exceptions.UnavailableException; +import org.apache.cassandra.gms.ApplicationState; +import org.apache.cassandra.gms.EndpointState; +import org.apache.cassandra.gms.FailureDetector; +import org.apache.cassandra.gms.GossipDigestAck2VerbHandler; +import org.apache.cassandra.gms.GossipDigestAckVerbHandler; +import org.apache.cassandra.gms.GossipDigestSynVerbHandler; +import org.apache.cassandra.gms.GossipShutdownVerbHandler; +import org.apache.cassandra.gms.Gossiper; +import org.apache.cassandra.gms.IEndpointStateChangeSubscriber; +import org.apache.cassandra.gms.IFailureDetector; +import org.apache.cassandra.gms.TokenSerializer; +import org.apache.cassandra.gms.VersionedValue; import org.apache.cassandra.hints.HintVerbHandler; import org.apache.cassandra.hints.HintsService; import org.apache.cassandra.io.sstable.SSTableLoader; import org.apache.cassandra.io.sstable.format.VersionAndType; import org.apache.cassandra.io.util.FileUtils; -import org.apache.cassandra.locator.*; +import org.apache.cassandra.locator.AbstractReplicationStrategy; +import org.apache.cassandra.locator.DynamicEndpointSnitch; +import org.apache.cassandra.locator.IEndpointSnitch; +import org.apache.cassandra.locator.LocalStrategy; +import org.apache.cassandra.locator.TokenMetadata; import org.apache.cassandra.metrics.StorageMetrics; -import org.apache.cassandra.net.*; -import org.apache.cassandra.repair.*; +import org.apache.cassandra.net.AsyncOneResponse; +import org.apache.cassandra.net.MessageOut; +import org.apache.cassandra.net.MessagingService; +import org.apache.cassandra.net.ResponseVerbHandler; +import org.apache.cassandra.repair.RepairMessageVerbHandler; +import org.apache.cassandra.repair.RepairParallelism; +import org.apache.cassandra.repair.RepairRunnable; +import org.apache.cassandra.repair.SystemDistributedKeyspace; import org.apache.cassandra.repair.messages.RepairOption; import org.apache.cassandra.schema.KeyspaceMetadata; import org.apache.cassandra.schema.SchemaKeyspace; import org.apache.cassandra.service.paxos.CommitVerbHandler; import org.apache.cassandra.service.paxos.PrepareVerbHandler; import org.apache.cassandra.service.paxos.ProposeVerbHandler; -import org.apache.cassandra.streaming.*; +import org.apache.cassandra.streaming.ReplicationFinishedVerbHandler; +import org.apache.cassandra.streaming.StreamManager; +import org.apache.cassandra.streaming.StreamPlan; +import org.apache.cassandra.streaming.StreamResultFuture; +import org.apache.cassandra.streaming.StreamState; import org.apache.cassandra.thrift.EndpointDetails; import org.apache.cassandra.thrift.TokenRange; import org.apache.cassandra.thrift.cassandraConstants; import org.apache.cassandra.tracing.TraceKeyspace; -import org.apache.cassandra.utils.*; +import org.apache.cassandra.utils.BackgroundActivityMonitor; +import org.apache.cassandra.utils.FBUtilities; +import org.apache.cassandra.utils.JVMStabilityInspector; +import org.apache.cassandra.utils.MBeanWrapper; +import org.apache.cassandra.utils.OutputHandler; +import org.apache.cassandra.utils.Pair; +import org.apache.cassandra.utils.WindowsTimer; +import org.apache.cassandra.utils.WrappedRunnable; import org.apache.cassandra.utils.progress.ProgressEvent; import org.apache.cassandra.utils.progress.ProgressEventType; import org.apache.cassandra.utils.progress.jmx.JMXProgressSupport; @@ -1756,12 +1852,21 @@ public class StorageService extends NotificationBroadcasterSupport implements IE public String getLocalHostId() { - return getTokenMetadata().getHostId(FBUtilities.getBroadcastAddress()).toString(); + UUID id = getLocalHostUUID(); + return id != null ? id.toString() : null; } public UUID getLocalHostUUID() { - return getTokenMetadata().getHostId(FBUtilities.getBroadcastAddress()); + UUID id = getTokenMetadata().getHostId(FBUtilities.getBroadcastAddress()); + if (id != null) + return id; + // this condition is to prevent accessing the tables when the node is not started yet, and in particular, + // when it is not going to be started at all (e.g. when running some unit tests or client tools). + else if (DatabaseDescriptor.isDaemonInitialized()) + return SystemKeyspace.getLocalHostId(); + + return null; } public Map getHostIdMap() diff --git a/src/java/org/apache/cassandra/tools/SSTableMetadataViewer.java b/src/java/org/apache/cassandra/tools/SSTableMetadataViewer.java index 19af957228..f1000853ce 100644 --- a/src/java/org/apache/cassandra/tools/SSTableMetadataViewer.java +++ b/src/java/org/apache/cassandra/tools/SSTableMetadataViewer.java @@ -27,13 +27,16 @@ import org.apache.commons.cli.CommandLine; import org.apache.commons.cli.CommandLineParser; import org.apache.commons.cli.HelpFormatter; import org.apache.commons.cli.Option; -import org.apache.commons.cli.OptionBuilder; import org.apache.commons.cli.Options; import org.apache.commons.cli.ParseException; import org.apache.commons.cli.PosixParser; import org.apache.cassandra.io.sstable.Descriptor; -import org.apache.cassandra.io.sstable.metadata.*; +import org.apache.cassandra.io.sstable.metadata.CompactionMetadata; +import org.apache.cassandra.io.sstable.metadata.MetadataComponent; +import org.apache.cassandra.io.sstable.metadata.MetadataType; +import org.apache.cassandra.io.sstable.metadata.StatsMetadata; +import org.apache.cassandra.io.sstable.metadata.ValidationMetadata; /** * Shows the contents of sstable metadata @@ -96,6 +99,7 @@ public class SSTableMetadataViewer out.printf("Estimated droppable tombstones: %s%n", stats.getEstimatedDroppableTombstoneRatio((int) (System.currentTimeMillis() / 1000) - gcgs)); out.printf("SSTable Level: %d%n", stats.sstableLevel); out.printf("Repaired at: %d%n", stats.repairedAt); + out.printf("Originating host id: %s%n", stats.originatingHostId); out.printf("Replay positions covered: %s\n", stats.commitLogIntervals); out.println("Estimated tombstone drop times:"); for (Map.Entry entry : stats.estimatedTombstoneDropTime.getAsMap().entrySet()) diff --git a/test/distributed/org/apache/cassandra/distributed/impl/Instance.java b/test/distributed/org/apache/cassandra/distributed/impl/Instance.java index 776def3b3d..4655ed4e09 100644 --- a/test/distributed/org/apache/cassandra/distributed/impl/Instance.java +++ b/test/distributed/org/apache/cassandra/distributed/impl/Instance.java @@ -18,12 +18,12 @@ package org.apache.cassandra.distributed.impl; -import java.io.File; -import java.io.IOException; -import java.net.InetAddress; import java.io.ByteArrayOutputStream; import java.io.Closeable; +import java.io.File; +import java.io.IOException; import java.io.PrintStream; +import java.net.InetAddress; import java.net.InetSocketAddress; import java.nio.ByteBuffer; import java.util.ArrayList; @@ -77,8 +77,8 @@ import org.apache.cassandra.distributed.api.NodeToolResult; import org.apache.cassandra.distributed.api.SimpleQueryResult; import org.apache.cassandra.distributed.mock.nodetool.InternalNodeProbe; import org.apache.cassandra.distributed.mock.nodetool.InternalNodeProbeFactory; -import org.apache.cassandra.distributed.shared.NetworkTopology; import org.apache.cassandra.distributed.shared.Metrics; +import org.apache.cassandra.distributed.shared.NetworkTopology; import org.apache.cassandra.gms.ApplicationState; import org.apache.cassandra.gms.Gossiper; import org.apache.cassandra.gms.VersionedValue; @@ -106,8 +106,8 @@ import org.apache.cassandra.service.QueryState; import org.apache.cassandra.service.StorageService; import org.apache.cassandra.service.StorageServiceMBean; import org.apache.cassandra.streaming.StreamCoordinator; -import org.apache.cassandra.tools.Output; import org.apache.cassandra.tools.NodeTool; +import org.apache.cassandra.tools.Output; import org.apache.cassandra.tracing.TraceState; import org.apache.cassandra.tracing.Tracing; import org.apache.cassandra.transport.messages.ResultMessage; @@ -569,7 +569,7 @@ public class Instance extends IsolatedExecutor implements IInvokableInstance // We need to persist this as soon as possible after startup checks. // This should be the first write to SystemKeyspace (CASSANDRA-11742) - SystemKeyspace.persistLocalMetadata(); + SystemKeyspace.persistLocalMetadata(config::hostId); LegacySchemaMigrator.migrate(); MessagingService.instance().verbSerializers.put(MessagingService.Verb.HINT,