@ -26,17 +26,21 @@ import (
"github.com/tidwall/gjson"
"github.com/tidwall/gjson"
)
)
// Read Write mutex for safe access to ServerConfig.
var serverConfigMu sync . RWMutex
// Config version
// Config version
const v17 = "17"
const v17 = "17"
var (
// serverConfig server config.
serverConfig * serverConfigV17
serverConfigMu sync . RWMutex
)
// serverConfigV17 server configuration version '17' which is like
// serverConfigV17 server configuration version '17' which is like
// version '16' except it adds support for "format" parameter in
// version '16' except it adds support for "format" parameter in
// database event notification targets: PostgreSQL, MySQL, Redis and
// database event notification targets: PostgreSQL, MySQL, Redis and
// Elasticsearch.
// Elasticsearch.
type serverConfigV17 struct {
type serverConfigV17 struct {
sync . RWMutex
Version string ` json:"version" `
Version string ` json:"version" `
// S3 API configuration.
// S3 API configuration.
@ -51,6 +55,73 @@ type serverConfigV17 struct {
Notify * notifier ` json:"notify" `
Notify * notifier ` json:"notify" `
}
}
// GetVersion get current config version.
func ( s * serverConfigV17 ) GetVersion ( ) string {
s . RLock ( )
defer s . RUnlock ( )
return s . Version
}
// SetRegion set new region.
func ( s * serverConfigV17 ) SetRegion ( region string ) {
s . Lock ( )
defer s . Unlock ( )
s . Region = region
}
// GetRegion get current region.
func ( s * serverConfigV17 ) GetRegion ( ) string {
s . RLock ( )
defer s . RUnlock ( )
return s . Region
}
// SetCredentials set new credentials.
func ( s * serverConfigV17 ) SetCredential ( creds credential ) {
s . Lock ( )
defer s . Unlock ( )
// Set updated credential.
s . Credential = creds
}
// GetCredentials get current credentials.
func ( s * serverConfigV17 ) GetCredential ( ) credential {
s . RLock ( )
defer s . RUnlock ( )
return s . Credential
}
// SetBrowser set if browser is enabled.
func ( s * serverConfigV17 ) SetBrowser ( b bool ) {
s . Lock ( )
defer s . Unlock ( )
// Set the new value.
s . Browser = BrowserFlag ( b )
}
// GetCredentials get current credentials.
func ( s * serverConfigV17 ) GetBrowser ( ) bool {
s . RLock ( )
defer s . RUnlock ( )
return bool ( s . Browser )
}
// Save config.
func ( s * serverConfigV17 ) Save ( ) error {
s . RLock ( )
defer s . RUnlock ( )
// Save config file.
return quick . Save ( getConfigFile ( ) , s )
}
func newServerConfigV17 ( ) * serverConfigV17 {
func newServerConfigV17 ( ) * serverConfigV17 {
srvCfg := & serverConfigV17 {
srvCfg := & serverConfigV17 {
Version : v17 ,
Version : v17 ,
@ -91,20 +162,14 @@ func newConfig() error {
// Initialize server config.
// Initialize server config.
srvCfg := newServerConfigV17 ( )
srvCfg := newServerConfigV17 ( )
// If env is set for a fresh start, save them to config file.
// If env is set override the credentials from config file.
if globalIsEnvCreds {
if globalIsEnvCreds {
srvCfg . SetCredential ( globalActiveCred )
srvCfg . SetCredential ( globalActiveCred )
}
}
if globalIsEnvBrowser {
if globalIsEnvBrowser {
srvCfg . SetBrowser ( globalIsBrowserEnabled )
srvCfg . SetBrowser ( globalIsBrowserEnabled )
}
}
// Create config path.
if err := createConfigDir ( ) ; err != nil {
return err
}
// hold the mutex lock before a new config is assigned.
// hold the mutex lock before a new config is assigned.
// Save the new config globally.
// Save the new config globally.
// unlock the mutex.
// unlock the mutex.
@ -116,42 +181,6 @@ func newConfig() error {
return serverConfig . Save ( )
return serverConfig . Save ( )
}
}
// loadConfig - loads a new config from disk, overrides params from env
// if found and valid
func loadConfig ( ) error {
srvCfg := & serverConfigV17 {
Region : globalMinioDefaultRegion ,
Browser : true ,
}
if _ , err := quick . Load ( getConfigFile ( ) , srvCfg ) ; err != nil {
return err
}
if srvCfg . Version != v17 {
return fmt . Errorf ( "configuration version mismatch. Expected: ‘%s’, Got: ‘%s’" , srvCfg . Version , v17 )
}
// If env is set override the credentials from config file.
if globalIsEnvCreds {
srvCfg . SetCredential ( globalActiveCred )
} else {
globalActiveCred = srvCfg . GetCredential ( )
}
if globalIsEnvBrowser {
srvCfg . SetBrowser ( globalIsBrowserEnabled )
} else {
globalIsBrowserEnabled = srvCfg . GetBrowser ( )
}
// hold the mutex lock before a new config is assigned.
serverConfigMu . Lock ( )
// Save the loaded config globally.
serverConfig = srvCfg
serverConfigMu . Unlock ( )
return nil
}
// doCheckDupJSONKeys recursively detects duplicate json keys
// doCheckDupJSONKeys recursively detects duplicate json keys
func doCheckDupJSONKeys ( key , value gjson . Result ) error {
func doCheckDupJSONKeys ( key , value gjson . Result ) error {
// Key occurrences map of the current scope to count
// Key occurrences map of the current scope to count
@ -203,8 +232,8 @@ func checkDupJSONKeys(json string) error {
return doCheckDupJSONKeys ( rootKey , config )
return doCheckDupJSONKeys ( rootKey , config )
}
}
// validateConfig checks for
// getValidConfig - returns valid server configuration
func validate Config( ) error {
func getValid Config( ) ( * serverConfigV17 , error ) {
srvCfg := & serverConfigV17 {
srvCfg := & serverConfigV17 {
Region : globalMinioDefaultRegion ,
Region : globalMinioDefaultRegion ,
Browser : true ,
Browser : true ,
@ -212,128 +241,74 @@ func validateConfig() error {
configFile := getConfigFile ( )
configFile := getConfigFile ( )
if _ , err := quick . Load ( configFile , srvCfg ) ; err != nil {
if _ , err := quick . Load ( configFile , srvCfg ) ; err != nil {
return err
return nil , err
}
}
if srvCfg . Version != v17 {
if srvCfg . Version != v17 {
// Older binary but newer config version.
return nil , fmt . Errorf ( "configuration version mismatch. Expected: ‘%s’, Got: ‘%s’" , v17 , srvCfg . Version )
// Config version can never be older as it would have migrated.
return fmt . Errorf ( "Expected config version: %s, newer config version found: %s" , v17 , srvCfg . Version )
}
}
// Load config file json and check for duplication json keys
// Load config file json and check for duplication json keys
jsonBytes , err := ioutil . ReadFile ( configFile )
jsonBytes , err := ioutil . ReadFile ( configFile )
if err != nil {
if err != nil {
return err
return nil , err
}
}
if err : = checkDupJSONKeys ( string ( jsonBytes ) ) ; err != nil {
if err = checkDupJSONKeys ( string ( jsonBytes ) ) ; err != nil {
return err
return nil , err
}
}
// Validate region field
// Validate region field
if srvCfg . GetRegion ( ) == "" {
if srvCfg . Region == "" {
return errors . New ( "Region config value cannot be empty" )
return nil , errors . New ( "Region config value cannot be empty" )
}
}
// Validate credential fields only when
// Validate credential fields only when
// they are not set via the environment
// they are not set via the environment
if ! globalIsEnvCreds {
if ! srvCfg . Credential . IsValid ( ) {
// Error out if global is env credential is not set and config has invalid credential
return errors . New ( "invalid credential" )
if ! globalIsEnvCreds && ! srvCfg . Credential . IsValid ( ) {
}
return nil , errors . New ( "invalid credential in config file " + configFile )
}
}
// Validate logger field
// Validate logger field
if err : = srvCfg . Logger . Validate ( ) ; err != nil {
if err = srvCfg . Logger . Validate ( ) ; err != nil {
return err
return nil , err
}
}
// Validate notify field
// Validate notify field
if err : = srvCfg . Notify . Validate ( ) ; err != nil {
if err = srvCfg . Notify . Validate ( ) ; err != nil {
return err
return nil , err
}
}
return nil
return srvCfg , nil
}
// serverConfig server config.
var serverConfig * serverConfigV17
// GetVersion get current config version.
func ( s serverConfigV17 ) GetVersion ( ) string {
serverConfigMu . RLock ( )
defer serverConfigMu . RUnlock ( )
return s . Version
}
}
// SetRegion set new region.
// loadConfig - loads a new config from disk, overrides params from env
func ( s * serverConfigV17 ) SetRegion ( region string ) {
// if found and valid
serverConfigMu . Lock ( )
func loadConfig ( ) error {
defer serverConfigMu . Unlock ( )
srvCfg , err := getValidConfig ( )
if err != nil {
// Empty region means "us-east-1" by default from S3 spec.
return err
if region == "" {
region = "us-east-1"
}
}
s . Region = region
}
// GetRegion get current region.
func ( s serverConfigV17 ) GetRegion ( ) string {
serverConfigMu . RLock ( )
defer serverConfigMu . RUnlock ( )
if s . Region != "" {
return s . Region
} // region empty
// Empty region means "us-east-1" by default from S3 spec.
return "us-east-1"
}
// SetCredentials set new credentials.
func ( s * serverConfigV17 ) SetCredential ( creds credential ) {
serverConfigMu . Lock ( )
defer serverConfigMu . Unlock ( )
// Set updated credential.
// If env is set override the credentials from config file.
s . Credential = creds
if globalIsEnvCreds {
}
srvCfg . SetCredential ( globalActiveCred )
}
// GetCredentials get current credentials.
if globalIsEnvBrowser {
func ( s serverConfigV17 ) GetCredential ( ) credential {
srvCfg . SetBrowser ( globalIsBrowserEnabled )
serverConfigMu . RLock ( )
}
defer serverConfigMu . RUnlock ( )
return s . Credential
}
// SetBrowser set if browser is enabled.
// hold the mutex lock before a new config is assigned.
func ( s * serverConfigV17 ) SetBrowser ( b bool ) {
serverConfigMu . Lock ( )
serverConfigMu . Lock ( )
defer serverConfigMu . Unlock ( )
serverConfig = srvCfg
if ! globalIsEnvCreds {
// Set the new value.
globalActiveCred = serverConfig . GetCredential ( )
s . Browser = BrowserFlag ( b )
}
}
if ! globalIsEnvBrowser {
globalIsBrowserEnabled = serverConfig . GetBrowser ( )
// GetCredentials get current credentials.
}
func ( s serverConfigV17 ) GetBrowser ( ) bool {
serverConfigMu . Unlock ( )
serverConfigMu . RLock ( )
defer serverConfigMu . RUnlock ( )
return bool ( s . Browser )
}
// Save config.
func ( s serverConfigV17 ) Save ( ) error {
serverConfigMu . RLock ( )
defer serverConfigMu . RUnlock ( )
// get config file.
configFile := getConfigFile ( )
// Save config file.
return nil
return quick . Save ( configFile , & s )
}
}