Add function GetRulesToApplyToSourcePath.

This commit is contained in:
Amy Boyd
2016-06-22 23:58:10 +01:00
parent cfc8de6801
commit 2a8ad5689c
4 changed files with 114 additions and 1 deletions

73
editorconfig/apply.go Normal file
View File

@@ -0,0 +1,73 @@
package editorconfig
import (
"path/filepath"
"sort"
"strings"
)
func GetRulesToApplyToSourcePath(sourcePath string, cfs []ConfigFile) map[string]string {
applicable := FilterConfigFilesToApplyToSourcePath(sourcePath, cfs)
applicableSorted := SortConfigFilesByPrecendence(applicable)
rules := make(map[string]string)
for _, cf := range applicableSorted {
for _, rule := range cf.DefaultRuleSet {
rules[rule.Name] = rule.Value
}
for _, rs := range cf.FileConstrainedRuleSets {
if rs.ConstraintRegexp.MatchString(sourcePath) {
for _, rule := range rs.Rules {
rules[rule.Name] = rule.Value
}
}
}
}
delete(rules, "root")
return rules
}
func FilterConfigFilesToApplyToSourcePath(sourcePath string, cfs []ConfigFile) []ConfigFile {
applicable := []ConfigFile{}
for _, cf := range cfs {
absSourcePath, err := filepath.Abs(sourcePath)
if err != nil {
ExitBecauseOfInternalError("Could not get absolute path for " + sourcePath)
}
absCfDir, err := filepath.Abs(cf.Dir())
if err != nil {
ExitBecauseOfInternalError("Could not get absolute path for " + cf.Dir())
}
if strings.HasPrefix(absSourcePath, absCfDir) {
applicable = append(applicable, cf)
}
}
return applicable
}
// ByPrecedence implements sort.Interface for []ConfigFile based on how many slashes are in the file's path.
type ByPrecedence []ConfigFile
func (a ByPrecedence) Len() int {
return len(a)
}
func (a ByPrecedence) Swap(i, j int) {
a[i], a[j] = a[j], a[i]
}
func (a ByPrecedence) Less(i, j int) bool {
return a[i].Precedence() < a[j].Precedence()
}
/**
* @return Least important files first, most important files last.
*/
func SortConfigFilesByPrecendence(cfs []ConfigFile) []ConfigFile {
sort.Sort(ByPrecedence(cfs))
return cfs
}

View File

@@ -0,0 +1,34 @@
package editorconfig
import (
"testing"
)
func TestGetRulesToApplyToSourcePath(t *testing.T) {
result := GetRulesToApplyToSourcePath(
"tests/a/b/file.go",
[]ConfigFile{
CreateConfigFileStruct("tests/.editorconfig"),
},
)
if result["end_of_line"] != "lf" {
t.Error("The end_of_line rule should come from the * file pattern")
}
if result["indent_style"] != "tabs" {
t.Error("The indent_style rule should come from the **.go file pattern, overriding the *'s indent_style")
}
}
func TestGetRulesToApplyToSourcePathWhenNoRulesShouldApply(t *testing.T) {
result := GetRulesToApplyToSourcePath(
"some-file-not-affected-by-rules",
[]ConfigFile{
CreateConfigFileStruct("tests/.editorconfig"),
},
)
if len(result) != 0 {
t.Error("No rules should be applied for the file")
}
}

View File

@@ -2,6 +2,7 @@ package editorconfig
import ( import (
"github.com/go-ini/ini" "github.com/go-ini/ini"
"path/filepath"
"regexp" "regexp"
"strings" "strings"
) )
@@ -51,9 +52,11 @@ type FileConstrainedRuleSet struct {
} }
func CreateConfigFileStruct(path string) ConfigFile { func CreateConfigFileStruct(path string) ConfigFile {
absPath, _ := filepath.Abs(path)
ini, err := ini.Load(path) ini, err := ini.Load(path)
if err != nil { if err != nil {
ExitBecauseOfInternalError("Could not parse " + path) ExitBecauseOfInternalError("Could not parse " + absPath)
} }
cf := ConfigFile{} cf := ConfigFile{}

View File

@@ -10,3 +10,6 @@ insert_final_newline = true
[keep-trailing-spaces] [keep-trailing-spaces]
trim_trailing_whitespace = false trim_trailing_whitespace = false
[**.go]
indent_style = tabs