Skip to content

Commit

Permalink
[Rest Api Compatibility] Licence accept_enterprise and response chang…
Browse files Browse the repository at this point in the history
…es (elastic#75479)

in elastic#50067 for _license the accept_enterprise = false was no longer supported. This
commit allows it under rest compatibility and is showing enterprise licenses as platinum
The same change had to be applied to _xpack endpoint elastic#58217

in elastic#50735 max_resource_units was introduced to be more accurate. For v7 requests, which do not know about enterprise license we will return max_node which will be set from max_resource_units (it assumes that one resource unit is 32GB - which corresponds to 1 node)

relates elastic#51816
  • Loading branch information
pgomulka authored and ywangd committed Jul 30, 2021
1 parent d3a9d7d commit 4b818e5
Show file tree
Hide file tree
Showing 6 changed files with 68 additions and 26 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
import org.gradle.api.tasks.Optional;

/**
* A transformation to replace a key/value combination.
* A transformation to replace a key/value combination.
*/
public class ReplaceTextual implements RestTestTransformByParentObject {
private final String keyToReplaceName;
Expand Down
30 changes: 14 additions & 16 deletions x-pack/plugin/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -139,19 +139,7 @@ def v7compatibilityNotSupportedTests = {
'ml/datafeeds_crud/Test update datafeed to point to missing job',
'ml/datafeeds_crud/Test update datafeed to point to different job',
'ml/datafeeds_crud/Test update datafeed to point to job already attached to another datafeed',
]
}

tasks.named("yamlRestCompatTest").configure {
/*
* We have to disable setting the number of available processors as tests in the same JVM randomize processors and will step on each
* other if we allow them to set the number of available processors as it's set-once in Netty.
*/
systemProperty 'es.set.netty.runtime.available.processors', 'false'

//TODO: blacklist specific to REST API compatibility
restTestBlacklist.addAll([
'license/30_enterprise_license/Installing enterprise license',
//rollup was an experimental feature
//https://github.com/elastic/elasticsearch/pull/41227.
'rollup/delete_job/Test basic delete_job',
'rollup/delete_job/Test delete job twice',
Expand All @@ -160,12 +148,21 @@ tasks.named("yamlRestCompatTest").configure {
'rollup/put_job/Test basic put_job',
//https://github.com/elastic/elasticsearch/pull/41502
'rollup/start_job/Test start job twice',
// a type field was added to cat.ml_trained_models #73660, this might need some work

// a type field was added to cat.ml_trained_models #73660, this is a backwards compatible change.
// still this is a cat api, and we don't support them with rest api compatibility. (the test would be very hard to transform too)
'ml/trained_model_cat_apis/Test cat trained models'
] + v7compatibilityNotSupportedTests())
]
}

tasks.named("yamlRestCompatTest").configure {
/*
* We have to disable setting the number of available processors as tests in the same JVM randomize processors and will step on each
* other if we allow them to set the number of available processors as it's set-once in Netty.
*/
systemProperty 'es.set.netty.runtime.available.processors', 'false'

systemProperty 'tests.rest.blacklist', restTestBlacklist.join(',')
systemProperty 'tests.rest.blacklist', v7compatibilityNotSupportedTests().join(',')
dependsOn "copyExtraResources"
}

Expand Down Expand Up @@ -220,4 +217,5 @@ tasks.named("precommit").configure {
tasks.named("transformV7RestTests").configure({ task ->
task.replaceValueInMatch("_type", "_doc")
task.addAllowedWarningRegex("\\[types removal\\].*")
task.addAllowedWarningRegexForTest("Including \\[accept_enterprise\\] in get license.*", "Installing enterprise license")
})
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
import org.elasticsearch.common.xcontent.XContentFactory;
import org.elasticsearch.common.xcontent.XContentParser;
import org.elasticsearch.common.xcontent.XContentType;
import org.elasticsearch.core.RestApiVersion;
import org.elasticsearch.protocol.xpack.license.LicenseStatus;

import java.io.IOException;
Expand Down Expand Up @@ -146,6 +147,12 @@ static boolean isEnterprise(String typeName) {
* to a specific license version
*/
public static final String LICENSE_VERSION_MODE = "license_version";
/**
* Set for {@link RestApiVersion#V_7} requests only
* XContent param name to map the "enterprise" license type to "platinum"
* for backwards compatibility with older clients
*/
public static final String XCONTENT_HIDE_ENTERPRISE = "hide_enterprise";

public static final Comparator<License> LATEST_ISSUE_DATE_FIRST = Comparator.comparing(License::issueDate).reversed();

Expand Down Expand Up @@ -516,6 +523,8 @@ public XContentBuilder toXContent(XContentBuilder builder, Params params) throws
public XContentBuilder toInnerXContent(XContentBuilder builder, Params params) throws IOException {
boolean licenseSpecMode = params.paramAsBoolean(LICENSE_SPEC_VIEW_MODE, false);
boolean restViewMode = params.paramAsBoolean(REST_VIEW_MODE, false);
boolean hideEnterprise = params.paramAsBoolean(XCONTENT_HIDE_ENTERPRISE, false);

boolean previouslyHumanReadable = builder.humanReadable();
if (licenseSpecMode && restViewMode) {
throw new IllegalArgumentException("can have either " + REST_VIEW_MODE + " or " + LICENSE_SPEC_VIEW_MODE);
Expand All @@ -534,7 +543,8 @@ public XContentBuilder toInnerXContent(XContentBuilder builder, Params params) t
builder.field(Fields.STATUS, status().label());
}
builder.field(Fields.UID, uid);
builder.field(Fields.TYPE, type);
final String bwcType = hideEnterprise && LicenseType.isEnterprise(type) ? LicenseType.PLATINUM.getTypeName() : type;
builder.field(Fields.TYPE, bwcType);
if (version == VERSION_START) {
builder.field(Fields.SUBSCRIPTION_TYPE, subscriptionType);
}
Expand All @@ -550,6 +560,8 @@ public XContentBuilder toInnerXContent(XContentBuilder builder, Params params) t
if (version >= VERSION_ENTERPRISE) {
builder.field(Fields.MAX_NODES, maxNodes == -1 ? null : maxNodes);
builder.field(Fields.MAX_RESOURCE_UNITS, maxResourceUnits == -1 ? null : maxResourceUnits);
} else if (hideEnterprise && maxNodes == -1) {
builder.field(Fields.MAX_NODES, maxResourceUnits);
} else {
builder.field(Fields.MAX_NODES, maxNodes);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,9 @@
import java.util.List;
import java.util.Map;

import static org.elasticsearch.core.RestApiVersion.V_7;
import static org.elasticsearch.core.RestApiVersion.V_8;
import static org.elasticsearch.core.RestApiVersion.onOrAfter;
import static org.elasticsearch.rest.RestRequest.Method.GET;
import static org.elasticsearch.rest.RestStatus.NOT_FOUND;
import static org.elasticsearch.rest.RestStatus.OK;
Expand Down Expand Up @@ -60,13 +63,21 @@ public RestChannelConsumer prepareRequest(final RestRequest request, final NodeC
overrideParams.put(License.REST_VIEW_MODE, "true");
overrideParams.put(License.LICENSE_VERSION_MODE, String.valueOf(License.VERSION_CURRENT));

if (request.getRestApiVersion() == V_7) {
// Hide enterprise licenses by default, there is an opt-in flag to show them
final boolean hideEnterprise = request.paramAsBoolean("accept_enterprise", false) == false;
final int licenseVersion = hideEnterprise ? License.VERSION_CRYPTO_ALGORITHMS : License.VERSION_CURRENT;
overrideParams.put(License.LICENSE_VERSION_MODE, String.valueOf(licenseVersion));
overrideParams.put(License.XCONTENT_HIDE_ENTERPRISE, String.valueOf(hideEnterprise));
}
// In 7.x, there was an opt-in flag to show "enterprise" licenses. In 8.0 the flag is deprecated and can only be true
// TODO Remove this from 9.0
if (request.hasParam("accept_enterprise")) {
deprecationLogger.deprecate(DeprecationCategory.API, "get_license_accept_enterprise",
"Including [accept_enterprise] in get license requests is deprecated." +
" The parameter will be removed in the next major version");
if (request.paramAsBoolean("accept_enterprise", true) == false) {
" The parameter will be removed in the next major version");
if (request.paramAsBoolean("accept_enterprise", true) == false
&& request.getRestApiVersion().matches(onOrAfter(V_8))) {
throw new IllegalArgumentException("The [accept_enterprise] parameters may not be false");
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@
import org.elasticsearch.common.xcontent.ConstructingObjectParser;
import org.elasticsearch.common.xcontent.ToXContentObject;
import org.elasticsearch.common.xcontent.XContentBuilder;
import org.elasticsearch.core.RestApiVersion;
import org.elasticsearch.license.License;
import org.elasticsearch.protocol.xpack.license.LicenseStatus;

import java.io.IOException;
Expand Down Expand Up @@ -203,11 +205,27 @@ public int hashCode() {

@Override
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
builder.startObject()
.field("uid", uid)
.field("type", type)
.field("mode", mode)
.field("status", status.label());
builder.startObject();
builder.field("uid", uid);

if (builder.getRestApiVersion() == RestApiVersion.V_7 && params.paramAsBoolean("accept_enterprise", false) == false) {
if (License.LicenseType.ENTERPRISE.getTypeName().equals(type)) {
builder.field("type", License.LicenseType.PLATINUM.getTypeName());
} else {
builder.field("type", type);
}

if (License.OperationMode.ENTERPRISE.description().equals(mode)) {
builder.field("mode", License.OperationMode.PLATINUM.description());
} else {
builder.field("mode", mode);
}
} else {
builder.field("type", type);
builder.field("mode", mode);
}

builder.field("status", status.label());
if (expiryDate != BASIC_SELF_GENERATED_LICENSE_EXPIRATION_MILLIS) {
builder.timeField("expiry_date_in_millis", "expiry_date", expiryDate);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
import org.elasticsearch.client.node.NodeClient;
import org.elasticsearch.common.logging.DeprecationCategory;
import org.elasticsearch.common.logging.DeprecationLogger;
import org.elasticsearch.core.RestApiVersion;
import org.elasticsearch.protocol.xpack.XPackInfoRequest;
import org.elasticsearch.rest.BaseRestHandler;
import org.elasticsearch.rest.RestRequest;
Expand All @@ -19,6 +20,7 @@
import java.util.EnumSet;
import java.util.List;

import static org.elasticsearch.core.RestApiVersion.onOrAfter;
import static org.elasticsearch.rest.RestRequest.Method.GET;
import static org.elasticsearch.rest.RestRequest.Method.HEAD;

Expand Down Expand Up @@ -50,7 +52,8 @@ public RestChannelConsumer prepareRequest(RestRequest request, NodeClient client
deprecationLogger.deprecate(DeprecationCategory.API, "get_license_accept_enterprise",
"Including [accept_enterprise] in get license requests is deprecated." +
" The parameter will be removed in the next major version");
if (request.paramAsBoolean("accept_enterprise", true) == false) {
if (request.paramAsBoolean("accept_enterprise", true) == false
&& request.getRestApiVersion().matches(onOrAfter(RestApiVersion.V_8))) {
throw new IllegalArgumentException("The [accept_enterprise] parameters may not be false");
}
}
Expand Down

0 comments on commit 4b818e5

Please sign in to comment.