2323import org .apache .lucene .index .IndexFormatTooNewException ;
2424import org .apache .lucene .index .IndexFormatTooOldException ;
2525import org .apache .lucene .store .OutputStreamIndexOutput ;
26+ import org .elasticsearch .cluster .metadata .MetaData ;
2627import org .elasticsearch .common .CheckedConsumer ;
2728import org .elasticsearch .common .CheckedFunction ;
2829import org .elasticsearch .common .blobstore .BlobContainer ;
3334import org .elasticsearch .common .io .stream .StreamOutput ;
3435import org .elasticsearch .common .lucene .store .ByteArrayIndexInput ;
3536import org .elasticsearch .common .lucene .store .IndexOutputOutputStream ;
37+ import org .elasticsearch .common .xcontent .LoggingDeprecationHandler ;
3638import org .elasticsearch .common .xcontent .NamedXContentRegistry ;
3739import org .elasticsearch .common .xcontent .ToXContent ;
3840import org .elasticsearch .common .xcontent .XContentBuilder ;
3941import org .elasticsearch .common .xcontent .XContentFactory ;
42+ import org .elasticsearch .common .xcontent .XContentHelper ;
4043import org .elasticsearch .common .xcontent .XContentParser ;
4144import org .elasticsearch .common .xcontent .XContentType ;
4245import org .elasticsearch .core .internal .io .Streams ;
4346import org .elasticsearch .gateway .CorruptStateException ;
47+ import org .elasticsearch .snapshots .SnapshotInfo ;
4448
4549import java .io .ByteArrayOutputStream ;
4650import java .io .IOException ;
4751import java .io .InputStream ;
4852import java .io .OutputStream ;
53+ import java .util .HashMap ;
54+ import java .util .Locale ;
55+ import java .util .Map ;
4956
5057/**
5158 * Snapshot metadata file format used in v2.0 and above
5259 */
53- public class ChecksumBlobStoreFormat <T extends ToXContent > extends BlobStoreFormat <T > {
60+ public final class ChecksumBlobStoreFormat <T extends ToXContent > {
61+
62+ // Serialization parameters to specify correct context for metadata serialization
63+ private static final ToXContent .Params SNAPSHOT_ONLY_FORMAT_PARAMS ;
64+
65+ static {
66+ Map <String , String > snapshotOnlyParams = new HashMap <>();
67+ // when metadata is serialized certain elements of the metadata shouldn't be included into snapshot
68+ // exclusion of these elements is done by setting MetaData.CONTEXT_MODE_PARAM to MetaData.CONTEXT_MODE_SNAPSHOT
69+ snapshotOnlyParams .put (MetaData .CONTEXT_MODE_PARAM , MetaData .CONTEXT_MODE_SNAPSHOT );
70+ // serialize SnapshotInfo using the SNAPSHOT mode
71+ snapshotOnlyParams .put (SnapshotInfo .CONTEXT_MODE_PARAM , SnapshotInfo .CONTEXT_MODE_SNAPSHOT );
72+ SNAPSHOT_ONLY_FORMAT_PARAMS = new ToXContent .MapParams (snapshotOnlyParams );
73+ }
5474
5575 private static final XContentType DEFAULT_X_CONTENT_TYPE = XContentType .SMILE ;
5676
@@ -59,12 +79,18 @@ public class ChecksumBlobStoreFormat<T extends ToXContent> extends BlobStoreForm
5979
6080 private static final int BUFFER_SIZE = 4096 ;
6181
62- protected final XContentType xContentType ;
82+ private final XContentType xContentType ;
6383
64- protected final boolean compress ;
84+ private final boolean compress ;
6585
6686 private final String codec ;
6787
88+ private final String blobNameFormat ;
89+
90+ private final CheckedFunction <XContentParser , T , IOException > reader ;
91+
92+ private final NamedXContentRegistry namedXContentRegistry ;
93+
6894 /**
6995 * @param codec codec name
7096 * @param blobNameFormat format of the blobname in {@link String#format} format
@@ -74,7 +100,9 @@ public class ChecksumBlobStoreFormat<T extends ToXContent> extends BlobStoreForm
74100 */
75101 public ChecksumBlobStoreFormat (String codec , String blobNameFormat , CheckedFunction <XContentParser , T , IOException > reader ,
76102 NamedXContentRegistry namedXContentRegistry , boolean compress , XContentType xContentType ) {
77- super (blobNameFormat , reader , namedXContentRegistry );
103+ this .reader = reader ;
104+ this .blobNameFormat = blobNameFormat ;
105+ this .namedXContentRegistry = namedXContentRegistry ;
78106 this .xContentType = xContentType ;
79107 this .compress = compress ;
80108 this .codec = codec ;
@@ -91,6 +119,29 @@ public ChecksumBlobStoreFormat(String codec, String blobNameFormat, CheckedFunct
91119 this (codec , blobNameFormat , reader , namedXContentRegistry , compress , DEFAULT_X_CONTENT_TYPE );
92120 }
93121
122+ /**
123+ * Reads and parses the blob with given name, applying name translation using the {link #blobName} method
124+ *
125+ * @param blobContainer blob container
126+ * @param name name to be translated into
127+ * @return parsed blob object
128+ */
129+ public T read (BlobContainer blobContainer , String name ) throws IOException {
130+ String blobName = blobName (name );
131+ return readBlob (blobContainer , blobName );
132+ }
133+
134+ /**
135+ * Deletes obj in the blob container
136+ */
137+ public void delete (BlobContainer blobContainer , String name ) throws IOException {
138+ blobContainer .deleteBlob (blobName (name ));
139+ }
140+
141+ public String blobName (String name ) {
142+ return String .format (Locale .ROOT , blobNameFormat , name );
143+ }
144+
94145 /**
95146 * Reads blob with specified name without resolving the blobName using using {@link #blobName} method.
96147 *
@@ -108,8 +159,10 @@ public T readBlob(BlobContainer blobContainer, String blobName) throws IOExcepti
108159 CodecUtil .checkHeader (indexInput , codec , VERSION , VERSION );
109160 long filePointer = indexInput .getFilePointer ();
110161 long contentSize = indexInput .length () - CodecUtil .footerLength () - filePointer ;
111- BytesReference bytesReference = new BytesArray (bytes , (int ) filePointer , (int ) contentSize );
112- return read (bytesReference );
162+ try (XContentParser parser = XContentHelper .createParser (namedXContentRegistry , LoggingDeprecationHandler .INSTANCE ,
163+ new BytesArray (bytes , (int ) filePointer , (int ) contentSize ))) {
164+ return reader .apply (parser );
165+ }
113166 } catch (CorruptIndexException | IndexFormatTooOldException | IndexFormatTooNewException ex ) {
114167 // we trick this into a dedicated exception with the original stacktrace
115168 throw new CorruptStateException (ex );
@@ -156,7 +209,17 @@ public void write(T obj, BlobContainer blobContainer, String name) throws IOExce
156209 }
157210
158211 private void writeTo (final T obj , final String blobName , final CheckedConsumer <BytesArray , IOException > consumer ) throws IOException {
159- final BytesReference bytes = write (obj );
212+ final BytesReference bytes ;
213+ try (BytesStreamOutput bytesStreamOutput = new BytesStreamOutput ()) {
214+ if (compress ) {
215+ try (StreamOutput compressedStreamOutput = CompressorFactory .COMPRESSOR .streamOutput (bytesStreamOutput )) {
216+ write (obj , compressedStreamOutput );
217+ }
218+ } else {
219+ write (obj , bytesStreamOutput );
220+ }
221+ bytes = bytesStreamOutput .bytes ();
222+ }
160223 try (ByteArrayOutputStream outputStream = new ByteArrayOutputStream ()) {
161224 final String resourceDesc = "ChecksumBlobStoreFormat.writeBlob(blob=\" " + blobName + "\" )" ;
162225 try (OutputStreamIndexOutput indexOutput = new OutputStreamIndexOutput (resourceDesc , blobName , outputStream , BUFFER_SIZE )) {
@@ -176,20 +239,7 @@ public void close() {
176239 }
177240 }
178241
179- protected BytesReference write (T obj ) throws IOException {
180- try (BytesStreamOutput bytesStreamOutput = new BytesStreamOutput ()) {
181- if (compress ) {
182- try (StreamOutput compressedStreamOutput = CompressorFactory .COMPRESSOR .streamOutput (bytesStreamOutput )) {
183- write (obj , compressedStreamOutput );
184- }
185- } else {
186- write (obj , bytesStreamOutput );
187- }
188- return bytesStreamOutput .bytes ();
189- }
190- }
191-
192- protected void write (T obj , StreamOutput streamOutput ) throws IOException {
242+ private void write (T obj , StreamOutput streamOutput ) throws IOException {
193243 try (XContentBuilder builder = XContentFactory .contentBuilder (xContentType , streamOutput )) {
194244 builder .startObject ();
195245 obj .toXContent (builder , SNAPSHOT_ONLY_FORMAT_PARAMS );
0 commit comments