@@ -355,28 +355,40 @@ func GetSplunkReadableNamespaceScopedSecretData(ctx context.Context, c splcommon
355355
356356 // Create individual token type data
357357 for _ , tokenType := range splcommon .GetSplunkSecretTokenTypes () {
358- splunkReadableData [tokenType ] = namespaceScopedSecret .Data [tokenType ]
358+ if _ , exists := namespaceScopedSecret .Data [tokenType ]; exists {
359+ splunkReadableData [tokenType ] = namespaceScopedSecret .Data [tokenType ]
360+ }
359361 }
360362
361- // Create default.yml
362- splunkReadableData [ "default.yml" ] = [] byte ( fmt .Sprintf (`
363+ // Create default.yml with optional splunk_secret
364+ defaultYmlBuilder := fmt .Sprintf (`
363365splunk:
364366 hec_disabled: 0
365367 hec_enableSSL: 0
366368 hec_token: "%s"
367369 password: "%s"
368- pass4SymmKey: "%s"
370+ pass4SymmKey: "%s"` ,
371+ namespaceScopedSecret .Data ["hec_token" ],
372+ namespaceScopedSecret .Data ["password" ],
373+ namespaceScopedSecret .Data ["pass4SymmKey" ])
374+
375+ // Add splunk_secret only if it exists
376+ if splunkSecret , exists := namespaceScopedSecret .Data ["splunk_secret" ]; exists {
377+ defaultYmlBuilder += fmt .Sprintf (`
378+ splunk_secret: "%s"` , splunkSecret )
379+ }
380+
381+ // Add idxc and shc sections
382+ defaultYmlBuilder += fmt .Sprintf (`
369383 idxc:
370384 secret: "%s"
371385 shc:
372386 secret: "%s"
373387` ,
374- namespaceScopedSecret .Data ["hec_token" ],
375- namespaceScopedSecret .Data ["password" ],
376- namespaceScopedSecret .Data ["pass4SymmKey" ],
377388 namespaceScopedSecret .Data ["idxc_secret" ],
378- namespaceScopedSecret .Data ["shc_secret" ]))
389+ namespaceScopedSecret .Data ["shc_secret" ])
379390
391+ splunkReadableData ["default.yml" ] = []byte (strings .TrimSpace (defaultYmlBuilder ))
380392 return splunkReadableData , nil
381393}
382394
@@ -451,9 +463,19 @@ func ApplyNamespaceScopedSecretObject(ctx context.Context, client splcommon.Cont
451463 namespacedName := types.NamespacedName {Namespace : namespace , Name : splcommon .GetNamespaceScopedSecretName (namespace )}
452464 err := client .Get (ctx , namespacedName , & current )
453465 if err == nil {
466+ // Validate existing secrets according to PasswordManagement documentation
467+ err = validateNamespaceScopedSecrets (scopedLog , & current )
468+ if err != nil {
469+ return nil , err
470+ }
471+
454472 // Generate values for only missing types of tokens them
455473 var updateNeeded bool = false
456474 for _ , tokenType := range splcommon .GetSplunkSecretTokenTypes () {
475+ if tokenType == "splunk_secret" {
476+ // splunk_secret is optional, skip if not found
477+ continue
478+ }
457479 if _ , ok := current .Data [tokenType ]; ! ok {
458480 scopedLog .Info ("Namespace scoped secret exists, missing value for token" , "missingTokenType" , tokenType )
459481 if current .Data == nil || reflect .ValueOf (current .Data ).Kind () != reflect .Map {
@@ -491,7 +513,7 @@ func ApplyNamespaceScopedSecretObject(ctx context.Context, client splcommon.Cont
491513 for _ , tokenType := range splcommon .GetSplunkSecretTokenTypes () {
492514 if tokenType == "hec_token" {
493515 current .Data [tokenType ] = generateHECToken ()
494- } else {
516+ } else if tokenType != "splunk_secret" {
495517 current .Data [tokenType ] = splcommon .GenerateSecret (splcommon .SecretBytes , 24 )
496518 }
497519 }
@@ -523,6 +545,40 @@ func ApplyNamespaceScopedSecretObject(ctx context.Context, client splcommon.Cont
523545 return & current , nil
524546}
525547
548+ // validateNamespaceScopedSecrets validates that all Splunk secret tokens that exist are not empty
549+ // and meet their specific requirements
550+ // Validates secrets documented in PasswordManagement: hec_token, password, pass4SymmKey, idxc_secret, shc_secret
551+ func validateNamespaceScopedSecrets (scopedLog interface {
552+ Info (msg string , keysAndValues ... interface {})
553+ Error (err error , msg string , keysAndValues ... interface {})
554+ }, secret * corev1.Secret ) error {
555+ if secret .Data == nil {
556+ scopedLog .Info ("Secret data is nil for namespace scoped secret" )
557+ return nil
558+ }
559+
560+ // Validate each documented secret token type
561+ for _ , tokenType := range splcommon .GetSplunkSecretTokenTypes () {
562+ if secretValue , exists := secret .Data [tokenType ]; exists {
563+ var err error
564+ if tokenType == "hec_token" {
565+ err = ValidateHECToken (secretValue )
566+ } else {
567+ err = ValidateSecret (secretValue )
568+ }
569+
570+ if err != nil {
571+ scopedLog .Error (err , "Validation failed for secret" , "secret" , tokenType )
572+ return fmt .Errorf ("validation failed for secret %s: %w" , tokenType , err )
573+ }
574+
575+ scopedLog .Info ("Namespace scoped secret validation passed" , "secret" , tokenType )
576+ }
577+ }
578+
579+ return nil
580+ }
581+
526582// GetSecretByName retrieves namespace scoped secret object for a given name
527583func GetSecretByName (ctx context.Context , c splcommon.ControllerClient , namespace string , logHandle string , name string ) (* corev1.Secret , error ) {
528584 var namespaceScopedSecret corev1.Secret
0 commit comments