93 lines
2.0 KiB
Go
93 lines
2.0 KiB
Go
package gsp
|
|
|
|
import (
|
|
"os"
|
|
"path/filepath"
|
|
"sort"
|
|
"strings"
|
|
|
|
"gopkg.in/yaml.v3"
|
|
)
|
|
|
|
var ignoredDirs = map[string]bool{
|
|
".git": true,
|
|
".gsp": true,
|
|
"node_modules": true,
|
|
"dist": true,
|
|
"build": true,
|
|
"bin": true,
|
|
}
|
|
|
|
func LoadProject(root string) (*Project, error) {
|
|
absRoot, err := filepath.Abs(root)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
project := &Project{
|
|
Root: absRoot,
|
|
ByID: map[string]*Unit{},
|
|
Duplicates: map[string][]*Unit{},
|
|
}
|
|
|
|
var files []string
|
|
err = filepath.WalkDir(absRoot, func(path string, entry os.DirEntry, walkErr error) error {
|
|
if walkErr != nil {
|
|
project.LoadIssues = append(project.LoadIssues, Issue{Level: "error", Code: "walk_error", File: path, Message: walkErr.Error()})
|
|
return nil
|
|
}
|
|
if entry.IsDir() {
|
|
if ignoredDirs[entry.Name()] {
|
|
return filepath.SkipDir
|
|
}
|
|
return nil
|
|
}
|
|
if strings.EqualFold(filepath.Ext(entry.Name()), ".gsp") {
|
|
files = append(files, path)
|
|
}
|
|
return nil
|
|
})
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
sort.Strings(files)
|
|
|
|
for _, file := range files {
|
|
unit, err := readUnit(absRoot, file)
|
|
if err != nil {
|
|
project.LoadIssues = append(project.LoadIssues, Issue{Level: "error", Code: "parse_error", File: relPath(absRoot, file), Message: err.Error()})
|
|
continue
|
|
}
|
|
project.Units = append(project.Units, unit)
|
|
if unit.ID == "" {
|
|
continue
|
|
}
|
|
if existing, ok := project.ByID[unit.ID]; ok {
|
|
project.Duplicates[unit.ID] = append(project.Duplicates[unit.ID], existing, unit)
|
|
continue
|
|
}
|
|
project.ByID[unit.ID] = unit
|
|
}
|
|
return project, nil
|
|
}
|
|
|
|
func readUnit(root, file string) (*Unit, error) {
|
|
data, err := os.ReadFile(file)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
var unit Unit
|
|
if err := yaml.Unmarshal(data, &unit); err != nil {
|
|
return nil, err
|
|
}
|
|
unit.File = relPath(root, file)
|
|
return &unit, nil
|
|
}
|
|
|
|
func relPath(root, path string) string {
|
|
rel, err := filepath.Rel(root, path)
|
|
if err != nil {
|
|
return path
|
|
}
|
|
return filepath.ToSlash(rel)
|
|
}
|