Skip to content

Commit 3f5d717

Browse files
committed
Remove PROTO-serialization from IndexMetaData.Custom (II)
Switches IndexMetaData.Custom to standard named serialization. Supersedes elastic#32683
1 parent 79375d3 commit 3f5d717

File tree

12 files changed

+526
-126
lines changed

12 files changed

+526
-126
lines changed

libs/x-content/src/main/java/org/elasticsearch/common/xcontent/NamedXContentRegistry.java

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -141,4 +141,15 @@ public <T, C> T parseNamedObject(Class<T> categoryClass, String name, XContentPa
141141
return categoryClass.cast(entry.parser.parse(parser, context));
142142
}
143143

144+
/**
145+
* Returns true if the given named object is supported by the current stream
146+
*/
147+
public <T> boolean supportsNamedObject(Class<T> categoryClass, String name) {
148+
Map<String, Entry> parsers = registry.get(categoryClass);
149+
if (parsers == null || registry.isEmpty()) {
150+
return false;
151+
}
152+
return parsers.containsKey(name);
153+
}
154+
144155
}

server/src/main/java/org/elasticsearch/action/admin/indices/create/CreateIndexRequest.java

Lines changed: 41 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -40,27 +40,32 @@
4040
import org.elasticsearch.common.settings.Settings;
4141
import org.elasticsearch.common.xcontent.DeprecationHandler;
4242
import org.elasticsearch.common.xcontent.LoggingDeprecationHandler;
43+
import org.elasticsearch.common.xcontent.NamedObjectNotFoundException;
4344
import org.elasticsearch.common.xcontent.NamedXContentRegistry;
4445
import org.elasticsearch.common.xcontent.ToXContentObject;
4546
import org.elasticsearch.common.xcontent.XContentBuilder;
4647
import org.elasticsearch.common.xcontent.XContentFactory;
4748
import org.elasticsearch.common.xcontent.XContentHelper;
4849
import org.elasticsearch.common.xcontent.XContentParser;
4950
import org.elasticsearch.common.xcontent.XContentType;
51+
import org.elasticsearch.plugins.spi.NamedXContentProvider;
5052

5153
import java.io.IOException;
5254
import java.io.InputStream;
5355
import java.io.UncheckedIOException;
56+
import java.util.ArrayList;
5457
import java.util.HashMap;
5558
import java.util.HashSet;
59+
import java.util.List;
5660
import java.util.Map;
5761
import java.util.Objects;
62+
import java.util.ServiceLoader;
5863
import java.util.Set;
5964

6065
import static org.elasticsearch.action.ValidateActions.addValidationError;
66+
import static org.elasticsearch.common.settings.Settings.Builder.EMPTY_SETTINGS;
6167
import static org.elasticsearch.common.settings.Settings.readSettingsFromStream;
6268
import static org.elasticsearch.common.settings.Settings.writeSettingsToStream;
63-
import static org.elasticsearch.common.settings.Settings.Builder.EMPTY_SETTINGS;
6469

6570
/**
6671
* A request to create an index. Best created with {@link org.elasticsearch.client.Requests#createIndexRequest(String)}.
@@ -374,8 +379,16 @@ public CreateIndexRequest source(BytesReference source, XContentType xContentTyp
374379
/**
375380
* Sets the settings and mappings as a single source.
376381
*/
377-
@SuppressWarnings("unchecked")
378382
public CreateIndexRequest source(Map<String, ?> source, DeprecationHandler deprecationHandler) {
383+
return source(source, deprecationHandler, null);
384+
}
385+
386+
387+
/**
388+
* Sets the settings, mappings and customs as a single source, using specified registry to parse customs
389+
*/
390+
@SuppressWarnings("unchecked")
391+
public CreateIndexRequest source(Map<String, ?> source, DeprecationHandler deprecationHandler, NamedXContentRegistry customsRegistry) {
379392
for (Map.Entry<String, ?> entry : source.entrySet()) {
380393
String name = entry.getKey();
381394
if (SETTINGS.match(name, deprecationHandler)) {
@@ -389,15 +402,20 @@ public CreateIndexRequest source(Map<String, ?> source, DeprecationHandler depre
389402
aliases((Map<String, Object>) entry.getValue());
390403
} else {
391404
// maybe custom?
392-
IndexMetaData.Custom proto = IndexMetaData.lookupPrototype(name);
393-
if (proto != null) {
405+
if (entry.getValue() instanceof Map) {
406+
if (customsRegistry == null) {
407+
// Custom registry wasn't specified - we are in client mode let's try loading it from SPI
408+
customsRegistry = new NamedXContentRegistry(getProvidedNamedXContents());
409+
}
394410
try {
395-
customs.put(name, proto.fromMap((Map<String, Object>) entry.getValue()));
411+
customs.put(name, IndexMetaData.parseCustom(name, (Map<String, Object>) entry.getValue(), deprecationHandler,
412+
customsRegistry));
396413
} catch (IOException e) {
397-
throw new ElasticsearchParseException("failed to parse custom metadata for [{}]", name);
414+
throw new ElasticsearchParseException("failed to parse custom metadata for [{}]", e, name);
415+
} catch (NamedObjectNotFoundException e) {
416+
throw new ElasticsearchParseException("unknown key [{}] for create index", e, name);
398417
}
399418
} else {
400-
// found a key which is neither custom defined nor one of the supported ones
401419
throw new ElasticsearchParseException("unknown key [{}] for create index", name);
402420
}
403421
}
@@ -417,7 +435,7 @@ public Set<Alias> aliases() {
417435
* Adds custom metadata to the index to be created.
418436
*/
419437
public CreateIndexRequest custom(IndexMetaData.Custom custom) {
420-
customs.put(custom.type(), custom);
438+
customs.put(custom.getWriteableName(), custom);
421439
return this;
422440
}
423441

@@ -476,9 +494,8 @@ public void readFrom(StreamInput in) throws IOException {
476494
}
477495
int customSize = in.readVInt();
478496
for (int i = 0; i < customSize; i++) {
479-
String type = in.readString();
480-
IndexMetaData.Custom customIndexMetaData = IndexMetaData.lookupPrototypeSafe(type).readFrom(in);
481-
customs.put(type, customIndexMetaData);
497+
IndexMetaData.Custom customIndexMetaData = in.readNamedWriteable(IndexMetaData.Custom.class);;
498+
customs.put(customIndexMetaData.getWriteableName(), customIndexMetaData);
482499
}
483500
int aliasesSize = in.readVInt();
484501
for (int i = 0; i < aliasesSize; i++) {
@@ -502,9 +519,8 @@ public void writeTo(StreamOutput out) throws IOException {
502519
out.writeString(entry.getValue());
503520
}
504521
out.writeVInt(customs.size());
505-
for (Map.Entry<String, IndexMetaData.Custom> entry : customs.entrySet()) {
506-
out.writeString(entry.getKey());
507-
entry.getValue().writeTo(out);
522+
for (IndexMetaData.Custom custom : customs.values()) {
523+
out.writeNamedWriteable(custom);
508524
}
509525
out.writeVInt(aliases.size());
510526
for (Alias alias : aliases) {
@@ -548,4 +564,15 @@ public XContentBuilder innerToXContent(XContentBuilder builder, Params params) t
548564
}
549565
return builder;
550566
}
567+
568+
/**
569+
* Loads and returns the {@link NamedXContentRegistry.Entry} parsers provided by plugins.
570+
*/
571+
public static List<NamedXContentRegistry.Entry> getProvidedNamedXContents() {
572+
List<NamedXContentRegistry.Entry> entries = new ArrayList<>();
573+
for (NamedXContentProvider service : ServiceLoader.load(NamedXContentProvider.class)) {
574+
entries.addAll(service.getNamedXContentParsers());
575+
}
576+
return entries;
577+
}
551578
}

server/src/main/java/org/elasticsearch/action/admin/indices/create/CreateIndexRequestBuilder.java

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -184,6 +184,14 @@ public CreateIndexRequestBuilder addAlias(Alias alias) {
184184
return this;
185185
}
186186

187+
/**
188+
* Sets custom metadata on index creation
189+
*/
190+
public CreateIndexRequestBuilder setCustom(IndexMetaData.Custom custom) {
191+
request.custom(custom);
192+
return this;
193+
}
194+
187195
/**
188196
* Sets the settings and mappings as a single source.
189197
*/
@@ -224,14 +232,6 @@ public CreateIndexRequestBuilder setSource(Map<String, ?> source) {
224232
return this;
225233
}
226234

227-
/**
228-
* Adds custom metadata to the index to be created.
229-
*/
230-
public CreateIndexRequestBuilder addCustom(IndexMetaData.Custom custom) {
231-
request.custom(custom);
232-
return this;
233-
}
234-
235235
/**
236236
* Sets the settings and mappings as a single source.
237237
*/

server/src/main/java/org/elasticsearch/action/admin/indices/template/put/PutIndexTemplateRequest.java

Lines changed: 33 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@
3939
import org.elasticsearch.common.settings.Settings;
4040
import org.elasticsearch.common.xcontent.DeprecationHandler;
4141
import org.elasticsearch.common.xcontent.LoggingDeprecationHandler;
42+
import org.elasticsearch.common.xcontent.NamedObjectNotFoundException;
4243
import org.elasticsearch.common.xcontent.NamedXContentRegistry;
4344
import org.elasticsearch.common.xcontent.ToXContent;
4445
import org.elasticsearch.common.xcontent.XContentBuilder;
@@ -61,9 +62,10 @@
6162
import java.util.stream.Collectors;
6263

6364
import static org.elasticsearch.action.ValidateActions.addValidationError;
65+
import static org.elasticsearch.action.admin.indices.create.CreateIndexRequest.getProvidedNamedXContents;
66+
import static org.elasticsearch.common.settings.Settings.Builder.EMPTY_SETTINGS;
6467
import static org.elasticsearch.common.settings.Settings.readSettingsFromStream;
6568
import static org.elasticsearch.common.settings.Settings.writeSettingsToStream;
66-
import static org.elasticsearch.common.settings.Settings.Builder.EMPTY_SETTINGS;
6769

6870
/**
6971
* A request to create an index template.
@@ -305,11 +307,16 @@ public PutIndexTemplateRequest source(XContentBuilder templateBuilder) {
305307
}
306308
}
307309

310+
@SuppressWarnings("unchecked")
311+
public PutIndexTemplateRequest source(Map<String, Object> templateSource) {
312+
return source(templateSource, null);
313+
}
314+
308315
/**
309316
* The template source definition.
310317
*/
311318
@SuppressWarnings("unchecked")
312-
public PutIndexTemplateRequest source(Map<String, Object> templateSource) {
319+
public PutIndexTemplateRequest source(Map<String, Object> templateSource, NamedXContentRegistry customsRegistry) {
313320
Map<String, Object> source = templateSource;
314321
for (Map.Entry<String, Object> entry : source.entrySet()) {
315322
String name = entry.getKey();
@@ -354,13 +361,21 @@ public PutIndexTemplateRequest source(Map<String, Object> templateSource) {
354361
aliases((Map<String, Object>) entry.getValue());
355362
} else {
356363
// maybe custom?
357-
IndexMetaData.Custom proto = IndexMetaData.lookupPrototype(name);
358-
if (proto != null) {
364+
if (entry.getValue() instanceof Map) {
365+
if (customsRegistry == null) {
366+
// Custom registry wasn't specified - we are in client mode let's try loading it from SPI
367+
customsRegistry = new NamedXContentRegistry(getProvidedNamedXContents());
368+
}
359369
try {
360-
customs.put(name, proto.fromMap((Map<String, Object>) entry.getValue()));
370+
customs.put(name, IndexMetaData.parseCustom(name, (Map<String, Object>) entry.getValue(),
371+
LoggingDeprecationHandler.INSTANCE, customsRegistry));
361372
} catch (IOException e) {
362-
throw new ElasticsearchParseException("failed to parse custom metadata for [{}]", name);
373+
throw new ElasticsearchParseException("failed to parse custom metadata for [{}]", e, name);
374+
} catch (NamedObjectNotFoundException e) {
375+
throw new ElasticsearchParseException("unknown key [{}] in the template", e, name);
363376
}
377+
} else {
378+
throw new ElasticsearchParseException("unknown key [{}] in the template ", name);
364379
}
365380
}
366381
}
@@ -388,6 +403,13 @@ public PutIndexTemplateRequest source(byte[] source, int offset, int length, XCo
388403
return source(new BytesArray(source, offset, length), xContentType);
389404
}
390405

406+
/**
407+
* The template source definition that should be parsed using specified customs registry.
408+
*/
409+
public PutIndexTemplateRequest source(BytesReference source, XContentType xContentType, NamedXContentRegistry customsRegistry) {
410+
return source(XContentHelper.convertToMap(source, true, xContentType).v2(), customsRegistry);
411+
}
412+
391413
/**
392414
* The template source definition.
393415
*/
@@ -396,7 +418,7 @@ public PutIndexTemplateRequest source(BytesReference source, XContentType xConte
396418
}
397419

398420
public PutIndexTemplateRequest custom(IndexMetaData.Custom custom) {
399-
customs.put(custom.type(), custom);
421+
customs.put(custom.getWriteableName(), custom);
400422
return this;
401423
}
402424

@@ -501,9 +523,8 @@ public void readFrom(StreamInput in) throws IOException {
501523
}
502524
int customSize = in.readVInt();
503525
for (int i = 0; i < customSize; i++) {
504-
String type = in.readString();
505-
IndexMetaData.Custom customIndexMetaData = IndexMetaData.lookupPrototypeSafe(type).readFrom(in);
506-
customs.put(type, customIndexMetaData);
526+
IndexMetaData.Custom customIndexMetaData = in.readNamedWriteable(IndexMetaData.Custom.class);
527+
customs.put(customIndexMetaData.getWriteableName(), customIndexMetaData);
507528
}
508529
int aliasesSize = in.readVInt();
509530
for (int i = 0; i < aliasesSize; i++) {
@@ -531,9 +552,8 @@ public void writeTo(StreamOutput out) throws IOException {
531552
out.writeString(entry.getValue());
532553
}
533554
out.writeVInt(customs.size());
534-
for (Map.Entry<String, IndexMetaData.Custom> entry : customs.entrySet()) {
535-
out.writeString(entry.getKey());
536-
entry.getValue().writeTo(out);
555+
for (IndexMetaData.Custom custom : customs.values()) {
556+
out.writeNamedWriteable(custom);
537557
}
538558
out.writeVInt(aliases.size());
539559
for (Alias alias : aliases) {

server/src/main/java/org/elasticsearch/action/admin/indices/template/put/PutIndexTemplateRequestBuilder.java

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
import org.elasticsearch.action.admin.indices.alias.Alias;
2222
import org.elasticsearch.action.support.master.MasterNodeOperationRequestBuilder;
2323
import org.elasticsearch.client.ElasticsearchClient;
24+
import org.elasticsearch.cluster.metadata.IndexMetaData;
2425
import org.elasticsearch.common.bytes.BytesReference;
2526
import org.elasticsearch.common.settings.Settings;
2627
import org.elasticsearch.common.xcontent.XContentBuilder;
@@ -210,6 +211,16 @@ public PutIndexTemplateRequestBuilder addMapping(String type, Map<String, Object
210211
return this;
211212
}
212213

214+
/**
215+
* Sets custom metadata object.
216+
*
217+
* @param custom The custom index metadata object
218+
*/
219+
public PutIndexTemplateRequestBuilder setCustom(IndexMetaData.Custom custom) {
220+
request.custom(custom);
221+
return this;
222+
}
223+
213224
/**
214225
* The template source definition.
215226
*/

0 commit comments

Comments
 (0)