Remove WriteOperations.put()/merge() with ensure parents
[mdsal.git] / binding / mdsal-binding-util / src / main / java / org / opendaylight / mdsal / binding / util / TransactionAdapter.java
1 /*
2  * Copyright © 2018 Red Hat, Inc. and others.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.mdsal.binding.util;
9
10 import static com.google.common.base.Preconditions.checkArgument;
11
12 import com.google.common.collect.ForwardingObject;
13 import com.google.common.util.concurrent.FluentFuture;
14 import java.util.Optional;
15 import org.eclipse.jdt.annotation.NonNull;
16 import org.opendaylight.mdsal.binding.api.DataBroker;
17 import org.opendaylight.mdsal.binding.api.ReadWriteTransaction;
18 import org.opendaylight.mdsal.binding.api.WriteTransaction;
19 import org.opendaylight.mdsal.common.api.CommitInfo;
20 import org.opendaylight.mdsal.common.api.LogicalDatastoreType;
21 import org.opendaylight.yangtools.yang.binding.DataObject;
22 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
23
24 /**
25  * Adapter allowing managed, datastore-constrained transactions to be used with methods expecting
26  * generic {@link DataBroker} transactions.
27  *
28  * <p>The adapted transactions maintain the following constraints: they cannot be cancelled or
29  * submitted (only the transaction manager can do this), and they cannot access a logical datastore
30  * other than the one they were created for.
31  *
32  * @deprecated This is only intended for temporary use during complex migrations to managed transactions.
33  */
34 @Deprecated
35 public final class TransactionAdapter {
36     private TransactionAdapter() {
37     }
38
39     /**
40      * Adapts the given datastore-constrained read-write transaction to a generic read-write transaction.
41      *
42      * @param datastoreTx The transaction to adapt.
43      * @return The adapted transaction.
44      * @throws NullPointerException if the provided transaction is {@code null}.
45      */
46     public static ReadWriteTransaction toReadWriteTransaction(
47             final TypedReadWriteTransaction<? extends Datastore> datastoreTx) {
48         if (datastoreTx instanceof TypedReadWriteTransactionImpl) {
49             final TypedReadWriteTransactionImpl<?> txImpl = (TypedReadWriteTransactionImpl<?>) datastoreTx;
50             return new ReadWriteTransactionAdapter<>(txImpl.getDatastoreType(), txImpl);
51         }
52         throw new IllegalArgumentException("Unsupported TypedWriteTransaction implementation "
53                 + datastoreTx.getClass());
54     }
55
56     /**
57      * Adapts the given datastore-constrained write transaction to a generic write transaction. Note that this
58      * can be used to adapt a read-write transaction to a write transaction.
59      *
60      * @param datastoreTx The transaction to adapt.
61      * @return The adapted transaction.
62      */
63     public static WriteTransaction toWriteTransaction(final TypedWriteTransaction<? extends Datastore> datastoreTx) {
64         if (datastoreTx instanceof TypedWriteTransactionImpl) {
65             final TypedWriteTransactionImpl<?, ?> txImpl = (TypedWriteTransactionImpl<?, ?>) datastoreTx;
66             return new WriteTransactionAdapter<>(txImpl.getDatastoreType(), txImpl);
67         }
68         throw new IllegalArgumentException("Unsupported TypedWriteTransaction implementation "
69                 + datastoreTx.getClass());
70     }
71
72     private static class WriteTransactionAdapter<S extends Datastore, D extends TypedWriteTransaction<S>>
73             extends ForwardingObject implements WriteTransaction {
74         private final LogicalDatastoreType datastoreType;
75         private final D delegate;
76
77         WriteTransactionAdapter(final LogicalDatastoreType datastoreType, final D delegate) {
78             this.datastoreType = datastoreType;
79             this.delegate = delegate;
80         }
81
82         @Override
83         public <T extends DataObject> void put(final LogicalDatastoreType store, final InstanceIdentifier<T> path,
84                 final T data) {
85             checkStore(store);
86             delegate.put(path, data);
87         }
88
89         @Override
90         public <T extends DataObject> void mergeParentStructurePut(final LogicalDatastoreType store,
91                 final InstanceIdentifier<T> path, final T data) {
92             checkStore(store);
93             delegate.mergeParentStructurePut(path, data);
94         }
95
96         @Override
97         public <T extends DataObject> void merge(final LogicalDatastoreType store, final InstanceIdentifier<T> path,
98                 final T data) {
99             checkStore(store);
100             delegate.merge(path, data);
101         }
102
103         @Override
104         public <T extends DataObject> void mergeParentStructureMerge(final LogicalDatastoreType store,
105                 final InstanceIdentifier<T> path, final T data) {
106             checkStore(store);
107             delegate.mergeParentStructureMerge(path, data);
108         }
109
110         @Override
111         public boolean cancel() {
112             throw new UnsupportedOperationException("Managed transactions must not be cancelled");
113         }
114
115         @Override
116         public void delete(final LogicalDatastoreType store, final InstanceIdentifier<?> path) {
117             checkStore(store);
118             delegate.delete(path);
119         }
120
121         @Override
122         public @NonNull FluentFuture<? extends CommitInfo> commit() {
123             throw new UnsupportedOperationException("Managed transactions must not be committed");
124         }
125
126         @Override
127         public Object getIdentifier() {
128             return delegate.getIdentifier();
129         }
130
131         @Override
132         protected D delegate() {
133             return delegate;
134         }
135
136         void checkStore(final LogicalDatastoreType store) {
137             checkArgument(datastoreType.equals(store), "Invalid datastore %s used instead of %s", store, datastoreType);
138         }
139     }
140
141     private static final class ReadWriteTransactionAdapter<S extends Datastore>
142             extends WriteTransactionAdapter<S, TypedReadWriteTransaction<S>> implements ReadWriteTransaction {
143         ReadWriteTransactionAdapter(final LogicalDatastoreType datastoreType,
144                 final TypedReadWriteTransaction<S> delegate) {
145             super(datastoreType, delegate);
146         }
147
148         @Override
149         public <T extends DataObject> FluentFuture<Optional<T>> read(final LogicalDatastoreType store,
150                 final InstanceIdentifier<T> path) {
151             checkStore(store);
152             return delegate().read(path);
153         }
154
155         @Override
156         public FluentFuture<Boolean> exists(final LogicalDatastoreType store,final InstanceIdentifier<?> path) {
157             checkStore(store);
158             return delegate().exists(path);
159         }
160     }
161 }