Support to store browser config settings (#18631)

* csp_policy
* hsts_seconds
* hsts_include_subdomains
* hsts_preload
* referrer_policy
This commit is contained in:
Pedro Juarez
2024-01-01 08:36:33 -08:00
committed by GitHub
parent c1cae51fb5
commit 8f13c8c3bf
7 changed files with 268 additions and 1 deletions

View File

@@ -0,0 +1,164 @@
// Copyright (c) 2015-2023 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 <http://www.gnu.org/licenses/>.
package browser
import (
"fmt"
"strconv"
"sync"
"github.com/minio/minio/internal/config"
"github.com/minio/pkg/v2/env"
)
// Browser sub-system constants
const (
// browserCSPPolicy setting name for Content-Security-Policy response header value
browserCSPPolicy = "csp_policy"
// browserHSTSSeconds setting name for Strict-Transport-Security response header, amount of seconds for 'max-age'
browserHSTSSeconds = "hsts_seconds"
// browserHSTSIncludeSubdomains setting name for Strict-Transport-Security response header 'includeSubDomains' flag (true or false)
browserHSTSIncludeSubdomains = "hsts_include_subdomains"
// browserHSTSPreload setting name for Strict-Transport-Security response header 'preload' flag (true or false)
browserHSTSPreload = "hsts_preload"
// browserReferrerPolicy setting name for Referrer-Policy response header
browserReferrerPolicy = "referrer_policy"
EnvBrowserCSPPolicy = "MINIO_BROWSER_CONTENT_SECURITY_POLICY"
EnvBrowserHSTSSeconds = "MINIO_BROWSER_HSTS_SECONDS"
EnvBrowserHSTSIncludeSubdomains = "MINIO_BROWSER_HSTS_INCLUDE_SUB_DOMAINS"
EnvBrowserHSTSPreload = "MINIO_BROWSER_HSTS_PRELOAD"
EnvBrowserReferrerPolicy = "MINIO_BROWSER_REFERRER_POLICY"
)
// DefaultKVS - default storage class config
var (
DefaultKVS = config.KVS{
config.KV{
Key: browserCSPPolicy,
Value: "default-src 'self' 'unsafe-eval' 'unsafe-inline';",
},
config.KV{
Key: browserHSTSSeconds,
Value: "0",
},
config.KV{
Key: browserHSTSIncludeSubdomains,
Value: config.EnableOff,
},
config.KV{
Key: browserHSTSPreload,
Value: config.EnableOff,
},
config.KV{
Key: browserReferrerPolicy,
Value: "strict-origin-when-cross-origin",
},
}
)
// configLock is a global lock for browser config
var configLock sync.RWMutex
// Config storage class configuration
type Config struct {
CSPPolicy string `json:"csp_policy"`
HSTSSeconds int `json:"hsts_seconds"`
HSTSIncludeSubdomains bool `json:"hsts_include_subdomains"`
HSTSPreload bool `json:"hsts_preload"`
ReferrerPolicy string `json:"referrer_policy"`
}
// Update Updates browser with new config
func (browseCfg *Config) Update(newCfg Config) {
configLock.Lock()
defer configLock.Unlock()
browseCfg.CSPPolicy = newCfg.CSPPolicy
browseCfg.HSTSSeconds = newCfg.HSTSSeconds
browseCfg.HSTSIncludeSubdomains = newCfg.HSTSIncludeSubdomains
browseCfg.HSTSPreload = newCfg.HSTSPreload
browseCfg.ReferrerPolicy = newCfg.ReferrerPolicy
}
// LookupConfig - lookup api config and override with valid environment settings if any.
func LookupConfig(kvs config.KVS) (cfg Config, err error) {
cspPolicy := env.Get(EnvBrowserCSPPolicy, kvs.GetWithDefault(browserCSPPolicy, DefaultKVS))
hstsSeconds, err := strconv.Atoi(env.Get(EnvBrowserHSTSSeconds, kvs.GetWithDefault(browserHSTSSeconds, DefaultKVS)))
if err != nil {
return cfg, err
}
hstsIncludeSubdomains := env.Get(EnvBrowserHSTSIncludeSubdomains, kvs.GetWithDefault(browserHSTSIncludeSubdomains, DefaultKVS)) == config.EnableOn
hstsPreload := env.Get(EnvBrowserHSTSPreload, kvs.Get(browserHSTSPreload)) == config.EnableOn
referrerPolicy := env.Get(EnvBrowserReferrerPolicy, kvs.GetWithDefault(browserReferrerPolicy, DefaultKVS))
switch referrerPolicy {
case "no-referrer", "no-referrer-when-downgrade", "origin", "origin-when-cross-origin", "same-origin", "strict-origin", "strict-origin-when-cross-origin", "unsafe-url":
cfg.ReferrerPolicy = referrerPolicy
default:
return cfg, fmt.Errorf("invalid value %v for %s", referrerPolicy, browserReferrerPolicy)
}
cfg.CSPPolicy = cspPolicy
cfg.HSTSSeconds = hstsSeconds
cfg.HSTSIncludeSubdomains = hstsIncludeSubdomains
cfg.HSTSPreload = hstsPreload
return cfg, nil
}
// GetCSPolicy - Get the Content security Policy
func (browseCfg *Config) GetCSPolicy() string {
configLock.RLock()
defer configLock.RUnlock()
return browseCfg.CSPPolicy
}
// GetHSTSSeconds - Get the Content security Policy
func (browseCfg *Config) GetHSTSSeconds() int {
configLock.RLock()
defer configLock.RUnlock()
return browseCfg.HSTSSeconds
}
// IsHSTSIncludeSubdomains - is HSTS 'includeSubdomains' directive enabled
func (browseCfg *Config) IsHSTSIncludeSubdomains() string {
configLock.RLock()
defer configLock.RUnlock()
if browseCfg.HSTSSeconds > 0 && browseCfg.HSTSIncludeSubdomains {
return config.EnableOn
}
return config.EnableOff
}
// IsHSTSPreload - is HSTS 'preload' directive enabled
func (browseCfg *Config) IsHSTSPreload() string {
configLock.RLock()
defer configLock.RUnlock()
if browseCfg.HSTSSeconds > 0 && browseCfg.HSTSPreload {
return config.EnableOn
}
return config.EnableOff
}
// GetReferPolicy - Get the ReferPolicy
func (browseCfg *Config) GetReferPolicy() string {
configLock.RLock()
defer configLock.RUnlock()
return browseCfg.ReferrerPolicy
}

View File

@@ -0,0 +1,60 @@
// Copyright (c) 2015-2023 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 <http://www.gnu.org/licenses/>.
package browser
import "github.com/minio/minio/internal/config"
// Help template for browser feature.
var (
defaultHelpPostfix = func(key string) string {
return config.DefaultHelpPostfix(DefaultKVS, key)
}
Help = config.HelpKVS{
config.HelpKV{
Key: browserCSPPolicy,
Description: `set Content-Security-Policy response header value` + defaultHelpPostfix(browserCSPPolicy),
Optional: true,
Type: "string",
},
config.HelpKV{
Key: browserHSTSSeconds,
Description: `set Strict-Transport-Security 'max-age' amount of seconds value` + defaultHelpPostfix(browserHSTSSeconds),
Optional: true,
Type: "number",
},
config.HelpKV{
Key: browserHSTSIncludeSubdomains,
Description: `turn 'on' to set Strict-Transport-Security 'includeSubDomains' directive` + defaultHelpPostfix(browserHSTSIncludeSubdomains),
Optional: true,
Type: "boolean",
},
config.HelpKV{
Key: browserHSTSPreload,
Description: `turn 'on' to set Strict-Transport-Security 'preload' directive` + defaultHelpPostfix(browserHSTSPreload),
Optional: true,
Type: "boolean",
},
config.HelpKV{
Key: browserReferrerPolicy,
Description: `set Referrer-Policy response header value` + defaultHelpPostfix(browserReferrerPolicy),
Optional: true,
Type: "string",
},
}
)

View File

@@ -119,6 +119,7 @@ const (
CallhomeSubSys = madmin.CallhomeSubSys
DriveSubSys = madmin.DriveSubSys
BatchSubSys = madmin.BatchSubSys
BrowserSubSys = madmin.BrowserSubSys
// Add new constants here (similar to above) if you add new fields to config.
)
@@ -188,6 +189,7 @@ var SubSystemsDynamic = set.CreateStringSet(
StorageClassSubSys,
CacheSubSys,
BatchSubSys,
BrowserSubSys,
)
// SubSystemsSingleTargets - subsystems which only support single target.
@@ -209,8 +211,8 @@ var SubSystemsSingleTargets = set.CreateStringSet(
SubnetSubSys,
CallhomeSubSys,
DriveSubSys,
CacheSubSys,
BatchSubSys,
BrowserSubSys,
)
// Constant separators

View File

@@ -82,6 +82,7 @@ const (
EnvWorm = "MINIO_WORM" // legacy
EnvRegion = "MINIO_REGION" // legacy
EnvRegionName = "MINIO_REGION_NAME" // legacy
)
// Expiration Token durations