+
+ public static Builder builder() {
+ return new Builder();
+ }
+
+ public abstract static class AbstractBuilder<T extends AbstractBuilder<T, S>, S extends Shard> {
+ private final Class<? extends S> shardClass;
+ private ShardIdentifier id;
+ private Map<String, String> peerAddresses = Collections.emptyMap();
+ private DatastoreContext datastoreContext;
+ private EffectiveModelContextProvider schemaContextProvider;
+ private DatastoreSnapshot.ShardSnapshot restoreFromSnapshot;
+ private DataTree dataTree;
+
+ private volatile boolean sealed;
+
+ AbstractBuilder(final Class<? extends S> shardClass) {
+ this.shardClass = shardClass;
+ }
+
+ final void checkSealed() {
+ checkState(!sealed, "Builder is already sealed - further modifications are not allowed");
+ }
+
+ @SuppressWarnings("unchecked")
+ private T self() {
+ return (T) this;
+ }
+
+ public T id(final ShardIdentifier newId) {
+ checkSealed();
+ this.id = newId;
+ return self();
+ }
+
+ public T peerAddresses(final Map<String, String> newPeerAddresses) {
+ checkSealed();
+ this.peerAddresses = newPeerAddresses;
+ return self();
+ }
+
+ public T datastoreContext(final DatastoreContext newDatastoreContext) {
+ checkSealed();
+ this.datastoreContext = newDatastoreContext;
+ return self();
+ }
+
+ public T schemaContextProvider(final EffectiveModelContextProvider newSchemaContextProvider) {
+ checkSealed();
+ this.schemaContextProvider = requireNonNull(newSchemaContextProvider);
+ return self();
+ }
+
+ public T restoreFromSnapshot(final DatastoreSnapshot.ShardSnapshot newRestoreFromSnapshot) {
+ checkSealed();
+ this.restoreFromSnapshot = newRestoreFromSnapshot;
+ return self();
+ }
+
+ public T dataTree(final DataTree newDataTree) {
+ checkSealed();
+ this.dataTree = newDataTree;
+ return self();
+ }
+
+ public ShardIdentifier getId() {
+ return id;
+ }
+
+ public Map<String, String> getPeerAddresses() {
+ return peerAddresses;
+ }
+
+ public DatastoreContext getDatastoreContext() {
+ return datastoreContext;
+ }
+
+ public EffectiveModelContext getSchemaContext() {
+ return verifyNotNull(schemaContextProvider.getEffectiveModelContext());
+ }
+
+ public DatastoreSnapshot.ShardSnapshot getRestoreFromSnapshot() {
+ return restoreFromSnapshot;
+ }
+
+ public DataTree getDataTree() {
+ return dataTree;
+ }
+
+ public TreeType getTreeType() {
+ switch (datastoreContext.getLogicalStoreType()) {
+ case CONFIGURATION:
+ return TreeType.CONFIGURATION;
+ case OPERATIONAL:
+ return TreeType.OPERATIONAL;
+ default:
+ throw new IllegalStateException("Unhandled logical store type "
+ + datastoreContext.getLogicalStoreType());
+ }
+ }
+
+ protected void verify() {
+ requireNonNull(id, "id should not be null");
+ requireNonNull(peerAddresses, "peerAddresses should not be null");
+ requireNonNull(datastoreContext, "dataStoreContext should not be null");
+ requireNonNull(schemaContextProvider, "schemaContextProvider should not be null");
+ }
+
+ public Props props() {
+ sealed = true;
+ verify();
+ return Props.create(shardClass, this);
+ }
+ }
+
+ public static class Builder extends AbstractBuilder<Builder, Shard> {
+ Builder() {
+ this(Shard.class);
+ }
+
+ Builder(final Class<? extends Shard> shardClass) {
+ super(shardClass);
+ }
+ }
+
+ Ticker ticker() {
+ return Ticker.systemTicker();
+ }
+
+ void scheduleNextPendingTransaction() {
+ self().tell(RESUME_NEXT_PENDING_TRANSACTION, ActorRef.noSender());
+ }