Skip to content

Commit

Permalink
Support trial licenses inside enterprise_trial orchestration licenses (
Browse files Browse the repository at this point in the history
  • Loading branch information
pebrc authored Dec 15, 2021
1 parent 77be8f6 commit 3016db4
Show file tree
Hide file tree
Showing 5 changed files with 39 additions and 18 deletions.
5 changes: 2 additions & 3 deletions pkg/controller/common/license/match_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -225,14 +225,13 @@ func Test_bestMatchAt(t *testing.T) {
Type: LicenseTypeEnterpriseTrial,
Issuer: "API",
ClusterLicenses: []ElasticsearchLicense{
{License: license(twelveMonth, platinum)},
{License: license(twoMonth, gold)},
{License: license(twelveMonth, trial)},
},
},
},
},
},
want: license(twelveMonth, platinum),
want: license(twelveMonth, trial),
wantFound: true,
},
{
Expand Down
10 changes: 9 additions & 1 deletion pkg/controller/elasticsearch/license/apply.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,13 @@ func isTrial(l esclient.License) bool {
return l.Type == string(esclient.ElasticsearchLicenseTypeTrial)
}

// isECKManagedTrial returns true if this is a trial started via the internal trial mechanism in the operator. We use an
// empty license with only the type field populated to indicate to the Elasticsearch controller that a self-generated
// trial in Elasticsearch should be started. This can be done only once.
func isECKManagedTrial(l esclient.License) bool {
return isTrial(l) && l.Signature == "" && l.UID == "" && l.ExpiryDateInMillis == 0 && l.StartDateInMillis == 0
}

// isBasic returns true if an Elasticsearch license is of the basic type
func isBasic(l esclient.License) bool {
return l.Type == string(esclient.ElasticsearchLicenseTypeBasic)
Expand Down Expand Up @@ -117,7 +124,8 @@ func updateLicense(
},
}

if isTrial(desired) {
if isECKManagedTrial(desired) {
// start a self-generated trial in Elasticsearch, this can only be done once.
return pkgerrors.Wrap(startTrial(ctx, updater, esCluster), "failed to start trial")
}

Expand Down
11 changes: 5 additions & 6 deletions test/e2e/es/license_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -165,20 +165,19 @@ func TestEnterpriseTrialExtension(t *testing.T) {
licenseTestContext.Init(),
licenseTestContext.CheckElasticsearchLicense(client.ElasticsearchLicenseTypeTrial),
licenseTestContext.CheckEnterpriseTrialLicenseValid(trialSecretName),
// simulate a trial extension
licenseTestContext.CreateTrialExtension(licenseSecretName, privateKey.(*rsa.PrivateKey)),
// simulate a trial extension: old style with Enterprise Elasticsearch license
licenseTestContext.CreateTrialExtension(licenseSecretName, privateKey.(*rsa.PrivateKey), client.ElasticsearchLicenseTypeEnterprise),
licenseTestContext.CheckElasticsearchLicense(
client.ElasticsearchLicenseTypePlatinum, // depends on ES version
client.ElasticsearchLicenseTypeEnterprise,
),
// revert to basic again
licenseTestContext.DeleteAllEnterpriseLicenseSecrets(),
licenseTestContext.CheckElasticsearchLicense(client.ElasticsearchLicenseTypeBasic),
// repeatedly extending a trial is possible
licenseTestContext.CreateTrialExtension(licenseSecretName, privateKey.(*rsa.PrivateKey)),
// repeatedly extending a trial is possible: new style with Elasticsearch trial license
licenseTestContext.CreateTrialExtension(licenseSecretName, privateKey.(*rsa.PrivateKey), client.ElasticsearchLicenseTypeTrial),
licenseTestContext.CheckElasticsearchLicense(
client.ElasticsearchLicenseTypePlatinum, // depends on ES version
client.ElasticsearchLicenseTypeEnterprise,
client.ElasticsearchLicenseTypeTrial,
),
// cleanup license for the next tests
licenseTestContext.DeleteAllEnterpriseLicenseSecrets(),
Expand Down
27 changes: 21 additions & 6 deletions test/e2e/test/elasticsearch/license_fixture.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,40 +32,55 @@ type licenseSpec struct {
}

func (e ESLicense) SignableContentBytes() ([]byte, error) {
return json.Marshal(licenseSpec{
spec := licenseSpec{
UID: e.UID,
LicenseType: e.Type,
IssueDateInMillis: e.IssueDateInMillis,
ExpiryDateInMillis: e.ExpiryDateInMillis,
MaxNodes: nil, // assume v5 license w/ ERU
MaxNodes: &e.MaxNodes,
MaxResourceUnits: e.MaxResourceUnits,
IssuedTo: e.IssuedTo,
Issuer: e.Issuer,
StartDateInMillis: e.StartDateInMillis,
})
}

// v3 and v5 are handling maxNodes differently: v3 requires max_nodes v5 does not tolerate any other value than null
if e.MaxNodes == 0 {
spec.MaxNodes = nil
}

return json.Marshal(spec)
}

func (e ESLicense) Version() int {
return 5 // we only test the new enterprise capable license version
if e.Type == string(client.ElasticsearchLicenseTypeTrial) {
return 3 // we either test trials
}
return 5 // or the new enterprise capable license version
}

var _ license.Signable = &ESLicense{}

func GenerateTestLicense(signer *license.Signer) (client.License, error) {
func GenerateTestLicense(signer *license.Signer, typ client.ElasticsearchLicenseType) (client.License, error) {
uuid, err := uuid.NewUUID()
if err != nil {
return client.License{}, err
}
licenseSpec := client.License{
UID: uuid.String(),
Type: "enterprise",
Type: string(typ),
IssueDateInMillis: chrono.ToMillis(time.Now().Add(-3 * 24 * time.Hour)),
ExpiryDateInMillis: chrono.ToMillis(time.Now().Add(30 * 24 * time.Hour)),
MaxResourceUnits: 100,
IssuedTo: "ECK CI",
Issuer: "ECK e2e job",
StartDateInMillis: chrono.ToMillis(time.Now().Add(-3 * 24 * time.Hour)),
}
if typ == client.ElasticsearchLicenseTypeTrial {
licenseSpec.MaxResourceUnits = 0
licenseSpec.MaxNodes = 100
}

sign, err := signer.Sign(ESLicense{License: licenseSpec})
if err != nil {
return client.License{}, err
Expand Down
4 changes: 2 additions & 2 deletions test/e2e/test/elasticsearch/steps_license.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,13 +84,13 @@ func (ltctx *LicenseTestContext) CreateEnterpriseLicenseSecret(secretName string
}
}

func (ltctx *LicenseTestContext) CreateTrialExtension(secretName string, privateKey *rsa.PrivateKey) test.Step {
func (ltctx *LicenseTestContext) CreateTrialExtension(secretName string, privateKey *rsa.PrivateKey, esLicenseType client.ElasticsearchLicenseType) test.Step {
//nolint:thelper
return test.Step{
Name: "Creating a trial extension secret",
Test: func(t *testing.T) {
signer := license.NewSigner(privateKey)
clusterLicense, err := GenerateTestLicense(signer)
clusterLicense, err := GenerateTestLicense(signer, esLicenseType)
require.NoError(t, err)
trialExtension := license.EnterpriseLicense{
License: license.LicenseSpec{
Expand Down

0 comments on commit 3016db4

Please sign in to comment.