FeedRangeInternal.java
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
package com.azure.cosmos.implementation.feedranges;
import com.azure.cosmos.implementation.Constants;
import com.azure.cosmos.implementation.IRoutingMapProvider;
import com.azure.cosmos.implementation.JsonSerializable;
import com.azure.cosmos.implementation.Utils;
import com.azure.cosmos.implementation.apachecommons.collections.list.UnmodifiableList;
import com.azure.cosmos.implementation.routing.PartitionKeyInternal;
import com.azure.cosmos.implementation.routing.Range;
import com.azure.cosmos.models.FeedRange;
import com.azure.cosmos.models.PartitionKeyDefinition;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.node.ObjectNode;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import reactor.core.publisher.Mono;
import java.io.IOException;
import static com.azure.cosmos.implementation.guava25.base.Preconditions.checkNotNull;
public abstract class FeedRangeInternal extends JsonSerializable implements FeedRange {
private final static Logger LOGGER = LoggerFactory.getLogger(FeedRangeInternal.class);
public abstract void accept(FeedRangeVisitor visitor);
public abstract <TInput> void accept(GenericFeedRangeVisitor<TInput> visitor, TInput input);
public abstract <T> Mono<T> accept(FeedRangeAsyncVisitor<T> visitor);
public static FeedRangeInternal convert(final FeedRange feedRange) {
checkNotNull(feedRange, "Argument 'feedRange' must not be null");
if (feedRange instanceof FeedRangeInternal) {
return (FeedRangeInternal)feedRange;
}
String json = feedRange.toJsonString();
return fromJsonString(json);
}
/**
* Creates a range from a previously obtained string representation.
*
* @param json A string representation of a feed range
* @return A feed range
*/
public static FeedRangeInternal fromJsonString(String json) {
FeedRangeInternal parsedRange = FeedRangeInternal.tryParse(json);
if (parsedRange == null) {
throw new IllegalArgumentException(
String.format(
"The provided string '%s' does not represent any known format.",
json));
}
return parsedRange;
}
public abstract Mono<UnmodifiableList<Range<String>>> getEffectiveRanges(
IRoutingMapProvider routingMapProvider,
String containerRid,
PartitionKeyDefinition partitionKeyDefinition);
public abstract Mono<UnmodifiableList<String>> getPartitionKeyRanges(
IRoutingMapProvider routingMapProvider,
String containerRid,
PartitionKeyDefinition partitionKeyDefinition);
public void populatePropertyBag() {
super.populatePropertyBag();
}
@Override
public abstract String toString();
@Override
public String toJsonString() {
return this.toJson();
}
public static FeedRangeInternal tryParse(final String jsonString) {
checkNotNull(jsonString, "Argument 'jsonString' must not be null");
final ObjectMapper mapper = Utils.getSimpleObjectMapper();
try {
JsonNode rootNode = mapper.readTree(jsonString);
JsonNode rangeNode = rootNode.get(Constants.Properties.RANGE);
if (rangeNode != null && rangeNode.isObject()) {
Range<String> range = new Range<>((ObjectNode)rangeNode);
return new FeedRangeEpkImpl(range);
}
JsonNode pkNode = rootNode.get(Constants.Properties.FEED_RANGE_PARTITION_KEY);
if (pkNode != null && pkNode.isArray()) {
PartitionKeyInternal pk = mapper.convertValue(pkNode, PartitionKeyInternal.class);
return new FeedRangePartitionKeyImpl(pk);
}
JsonNode pkRangeIdNode =
rootNode.get(Constants.Properties.FEED_RANGE_PARTITION_KEY_RANGE_ID);
if (pkRangeIdNode != null && pkRangeIdNode.isTextual()) {
return new FeedRangePartitionKeyRangeImpl(pkRangeIdNode.asText());
}
return null;
} catch (final IOException ioError) {
LOGGER.debug("Failed to parse feed range JSON {}", jsonString, ioError);
return null;
}
}
}