2024-03-27 10:49:05 +00:00
package loader
2022-11-18 09:57:31 +00:00
import (
2022-11-28 09:59:43 +00:00
"context"
2025-01-23 13:58:18 +00:00
"fmt"
2022-11-18 09:57:31 +00:00
"path/filepath"
2023-08-15 13:50:40 +00:00
"slices"
2023-07-07 10:22:58 +00:00
"strings"
2022-11-18 09:57:31 +00:00
2023-05-16 16:35:39 +00:00
"github.com/databricks/cli/bundle"
"github.com/databricks/cli/bundle/config"
2024-03-25 14:18:47 +00:00
"github.com/databricks/cli/libs/diag"
2022-11-18 09:57:31 +00:00
)
type processRootIncludes struct { }
// ProcessRootIncludes expands the patterns in the configuration's include list
// into a list of mutators for each matching file.
2022-11-28 09:59:43 +00:00
func ProcessRootIncludes ( ) bundle . Mutator {
2022-11-18 09:57:31 +00:00
return & processRootIncludes { }
}
func ( m * processRootIncludes ) Name ( ) string {
return "ProcessRootIncludes"
}
2024-03-25 14:18:47 +00:00
func ( m * processRootIncludes ) Apply ( ctx context . Context , b * bundle . Bundle ) diag . Diagnostics {
2022-11-28 09:59:43 +00:00
var out [ ] bundle . Mutator
2022-11-18 09:57:31 +00:00
// Map with files we've already seen to avoid loading them twice.
2023-07-18 10:16:34 +00:00
seen := map [ string ] bool { }
for _ , file := range config . FileNames {
seen [ file ] = true
2022-11-18 09:57:31 +00:00
}
2023-02-20 20:01:28 +00:00
// Maintain list of files in order of files being loaded.
// This is stored in the bundle configuration for observability.
var files [ ] string
2025-01-23 13:58:18 +00:00
var diags diag . Diagnostics
2023-02-20 20:01:28 +00:00
2022-11-18 09:57:31 +00:00
// For each glob, find all files to load.
// Ordering of the list of globs is maintained in the output.
// For matches that appear in multiple globs, only the first is kept.
2022-11-28 09:59:43 +00:00
for _ , entry := range b . Config . Include {
2022-11-18 09:57:31 +00:00
// Include paths must be relative.
if filepath . IsAbs ( entry ) {
2024-03-25 14:18:47 +00:00
return diag . Errorf ( "%s: includes must be relative paths" , entry )
2022-11-18 09:57:31 +00:00
}
// Anchor includes to the bundle root path.
2024-09-27 10:03:05 +00:00
matches , err := filepath . Glob ( filepath . Join ( b . BundleRootPath , entry ) )
2022-11-18 09:57:31 +00:00
if err != nil {
2024-03-25 14:18:47 +00:00
return diag . FromErr ( err )
2022-11-18 09:57:31 +00:00
}
2023-07-07 10:22:58 +00:00
// If the entry is not a glob pattern and no matches found,
// return an error because the file defined is not found
if len ( matches ) == 0 && ! strings . ContainsAny ( entry , "*?[" ) {
2024-03-25 14:18:47 +00:00
return diag . Errorf ( "%s defined in 'include' section does not match any files" , entry )
2023-07-07 10:22:58 +00:00
}
2022-11-18 09:57:31 +00:00
// Filter matches to ones we haven't seen yet.
var includes [ ] string
2025-01-23 13:58:18 +00:00
for i , match := range matches {
2024-09-27 10:03:05 +00:00
rel , err := filepath . Rel ( b . BundleRootPath , match )
2022-11-18 09:57:31 +00:00
if err != nil {
2024-03-25 14:18:47 +00:00
return diag . FromErr ( err )
2022-11-18 09:57:31 +00:00
}
if _ , ok := seen [ rel ] ; ok {
continue
}
seen [ rel ] = true
2025-01-23 13:58:18 +00:00
if filepath . Ext ( rel ) != ".yaml" && filepath . Ext ( rel ) != ".yml" {
diags = diags . Append ( diag . Diagnostic {
Severity : diag . Error ,
Summary : "Files in the 'include' configuration section must be YAML files." ,
Detail : fmt . Sprintf ( "The file %s in the 'include' configuration section is not a YAML file, and only YAML files are supported. To include files to sync, specify them in the 'sync.include' configuration section instead." , rel ) ,
Locations : b . Config . GetLocations ( fmt . Sprintf ( "include[%d]" , i ) ) ,
} )
continue
}
2022-11-18 09:57:31 +00:00
includes = append ( includes , rel )
}
2025-01-23 13:58:18 +00:00
if len ( diags ) > 0 {
return diags
}
2022-11-18 09:57:31 +00:00
// Add matches to list of mutators to return.
slices . Sort ( includes )
2023-02-20 20:01:28 +00:00
files = append ( files , includes ... )
2022-11-18 09:57:31 +00:00
for _ , include := range includes {
2024-09-27 10:03:05 +00:00
out = append ( out , ProcessInclude ( filepath . Join ( b . BundleRootPath , include ) , include ) )
2022-11-18 09:57:31 +00:00
}
}
2023-02-20 20:01:28 +00:00
// Swap out the original includes list with the expanded globs.
b . Config . Include = files
2023-05-24 12:45:19 +00:00
return bundle . Apply ( ctx , b , bundle . Seq ( out ... ) )
2022-11-18 09:57:31 +00:00
}