From b4364723ef35a2a8cfd1c23438a05c81134cdbbf Mon Sep 17 00:00:00 2001 From: Shireesh Anjal <355479+anjalshireesh@users.noreply.github.com> Date: Wed, 15 Sep 2021 10:24:25 +0530 Subject: [PATCH] Add config to store subnet license (#13194) Command to set subnet license: `mc admin config set {alias} subnet license={token}` Signed-off-by: Shireesh Anjal Co-authored-by: Harshavardhana --- cmd/common-main.go | 6 +-- cmd/config-current.go | 14 ++++++ cmd/globals.go | 5 ++- internal/config/config.go | 4 ++ internal/config/subnet/license.go | 71 +++++++++++++++++++++++++++++++ 5 files changed, 94 insertions(+), 6 deletions(-) create mode 100644 internal/config/subnet/license.go diff --git a/cmd/common-main.go b/cmd/common-main.go index 156c7cf19..54d9687b9 100644 --- a/cmd/common-main.go +++ b/cmd/common-main.go @@ -155,8 +155,8 @@ func minioConfigToConsoleFeatures() { } os.Setenv("CONSOLE_MINIO_REGION", globalServerRegion) os.Setenv("CONSOLE_CERT_PASSWD", env.Get("MINIO_CERT_PASSWD", "")) - if globalSubnetLicense != "" { - os.Setenv("CONSOLE_SUBNET_LICENSE", globalSubnetLicense) + if globalSubnetConfig.License != "" { + os.Setenv("CONSOLE_SUBNET_LICENSE", globalSubnetConfig.License) } } @@ -602,8 +602,6 @@ func handleCommonEnvVars() { if tiers := env.Get("_MINIO_DEBUG_REMOTE_TIERS_IMMEDIATELY", ""); tiers != "" { globalDebugRemoteTiersImmediately = strings.Split(tiers, ",") } - - globalSubnetLicense = env.Get(config.EnvMinIOSubnetLicense, "") } func logStartupMessage(msg string) { diff --git a/cmd/config-current.go b/cmd/config-current.go index 0e4698d67..7a1dd8ae9 100644 --- a/cmd/config-current.go +++ b/cmd/config-current.go @@ -39,6 +39,7 @@ import ( "github.com/minio/minio/internal/config/policy/opa" "github.com/minio/minio/internal/config/scanner" "github.com/minio/minio/internal/config/storageclass" + "github.com/minio/minio/internal/config/subnet" "github.com/minio/minio/internal/crypto" xhttp "github.com/minio/minio/internal/http" "github.com/minio/minio/internal/kms" @@ -65,6 +66,7 @@ func initHelp() { config.AuditKafkaSubSys: logger.DefaultAuditKafkaKVS, config.HealSubSys: heal.DefaultKVS, config.ScannerSubSys: scanner.DefaultKVS, + config.SubnetSubSys: subnet.DefaultKVS, } for k, v := range notify.DefaultNotificationKVS { kvs[k] = v @@ -185,6 +187,12 @@ func initHelp() { Description: "publish bucket notifications to Redis datastores", MultipleTargets: true, }, + config.HelpKV{ + Key: config.SubnetSubSys, + Type: "string", + Description: "set subnet config for the cluster e.g. license token", + Optional: true, + }, } if globalIsErasure { @@ -223,6 +231,7 @@ func initHelp() { config.NotifyRedisSubSys: notify.HelpRedis, config.NotifyWebhookSubSys: notify.HelpWebhook, config.NotifyESSubSys: notify.HelpES, + config.SubnetSubSys: subnet.HelpLicense, } config.RegisterHelpSubSys(helpMap) @@ -508,6 +517,11 @@ func lookupConfigs(s config.Config, objAPI ObjectLayer) { logger.LogIf(ctx, fmt.Errorf("Unable to parse LDAP configuration: %w", err)) } + globalSubnetConfig, err = subnet.LookupConfig(s[config.SubnetSubSys][config.Default]) + if err != nil { + logger.LogIf(ctx, fmt.Errorf("Unable to parse subnet configuration: %w", err)) + } + // Load logger targets based on user's configuration loggerUserAgent := getUserAgent(getMinioMode()) diff --git a/cmd/globals.go b/cmd/globals.go index 6a83b93fd..9618a1672 100644 --- a/cmd/globals.go +++ b/cmd/globals.go @@ -41,6 +41,7 @@ import ( xtls "github.com/minio/minio/internal/config/identity/tls" "github.com/minio/minio/internal/config/policy/opa" "github.com/minio/minio/internal/config/storageclass" + "github.com/minio/minio/internal/config/subnet" xhttp "github.com/minio/minio/internal/http" etcd "go.etcd.io/etcd/client/v3" @@ -219,8 +220,8 @@ var ( // The name of this local node, fetched from arguments globalLocalNodeName string - // The global subnet license - globalSubnetLicense string + // The global subnet config + globalSubnetConfig subnet.Config globalRemoteEndpoints map[string]Endpoint diff --git a/internal/config/config.go b/internal/config/config.go index 736719fa2..3d95acc3d 100644 --- a/internal/config/config.go +++ b/internal/config/config.go @@ -58,6 +58,7 @@ const ( RegionName = "name" AccessKey = "access_key" SecretKey = "secret_key" + License = "license" ) // Top level config constants. @@ -79,6 +80,7 @@ const ( HealSubSys = "heal" ScannerSubSys = "scanner" CrawlerSubSys = "crawler" + SubnetSubSys = "subnet" // Add new constants here if you add new fields to config. ) @@ -127,6 +129,7 @@ var SubSystems = set.CreateStringSet( NotifyPostgresSubSys, NotifyRedisSubSys, NotifyWebhookSubSys, + SubnetSubSys, ) // SubSystemsDynamic - all sub-systems that have dynamic config. @@ -135,6 +138,7 @@ var SubSystemsDynamic = set.CreateStringSet( CompressionSubSys, ScannerSubSys, HealSubSys, + SubnetSubSys, ) // SubSystemsSingleTargets - subsystems which only support single target. diff --git a/internal/config/subnet/license.go b/internal/config/subnet/license.go new file mode 100644 index 000000000..377f73ad2 --- /dev/null +++ b/internal/config/subnet/license.go @@ -0,0 +1,71 @@ +// Copyright (c) 2015-2021 MinIO, Inc. +// +// This file is part of MinIO Object Storage stack +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU Affero General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Affero General Public License for more details. +// +// You should have received a copy of the GNU Affero General Public License +// along with this program. If not, see . + +package subnet + +import ( + jwtgo "github.com/golang-jwt/jwt" + "github.com/minio/minio/internal/config" + "github.com/minio/pkg/env" +) + +var ( + // DefaultKVS - default KV config for subnet settings + DefaultKVS = config.KVS{ + config.KV{ + Key: config.License, + Value: "", + }, + } + + // HelpLicense - provides help for license config + HelpLicense = config.HelpKVS{ + config.HelpKV{ + Key: config.License, + Type: "string", + Description: "Subnet license token for the cluster", + Optional: true, + }, + } +) + +// Config represents the subnet related configuration +type Config struct { + // The subnet license token + License string `json:"license"` +} + +func validateLicenseFormat(lic string) error { + if len(lic) == 0 { + return nil + } + + // Only verifying that the string is a parseable JWT token as of now + _, _, err := new(jwtgo.Parser).ParseUnverified(lic, jwtgo.MapClaims{}) + return err +} + +// LookupConfig - lookup config and override with valid environment settings if any. +func LookupConfig(kvs config.KVS) (cfg Config, err error) { + if err = config.CheckValidKeys(config.SubnetSubSys, kvs, DefaultKVS); err != nil { + return cfg, err + } + + cfg.License = env.Get(config.EnvMinIOSubnetLicense, kvs.Get(config.License)) + + return cfg, validateLicenseFormat(cfg.License) +}