Search in sources :

Example 6 with AttributeUpdateCollection

use of io.pravega.segmentstore.contracts.AttributeUpdateCollection in project pravega by pravega.

the class StreamSegmentContainer method getAndCacheAttributes.

/**
 * Gets the values of the given (Core and Extended) Attribute Ids for the given segment.
 *
 * @param segmentMetadata The SegmentMetadata for the Segment to retrieve attribute values for.
 * @param attributeIds    A Collection of AttributeIds to retrieve.
 * @param cache           If true, any Extended Attribute value that is not present in the SegmentMetadata cache will
 *                        be added to that (using a conditional updateAttributes() call) before completing.
 * @param timer           Timer for the operation.
 * @return A CompletableFuture that, when completed normally, will contain the desired result. If the operation failed,
 * it will be completed with the appropriate exception. If cache==true and the conditional call to updateAttributes()
 * could not be completed because of a conflicting update, it will be failed with BadAttributeUpdateException, in which
 * case a retry is warranted.
 */
private CompletableFuture<Map<AttributeId, Long>> getAndCacheAttributes(SegmentMetadata segmentMetadata, Collection<AttributeId> attributeIds, boolean cache, TimeoutTimer timer) {
    // Collect Core Attributes and Cached Extended Attributes.
    Map<AttributeId, Long> result = new HashMap<>();
    Map<AttributeId, Long> metadataAttributes = segmentMetadata.getAttributes();
    ArrayList<AttributeId> extendedAttributeIds = new ArrayList<>();
    attributeIds.forEach(attributeId -> {
        Long v = metadataAttributes.get(attributeId);
        if (v != null) {
            // This attribute is cached in the Segment Metadata, even if it has a value equal to Attributes.NULL_ATTRIBUTE_VALUE.
            result.put(attributeId, v);
        } else if (!Attributes.isCoreAttribute(attributeId)) {
            extendedAttributeIds.add(attributeId);
        }
    });
    if (extendedAttributeIds.isEmpty()) {
        // Nothing to lookup in the Attribute Index, so bail out early.
        return CompletableFuture.completedFuture(result);
    }
    // Collect remaining Extended Attributes.
    CompletableFuture<Map<AttributeId, Long>> r = this.attributeIndex.forSegment(segmentMetadata.getId(), timer.getRemaining()).thenComposeAsync(idx -> idx.get(extendedAttributeIds, timer.getRemaining()), this.executor).thenApplyAsync(extendedAttributes -> {
        if (extendedAttributeIds.size() == extendedAttributes.size()) {
            // We found a value for each Attribute Id. Nothing more to do.
            return extendedAttributes;
        }
        // Insert a NULL_ATTRIBUTE_VALUE for each missing value.
        Map<AttributeId, Long> allValues = new HashMap<>(extendedAttributes);
        extendedAttributeIds.stream().filter(id -> !extendedAttributes.containsKey(id)).forEach(id -> allValues.put(id, Attributes.NULL_ATTRIBUTE_VALUE));
        return allValues;
    }, this.executor);
    if (cache && !segmentMetadata.isSealed()) {
        // Add them to the cache if requested.
        r = r.thenComposeAsync(extendedAttributes -> {
            // Update the in-memory Segment Metadata using a special update (AttributeUpdateType.None, which should
            // complete if the attribute is not currently set). If it has some value, then a concurrent update
            // must have changed it and we cannot update anymore.
            val updates = new AttributeUpdateCollection();
            for (val e : extendedAttributes.entrySet()) {
                updates.add(new AttributeUpdate(e.getKey(), AttributeUpdateType.None, e.getValue()));
            }
            // invoke this one again.
            return addOperation(new UpdateAttributesOperation(segmentMetadata.getId(), updates), timer.getRemaining()).thenApply(v -> extendedAttributes);
        }, this.executor);
    }
    // Compile the final result.
    return r.thenApply(extendedAttributes -> {
        result.putAll(extendedAttributes);
        return result;
    });
}
Also used : ATTRIBUTE_SLTS_LATEST_SNAPSHOT_ID(io.pravega.segmentstore.contracts.Attributes.ATTRIBUTE_SLTS_LATEST_SNAPSHOT_ID) Storage(io.pravega.segmentstore.storage.Storage) StreamSegmentNotExistsException(io.pravega.segmentstore.contracts.StreamSegmentNotExistsException) ContainerEventProcessor(io.pravega.segmentstore.server.ContainerEventProcessor) OperationPriority(io.pravega.segmentstore.server.logs.operations.OperationPriority) SneakyThrows(lombok.SneakyThrows) Retry(io.pravega.common.util.Retry) MergeSegmentOperation(io.pravega.segmentstore.server.logs.operations.MergeSegmentOperation) RequiredArgsConstructor(lombok.RequiredArgsConstructor) ContainerMetadata(io.pravega.segmentstore.server.ContainerMetadata) SnapshotInfoStore(io.pravega.segmentstore.storage.chunklayer.SnapshotInfoStore) UpdateableSegmentMetadata(io.pravega.segmentstore.server.UpdateableSegmentMetadata) SegmentProperties(io.pravega.segmentstore.contracts.SegmentProperties) ReadIndexFactory(io.pravega.segmentstore.server.ReadIndexFactory) AttributeUpdate(io.pravega.segmentstore.contracts.AttributeUpdate) StreamSegmentSealedException(io.pravega.segmentstore.contracts.StreamSegmentSealedException) AttributeIndexFactory(io.pravega.segmentstore.server.attributes.AttributeIndexFactory) BufferView(io.pravega.common.util.BufferView) Duration(java.time.Duration) Map(java.util.Map) AbstractService(com.google.common.util.concurrent.AbstractService) Operation(io.pravega.segmentstore.server.logs.operations.Operation) StreamSegmentTruncateOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentTruncateOperation) RetryAndThrowConditionally(io.pravega.common.util.Retry.RetryAndThrowConditionally) Services(io.pravega.common.concurrent.Services) ContainerOfflineException(io.pravega.segmentstore.server.ContainerOfflineException) Attributes(io.pravega.segmentstore.contracts.Attributes) SegmentStoreMetrics(io.pravega.segmentstore.server.SegmentStoreMetrics) Collection(java.util.Collection) CompletionException(java.util.concurrent.CompletionException) Writer(io.pravega.segmentstore.server.Writer) Collectors(java.util.stream.Collectors) SimpleStorageFactory(io.pravega.segmentstore.storage.SimpleStorageFactory) Objects(java.util.Objects) List(java.util.List) Slf4j(lombok.extern.slf4j.Slf4j) SegmentContainerFactory(io.pravega.segmentstore.server.SegmentContainerFactory) ContainerTableExtension(io.pravega.segmentstore.server.tables.ContainerTableExtension) ATTRIBUTE_SLTS_LATEST_SNAPSHOT_EPOCH(io.pravega.segmentstore.contracts.Attributes.ATTRIBUTE_SLTS_LATEST_SNAPSHOT_EPOCH) WriterSegmentProcessor(io.pravega.segmentstore.server.WriterSegmentProcessor) Futures(io.pravega.common.concurrent.Futures) ReadResult(io.pravega.segmentstore.contracts.ReadResult) Getter(lombok.Getter) IllegalContainerStateException(io.pravega.segmentstore.server.IllegalContainerStateException) ExtendedChunkInfo(io.pravega.segmentstore.contracts.ExtendedChunkInfo) Exceptions(io.pravega.common.Exceptions) StorageFactory(io.pravega.segmentstore.storage.StorageFactory) AtomicBoolean(java.util.concurrent.atomic.AtomicBoolean) HashMap(java.util.HashMap) CompletableFuture(java.util.concurrent.CompletableFuture) PriorityCalculator(io.pravega.segmentstore.server.logs.PriorityCalculator) BadAttributeUpdateException(io.pravega.segmentstore.contracts.BadAttributeUpdateException) Supplier(java.util.function.Supplier) ArrayList(java.util.ArrayList) SegmentMetadata(io.pravega.segmentstore.server.SegmentMetadata) SegmentType(io.pravega.segmentstore.contracts.SegmentType) ImmutableList(com.google.common.collect.ImmutableList) AttributeUpdaterOperation(io.pravega.segmentstore.server.logs.operations.AttributeUpdaterOperation) ScheduledExecutorService(java.util.concurrent.ScheduledExecutorService) TableBasedMetadataStore(io.pravega.segmentstore.storage.metadata.TableBasedMetadataStore) AttributeIterator(io.pravega.segmentstore.server.AttributeIterator) StreamSegmentMapOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentMapOperation) Nullable(javax.annotation.Nullable) ChunkedSegmentStorage(io.pravega.segmentstore.storage.chunklayer.ChunkedSegmentStorage) LoggerHelpers(io.pravega.common.LoggerHelpers) SegmentContainerExtension(io.pravega.segmentstore.server.SegmentContainerExtension) WriterFactory(io.pravega.segmentstore.server.WriterFactory) NameUtils(io.pravega.shared.NameUtils) AttributeIndex(io.pravega.segmentstore.server.AttributeIndex) TimeoutTimer(io.pravega.common.TimeoutTimer) UpdateAttributesOperation(io.pravega.segmentstore.server.logs.operations.UpdateAttributesOperation) AttributeId(io.pravega.segmentstore.contracts.AttributeId) lombok.val(lombok.val) OperationLog(io.pravega.segmentstore.server.OperationLog) MergeStreamSegmentResult(io.pravega.segmentstore.contracts.MergeStreamSegmentResult) StreamSegmentMergedException(io.pravega.segmentstore.contracts.StreamSegmentMergedException) UtilsWrapper(io.pravega.segmentstore.storage.chunklayer.UtilsWrapper) Service(com.google.common.util.concurrent.Service) SnapshotInfo(io.pravega.segmentstore.storage.chunklayer.SnapshotInfo) Consumer(java.util.function.Consumer) DirectSegmentAccess(io.pravega.segmentstore.server.DirectSegmentAccess) ContainerAttributeIndex(io.pravega.segmentstore.server.attributes.ContainerAttributeIndex) AttributeUpdateCollection(io.pravega.segmentstore.contracts.AttributeUpdateCollection) SegmentOperation(io.pravega.segmentstore.server.SegmentOperation) StreamSegmentAppendOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentAppendOperation) OperationLogFactory(io.pravega.segmentstore.server.OperationLogFactory) SegmentContainer(io.pravega.segmentstore.server.SegmentContainer) Preconditions(com.google.common.base.Preconditions) AttributeUpdateType(io.pravega.segmentstore.contracts.AttributeUpdateType) ReadIndex(io.pravega.segmentstore.server.ReadIndex) Collections(java.util.Collections) DeleteSegmentOperation(io.pravega.segmentstore.server.logs.operations.DeleteSegmentOperation) StreamSegmentSealOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentSealOperation) lombok.val(lombok.val) AttributeUpdateCollection(io.pravega.segmentstore.contracts.AttributeUpdateCollection) AttributeUpdate(io.pravega.segmentstore.contracts.AttributeUpdate) UpdateAttributesOperation(io.pravega.segmentstore.server.logs.operations.UpdateAttributesOperation) HashMap(java.util.HashMap) AttributeId(io.pravega.segmentstore.contracts.AttributeId) ArrayList(java.util.ArrayList) Map(java.util.Map) HashMap(java.util.HashMap)

Example 7 with AttributeUpdateCollection

use of io.pravega.segmentstore.contracts.AttributeUpdateCollection in project pravega by pravega.

the class StreamSegmentContainer method mergeStreamSegment.

private CompletableFuture<MergeStreamSegmentResult> mergeStreamSegment(long targetSegmentId, long sourceSegmentId, AttributeUpdateCollection attributeUpdates, TimeoutTimer timer) {
    // Get a reference to the source segment's metadata now, before the merge. It may not be accessible afterwards.
    SegmentMetadata sourceMetadata = this.metadata.getStreamSegmentMetadata(sourceSegmentId);
    CompletableFuture<Void> sealResult = trySealStreamSegment(sourceMetadata, timer.getRemaining());
    if (sourceMetadata.getLength() == 0) {
        // writes in the pipeline. As such, we cannot pipeline the two operations, and must wait for the seal to finish first.
        return sealResult.thenComposeAsync(v -> {
            // to and including the seal, so if there were any writes outstanding before, they should now be reflected in it.
            if (sourceMetadata.getLength() == 0) {
                // Source is still empty after sealing - OK to delete.
                log.debug("{}: Updating attributes (if any) and deleting empty source segment instead of merging {}.", this.traceObjectId, sourceMetadata.getName());
                // Execute the attribute update on the target segment only if needed.
                Supplier<CompletableFuture<Void>> updateAttributesIfNeeded = () -> attributeUpdates == null ? CompletableFuture.completedFuture(null) : updateAttributesForSegment(targetSegmentId, attributeUpdates, timer.getRemaining());
                return updateAttributesIfNeeded.get().thenCompose(v2 -> deleteStreamSegment(sourceMetadata.getName(), timer.getRemaining()).thenApply(v3 -> new MergeStreamSegmentResult(this.metadata.getStreamSegmentMetadata(targetSegmentId).getLength(), sourceMetadata.getLength(), sourceMetadata.getAttributes())));
            } else {
                // Source now has some data - we must merge the two.
                MergeSegmentOperation operation = new MergeSegmentOperation(targetSegmentId, sourceSegmentId, attributeUpdates);
                return processAttributeUpdaterOperation(operation, timer).thenApply(v2 -> new MergeStreamSegmentResult(operation.getStreamSegmentOffset() + operation.getLength(), operation.getLength(), sourceMetadata.getAttributes()));
            }
        }, this.executor);
    } else {
        // Source is not empty, so we cannot delete. Make use of the DurableLog's pipelining abilities by queueing up
        // the Merge right after the Seal.
        MergeSegmentOperation operation = new MergeSegmentOperation(targetSegmentId, sourceSegmentId, attributeUpdates);
        return CompletableFuture.allOf(sealResult, processAttributeUpdaterOperation(operation, timer)).thenApply(v2 -> new MergeStreamSegmentResult(operation.getStreamSegmentOffset() + operation.getLength(), operation.getLength(), sourceMetadata.getAttributes()));
    }
}
Also used : UpdateableSegmentMetadata(io.pravega.segmentstore.server.UpdateableSegmentMetadata) SegmentMetadata(io.pravega.segmentstore.server.SegmentMetadata) ATTRIBUTE_SLTS_LATEST_SNAPSHOT_ID(io.pravega.segmentstore.contracts.Attributes.ATTRIBUTE_SLTS_LATEST_SNAPSHOT_ID) Storage(io.pravega.segmentstore.storage.Storage) StreamSegmentNotExistsException(io.pravega.segmentstore.contracts.StreamSegmentNotExistsException) ContainerEventProcessor(io.pravega.segmentstore.server.ContainerEventProcessor) OperationPriority(io.pravega.segmentstore.server.logs.operations.OperationPriority) SneakyThrows(lombok.SneakyThrows) Retry(io.pravega.common.util.Retry) MergeSegmentOperation(io.pravega.segmentstore.server.logs.operations.MergeSegmentOperation) RequiredArgsConstructor(lombok.RequiredArgsConstructor) ContainerMetadata(io.pravega.segmentstore.server.ContainerMetadata) SnapshotInfoStore(io.pravega.segmentstore.storage.chunklayer.SnapshotInfoStore) UpdateableSegmentMetadata(io.pravega.segmentstore.server.UpdateableSegmentMetadata) SegmentProperties(io.pravega.segmentstore.contracts.SegmentProperties) ReadIndexFactory(io.pravega.segmentstore.server.ReadIndexFactory) AttributeUpdate(io.pravega.segmentstore.contracts.AttributeUpdate) StreamSegmentSealedException(io.pravega.segmentstore.contracts.StreamSegmentSealedException) AttributeIndexFactory(io.pravega.segmentstore.server.attributes.AttributeIndexFactory) BufferView(io.pravega.common.util.BufferView) Duration(java.time.Duration) Map(java.util.Map) AbstractService(com.google.common.util.concurrent.AbstractService) Operation(io.pravega.segmentstore.server.logs.operations.Operation) StreamSegmentTruncateOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentTruncateOperation) RetryAndThrowConditionally(io.pravega.common.util.Retry.RetryAndThrowConditionally) Services(io.pravega.common.concurrent.Services) ContainerOfflineException(io.pravega.segmentstore.server.ContainerOfflineException) Attributes(io.pravega.segmentstore.contracts.Attributes) SegmentStoreMetrics(io.pravega.segmentstore.server.SegmentStoreMetrics) Collection(java.util.Collection) CompletionException(java.util.concurrent.CompletionException) Writer(io.pravega.segmentstore.server.Writer) Collectors(java.util.stream.Collectors) SimpleStorageFactory(io.pravega.segmentstore.storage.SimpleStorageFactory) Objects(java.util.Objects) List(java.util.List) Slf4j(lombok.extern.slf4j.Slf4j) SegmentContainerFactory(io.pravega.segmentstore.server.SegmentContainerFactory) ContainerTableExtension(io.pravega.segmentstore.server.tables.ContainerTableExtension) ATTRIBUTE_SLTS_LATEST_SNAPSHOT_EPOCH(io.pravega.segmentstore.contracts.Attributes.ATTRIBUTE_SLTS_LATEST_SNAPSHOT_EPOCH) WriterSegmentProcessor(io.pravega.segmentstore.server.WriterSegmentProcessor) Futures(io.pravega.common.concurrent.Futures) ReadResult(io.pravega.segmentstore.contracts.ReadResult) Getter(lombok.Getter) IllegalContainerStateException(io.pravega.segmentstore.server.IllegalContainerStateException) ExtendedChunkInfo(io.pravega.segmentstore.contracts.ExtendedChunkInfo) Exceptions(io.pravega.common.Exceptions) StorageFactory(io.pravega.segmentstore.storage.StorageFactory) AtomicBoolean(java.util.concurrent.atomic.AtomicBoolean) HashMap(java.util.HashMap) CompletableFuture(java.util.concurrent.CompletableFuture) PriorityCalculator(io.pravega.segmentstore.server.logs.PriorityCalculator) BadAttributeUpdateException(io.pravega.segmentstore.contracts.BadAttributeUpdateException) Supplier(java.util.function.Supplier) ArrayList(java.util.ArrayList) SegmentMetadata(io.pravega.segmentstore.server.SegmentMetadata) SegmentType(io.pravega.segmentstore.contracts.SegmentType) ImmutableList(com.google.common.collect.ImmutableList) AttributeUpdaterOperation(io.pravega.segmentstore.server.logs.operations.AttributeUpdaterOperation) ScheduledExecutorService(java.util.concurrent.ScheduledExecutorService) TableBasedMetadataStore(io.pravega.segmentstore.storage.metadata.TableBasedMetadataStore) AttributeIterator(io.pravega.segmentstore.server.AttributeIterator) StreamSegmentMapOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentMapOperation) Nullable(javax.annotation.Nullable) ChunkedSegmentStorage(io.pravega.segmentstore.storage.chunklayer.ChunkedSegmentStorage) LoggerHelpers(io.pravega.common.LoggerHelpers) SegmentContainerExtension(io.pravega.segmentstore.server.SegmentContainerExtension) WriterFactory(io.pravega.segmentstore.server.WriterFactory) NameUtils(io.pravega.shared.NameUtils) AttributeIndex(io.pravega.segmentstore.server.AttributeIndex) TimeoutTimer(io.pravega.common.TimeoutTimer) UpdateAttributesOperation(io.pravega.segmentstore.server.logs.operations.UpdateAttributesOperation) AttributeId(io.pravega.segmentstore.contracts.AttributeId) lombok.val(lombok.val) OperationLog(io.pravega.segmentstore.server.OperationLog) MergeStreamSegmentResult(io.pravega.segmentstore.contracts.MergeStreamSegmentResult) StreamSegmentMergedException(io.pravega.segmentstore.contracts.StreamSegmentMergedException) UtilsWrapper(io.pravega.segmentstore.storage.chunklayer.UtilsWrapper) Service(com.google.common.util.concurrent.Service) SnapshotInfo(io.pravega.segmentstore.storage.chunklayer.SnapshotInfo) Consumer(java.util.function.Consumer) DirectSegmentAccess(io.pravega.segmentstore.server.DirectSegmentAccess) ContainerAttributeIndex(io.pravega.segmentstore.server.attributes.ContainerAttributeIndex) AttributeUpdateCollection(io.pravega.segmentstore.contracts.AttributeUpdateCollection) SegmentOperation(io.pravega.segmentstore.server.SegmentOperation) StreamSegmentAppendOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentAppendOperation) OperationLogFactory(io.pravega.segmentstore.server.OperationLogFactory) SegmentContainer(io.pravega.segmentstore.server.SegmentContainer) Preconditions(com.google.common.base.Preconditions) AttributeUpdateType(io.pravega.segmentstore.contracts.AttributeUpdateType) ReadIndex(io.pravega.segmentstore.server.ReadIndex) Collections(java.util.Collections) DeleteSegmentOperation(io.pravega.segmentstore.server.logs.operations.DeleteSegmentOperation) StreamSegmentSealOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentSealOperation) CompletableFuture(java.util.concurrent.CompletableFuture) MergeSegmentOperation(io.pravega.segmentstore.server.logs.operations.MergeSegmentOperation) MergeStreamSegmentResult(io.pravega.segmentstore.contracts.MergeStreamSegmentResult)

Example 8 with AttributeUpdateCollection

use of io.pravega.segmentstore.contracts.AttributeUpdateCollection in project pravega by pravega.

the class StreamSegmentContainer method mergeStreamSegment.

@Override
public CompletableFuture<MergeStreamSegmentResult> mergeStreamSegment(String targetStreamSegment, String sourceStreamSegment, AttributeUpdateCollection attributes, Duration timeout) {
    ensureRunning();
    logRequest("mergeStreamSegment", targetStreamSegment, sourceStreamSegment);
    this.metrics.mergeSegment();
    TimeoutTimer timer = new TimeoutTimer(timeout);
    // complete the cleanup phase, but still bubble up any exceptions to the caller.
    return this.metadataStore.getOrAssignSegmentId(targetStreamSegment, timer.getRemaining(), targetSegmentId -> this.metadataStore.getOrAssignSegmentId(sourceStreamSegment, timer.getRemaining(), sourceSegmentId -> mergeStreamSegment(targetSegmentId, sourceSegmentId, attributes, timer))).handleAsync((msr, ex) -> {
        if (ex == null || Exceptions.unwrap(ex) instanceof StreamSegmentMergedException) {
            // No exception or segment was already merged. Need to clear SegmentInfo for source.
            // We can do this asynchronously and not wait on it.
            this.metadataStore.clearSegmentInfo(sourceStreamSegment, timer.getRemaining());
        }
        if (ex == null) {
            // Everything is good. Return the result.
            return msr;
        } else {
            // Re-throw the exception to the caller in this case.
            throw new CompletionException(ex);
        }
    }, this.executor);
}
Also used : ATTRIBUTE_SLTS_LATEST_SNAPSHOT_ID(io.pravega.segmentstore.contracts.Attributes.ATTRIBUTE_SLTS_LATEST_SNAPSHOT_ID) Storage(io.pravega.segmentstore.storage.Storage) StreamSegmentNotExistsException(io.pravega.segmentstore.contracts.StreamSegmentNotExistsException) ContainerEventProcessor(io.pravega.segmentstore.server.ContainerEventProcessor) OperationPriority(io.pravega.segmentstore.server.logs.operations.OperationPriority) SneakyThrows(lombok.SneakyThrows) Retry(io.pravega.common.util.Retry) MergeSegmentOperation(io.pravega.segmentstore.server.logs.operations.MergeSegmentOperation) RequiredArgsConstructor(lombok.RequiredArgsConstructor) ContainerMetadata(io.pravega.segmentstore.server.ContainerMetadata) SnapshotInfoStore(io.pravega.segmentstore.storage.chunklayer.SnapshotInfoStore) UpdateableSegmentMetadata(io.pravega.segmentstore.server.UpdateableSegmentMetadata) SegmentProperties(io.pravega.segmentstore.contracts.SegmentProperties) ReadIndexFactory(io.pravega.segmentstore.server.ReadIndexFactory) AttributeUpdate(io.pravega.segmentstore.contracts.AttributeUpdate) StreamSegmentSealedException(io.pravega.segmentstore.contracts.StreamSegmentSealedException) AttributeIndexFactory(io.pravega.segmentstore.server.attributes.AttributeIndexFactory) BufferView(io.pravega.common.util.BufferView) Duration(java.time.Duration) Map(java.util.Map) AbstractService(com.google.common.util.concurrent.AbstractService) Operation(io.pravega.segmentstore.server.logs.operations.Operation) StreamSegmentTruncateOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentTruncateOperation) RetryAndThrowConditionally(io.pravega.common.util.Retry.RetryAndThrowConditionally) Services(io.pravega.common.concurrent.Services) ContainerOfflineException(io.pravega.segmentstore.server.ContainerOfflineException) Attributes(io.pravega.segmentstore.contracts.Attributes) SegmentStoreMetrics(io.pravega.segmentstore.server.SegmentStoreMetrics) Collection(java.util.Collection) CompletionException(java.util.concurrent.CompletionException) Writer(io.pravega.segmentstore.server.Writer) Collectors(java.util.stream.Collectors) SimpleStorageFactory(io.pravega.segmentstore.storage.SimpleStorageFactory) Objects(java.util.Objects) List(java.util.List) Slf4j(lombok.extern.slf4j.Slf4j) SegmentContainerFactory(io.pravega.segmentstore.server.SegmentContainerFactory) ContainerTableExtension(io.pravega.segmentstore.server.tables.ContainerTableExtension) ATTRIBUTE_SLTS_LATEST_SNAPSHOT_EPOCH(io.pravega.segmentstore.contracts.Attributes.ATTRIBUTE_SLTS_LATEST_SNAPSHOT_EPOCH) WriterSegmentProcessor(io.pravega.segmentstore.server.WriterSegmentProcessor) Futures(io.pravega.common.concurrent.Futures) ReadResult(io.pravega.segmentstore.contracts.ReadResult) Getter(lombok.Getter) IllegalContainerStateException(io.pravega.segmentstore.server.IllegalContainerStateException) ExtendedChunkInfo(io.pravega.segmentstore.contracts.ExtendedChunkInfo) Exceptions(io.pravega.common.Exceptions) StorageFactory(io.pravega.segmentstore.storage.StorageFactory) AtomicBoolean(java.util.concurrent.atomic.AtomicBoolean) HashMap(java.util.HashMap) CompletableFuture(java.util.concurrent.CompletableFuture) PriorityCalculator(io.pravega.segmentstore.server.logs.PriorityCalculator) BadAttributeUpdateException(io.pravega.segmentstore.contracts.BadAttributeUpdateException) Supplier(java.util.function.Supplier) ArrayList(java.util.ArrayList) SegmentMetadata(io.pravega.segmentstore.server.SegmentMetadata) SegmentType(io.pravega.segmentstore.contracts.SegmentType) ImmutableList(com.google.common.collect.ImmutableList) AttributeUpdaterOperation(io.pravega.segmentstore.server.logs.operations.AttributeUpdaterOperation) ScheduledExecutorService(java.util.concurrent.ScheduledExecutorService) TableBasedMetadataStore(io.pravega.segmentstore.storage.metadata.TableBasedMetadataStore) AttributeIterator(io.pravega.segmentstore.server.AttributeIterator) StreamSegmentMapOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentMapOperation) Nullable(javax.annotation.Nullable) ChunkedSegmentStorage(io.pravega.segmentstore.storage.chunklayer.ChunkedSegmentStorage) LoggerHelpers(io.pravega.common.LoggerHelpers) SegmentContainerExtension(io.pravega.segmentstore.server.SegmentContainerExtension) WriterFactory(io.pravega.segmentstore.server.WriterFactory) NameUtils(io.pravega.shared.NameUtils) AttributeIndex(io.pravega.segmentstore.server.AttributeIndex) TimeoutTimer(io.pravega.common.TimeoutTimer) UpdateAttributesOperation(io.pravega.segmentstore.server.logs.operations.UpdateAttributesOperation) AttributeId(io.pravega.segmentstore.contracts.AttributeId) lombok.val(lombok.val) OperationLog(io.pravega.segmentstore.server.OperationLog) MergeStreamSegmentResult(io.pravega.segmentstore.contracts.MergeStreamSegmentResult) StreamSegmentMergedException(io.pravega.segmentstore.contracts.StreamSegmentMergedException) UtilsWrapper(io.pravega.segmentstore.storage.chunklayer.UtilsWrapper) Service(com.google.common.util.concurrent.Service) SnapshotInfo(io.pravega.segmentstore.storage.chunklayer.SnapshotInfo) Consumer(java.util.function.Consumer) DirectSegmentAccess(io.pravega.segmentstore.server.DirectSegmentAccess) ContainerAttributeIndex(io.pravega.segmentstore.server.attributes.ContainerAttributeIndex) AttributeUpdateCollection(io.pravega.segmentstore.contracts.AttributeUpdateCollection) SegmentOperation(io.pravega.segmentstore.server.SegmentOperation) StreamSegmentAppendOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentAppendOperation) OperationLogFactory(io.pravega.segmentstore.server.OperationLogFactory) SegmentContainer(io.pravega.segmentstore.server.SegmentContainer) Preconditions(com.google.common.base.Preconditions) AttributeUpdateType(io.pravega.segmentstore.contracts.AttributeUpdateType) ReadIndex(io.pravega.segmentstore.server.ReadIndex) Collections(java.util.Collections) DeleteSegmentOperation(io.pravega.segmentstore.server.logs.operations.DeleteSegmentOperation) StreamSegmentSealOperation(io.pravega.segmentstore.server.logs.operations.StreamSegmentSealOperation) CompletionException(java.util.concurrent.CompletionException) StreamSegmentMergedException(io.pravega.segmentstore.contracts.StreamSegmentMergedException) TimeoutTimer(io.pravega.common.TimeoutTimer)

Example 9 with AttributeUpdateCollection

use of io.pravega.segmentstore.contracts.AttributeUpdateCollection in project pravega by pravega.

the class ContainerRecoveryUtils method updateCoreAttributes.

/**
 * Updates Core Attributes for all Segments for the given Containers.
 * This method iterates through all the back copies of Container Metadata Segments, interprets all entries as
 * Segment-SegmentInfo mappings and extracts the Core Attributes for each. These Core Attributes are then applied
 * to the same segments in the given Containers.
 * @param backUpMetadataSegments    A map of back copies of metadata segments along with their container Ids.
 * @param containersMap             A map of {@link DebugStreamSegmentContainer} instances with their container Ids.
 * @param executorService           A thread pool for execution.
 * @param timeout                   Timeout for the operation.
 * @throws InterruptedException     If the operation was interrupted while waiting.
 * @throws TimeoutException         If the timeout expired prior to being able to complete update attributes for all segments.
 * @throws ExecutionException       When execution of update attributes to all segments encountered an error.
 */
public static void updateCoreAttributes(Map<Integer, String> backUpMetadataSegments, Map<Integer, DebugStreamSegmentContainer> containersMap, ExecutorService executorService, Duration timeout) throws InterruptedException, ExecutionException, TimeoutException {
    Preconditions.checkState(backUpMetadataSegments.size() == containersMap.size(), "The number of " + "back-up metadata segments = %s and the number of containers = %s should match.", backUpMetadataSegments.size(), containersMap.size());
    val args = IteratorArgs.builder().fetchTimeout(timeout).build();
    SegmentToContainerMapper segToConMapper = new SegmentToContainerMapper(containersMap.size(), true);
    // Iterate through all back up metadata segments
    for (val backUpMetadataSegmentEntry : backUpMetadataSegments.entrySet()) {
        // Get the name of original metadata segment
        val metadataSegment = NameUtils.getMetadataSegmentName(backUpMetadataSegmentEntry.getKey());
        // Get the name of back up metadata segment
        val backUpMetadataSegment = backUpMetadataSegmentEntry.getValue();
        // Get the container for back up metadata segment
        val containerForBackUpMetadataSegment = containersMap.get(segToConMapper.getContainerId(backUpMetadataSegment));
        log.info("Back up container metadata segment name: {} and its container id: {}", backUpMetadataSegment, containerForBackUpMetadataSegment.getId());
        // Get the container for segments inside back up metadata segment
        val container = containersMap.get(backUpMetadataSegmentEntry.getKey());
        // Make sure the backup segment is registered as a table segment.
        val bmsInfo = containerForBackUpMetadataSegment.getStreamSegmentInfo(backUpMetadataSegment, timeout).get(timeout.toMillis(), TimeUnit.MILLISECONDS);
        if (bmsInfo.getAttributes().getOrDefault(TableAttributes.INDEX_OFFSET, Attributes.NULL_ATTRIBUTE_VALUE) == Attributes.NULL_ATTRIBUTE_VALUE) {
            log.info("Back up container metadata segment name: {} does not have INDEX_OFFSET set; setting to 0 (forcing reindexing).", backUpMetadataSegment);
            containerForBackUpMetadataSegment.forSegment(backUpMetadataSegment, timeout).thenCompose(s -> s.updateAttributes(AttributeUpdateCollection.from(new AttributeUpdate(TableAttributes.INDEX_OFFSET, AttributeUpdateType.Replace, 0)), timeout)).get(timeout.toMillis(), TimeUnit.MILLISECONDS);
            refreshDerivedProperties(backUpMetadataSegment, containerForBackUpMetadataSegment);
        }
        // Get the iterator to iterate through all segments in the back up metadata segment
        val tableExtension = containerForBackUpMetadataSegment.getExtension(ContainerTableExtension.class);
        val entryIterator = tableExtension.entryIterator(backUpMetadataSegment, args).get(timeout.toMillis(), TimeUnit.MILLISECONDS);
        val futures = new ArrayList<CompletableFuture<Void>>();
        // Iterating through all segments in the back up metadata segment
        entryIterator.forEachRemaining(item -> {
            for (val entry : item.getEntries()) {
                val segmentInfo = MetadataStore.SegmentInfo.deserialize(entry.getValue());
                val properties = segmentInfo.getProperties();
                // skip, if this is original metadata segment
                if (properties.getName().equals(metadataSegment)) {
                    continue;
                }
                // Get the attributes for the current segment
                val attributeUpdates = properties.getAttributes().entrySet().stream().map(e -> new AttributeUpdate(e.getKey(), AttributeUpdateType.Replace, e.getValue())).collect(Collectors.toCollection(AttributeUpdateCollection::new));
                log.info("Segment Name: {} Attributes Updates: {}", properties.getName(), attributeUpdates);
                // Update attributes for the current segment
                futures.add(Futures.exceptionallyExpecting(container.updateAttributes(properties.getName(), attributeUpdates, timeout).thenRun(() -> refreshDerivedProperties(properties.getName(), container)), ex -> ex instanceof StreamSegmentNotExistsException, null));
            }
        }, executorService).get(timeout.toMillis(), TimeUnit.MILLISECONDS);
        // Waiting for update attributes for all segments in each back up metadata segment.
        Futures.allOf(futures).get(timeout.toMillis(), TimeUnit.MILLISECONDS);
    }
}
Also used : lombok.val(lombok.val) TableAttributes(io.pravega.segmentstore.contracts.tables.TableAttributes) Storage(io.pravega.segmentstore.storage.Storage) StreamSegmentNotExistsException(io.pravega.segmentstore.contracts.StreamSegmentNotExistsException) Date(java.util.Date) Exceptions(io.pravega.common.Exceptions) SimpleDateFormat(java.text.SimpleDateFormat) TimeoutException(java.util.concurrent.TimeoutException) HashMap(java.util.HashMap) CompletableFuture(java.util.concurrent.CompletableFuture) IteratorArgs(io.pravega.segmentstore.contracts.tables.IteratorArgs) ArrayList(java.util.ArrayList) SegmentProperties(io.pravega.segmentstore.contracts.SegmentProperties) HashSet(java.util.HashSet) AttributeUpdate(io.pravega.segmentstore.contracts.AttributeUpdate) ByteArrayInputStream(java.io.ByteArrayInputStream) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) Duration(java.time.Duration) Map(java.util.Map) ExecutorService(java.util.concurrent.ExecutorService) NameUtils(io.pravega.shared.NameUtils) Attributes(io.pravega.segmentstore.contracts.Attributes) Iterator(java.util.Iterator) lombok.val(lombok.val) Set(java.util.Set) Collectors(java.util.stream.Collectors) ExecutionException(java.util.concurrent.ExecutionException) TimeUnit(java.util.concurrent.TimeUnit) Slf4j(lombok.extern.slf4j.Slf4j) AttributeUpdateCollection(io.pravega.segmentstore.contracts.AttributeUpdateCollection) ContainerTableExtension(io.pravega.segmentstore.server.tables.ContainerTableExtension) SegmentToContainerMapper(io.pravega.shared.segment.SegmentToContainerMapper) Preconditions(com.google.common.base.Preconditions) AttributeUpdateType(io.pravega.segmentstore.contracts.AttributeUpdateType) Futures(io.pravega.common.concurrent.Futures) NameUtils.getMetadataSegmentName(io.pravega.shared.NameUtils.getMetadataSegmentName) AttributeUpdateCollection(io.pravega.segmentstore.contracts.AttributeUpdateCollection) AttributeUpdate(io.pravega.segmentstore.contracts.AttributeUpdate) SegmentToContainerMapper(io.pravega.shared.segment.SegmentToContainerMapper) ArrayList(java.util.ArrayList) StreamSegmentNotExistsException(io.pravega.segmentstore.contracts.StreamSegmentNotExistsException)

Example 10 with AttributeUpdateCollection

use of io.pravega.segmentstore.contracts.AttributeUpdateCollection in project pravega by pravega.

the class MetadataStore method createTransientSegment.

/**
 * Creates a new Transient Segment with given name.
 *
 * @param segmentName The case-sensitive Segment Name.
 * @param attributes  The initial attributes for the StreamSegment, if any.
 * @param timeout     Timeout for the operation.
 * @return A CompletableFuture that, when completed normally, will indicate the TransientSegment has been created.
 */
private CompletableFuture<Void> createTransientSegment(String segmentName, Collection<AttributeUpdate> attributes, Duration timeout) {
    AttributeUpdateCollection attrs = AttributeUpdateCollection.from(attributes);
    attrs.add(new AttributeUpdate(Attributes.CREATION_EPOCH, AttributeUpdateType.None, this.connector.containerMetadata.getContainerEpoch()));
    return Futures.toVoid(submitAssignmentWithRetry(newSegment(segmentName, SegmentType.TRANSIENT_SEGMENT, attrs), timeout));
}
Also used : AttributeUpdateCollection(io.pravega.segmentstore.contracts.AttributeUpdateCollection) AttributeUpdate(io.pravega.segmentstore.contracts.AttributeUpdate)

Aggregations

AttributeUpdateCollection (io.pravega.segmentstore.contracts.AttributeUpdateCollection)33 AttributeUpdate (io.pravega.segmentstore.contracts.AttributeUpdate)28 lombok.val (lombok.val)23 AttributeId (io.pravega.segmentstore.contracts.AttributeId)18 ArrayList (java.util.ArrayList)17 HashMap (java.util.HashMap)16 SegmentProperties (io.pravega.segmentstore.contracts.SegmentProperties)15 CompletableFuture (java.util.concurrent.CompletableFuture)15 AttributeUpdateType (io.pravega.segmentstore.contracts.AttributeUpdateType)14 Test (org.junit.Test)14 Map (java.util.Map)13 Attributes (io.pravega.segmentstore.contracts.Attributes)12 Exceptions (io.pravega.common.Exceptions)11 Futures (io.pravega.common.concurrent.Futures)11 BufferView (io.pravega.common.util.BufferView)11 BadAttributeUpdateException (io.pravega.segmentstore.contracts.BadAttributeUpdateException)11 SegmentType (io.pravega.segmentstore.contracts.SegmentType)11 UpdateableSegmentMetadata (io.pravega.segmentstore.server.UpdateableSegmentMetadata)11 Operation (io.pravega.segmentstore.server.logs.operations.Operation)11 StreamSegmentSealOperation (io.pravega.segmentstore.server.logs.operations.StreamSegmentSealOperation)11