|
2 | 2 | package config
|
3 | 3 |
|
4 | 4 | import (
|
| 5 | + "bufio" |
| 6 | + "errors" |
5 | 7 | "fmt"
|
6 | 8 | "os"
|
7 | 9 | "path/filepath"
|
8 | 10 |
|
9 |
| - "github.com/conventionalcommit/commitlint/formatter" |
| 11 | + "gopkg.in/yaml.v3" |
| 12 | + |
10 | 13 | "github.com/conventionalcommit/commitlint/lint"
|
11 |
| - "github.com/conventionalcommit/commitlint/rule" |
12 | 14 | )
|
13 | 15 |
|
14 | 16 | const (
|
15 | 17 | // ConfFileName represent config file name
|
16 | 18 | ConfFileName = "commitlint.yaml"
|
17 | 19 | )
|
18 | 20 |
|
19 |
| -var allFormatters = []lint.Formatter{ |
20 |
| - &formatter.DefaultFormatter{}, |
21 |
| - &formatter.JSONFormatter{}, |
22 |
| -} |
23 |
| - |
24 |
| -var allRules = []lint.Rule{ |
25 |
| - &rule.BodyMinLenRule{}, |
26 |
| - &rule.BodyMaxLenRule{}, |
27 |
| - |
28 |
| - &rule.FooterMinLenRule{}, |
29 |
| - &rule.FooterMaxLenRule{}, |
30 |
| - |
31 |
| - &rule.HeadMaxLenRule{}, |
32 |
| - &rule.HeadMinLenRule{}, |
33 |
| - |
34 |
| - &rule.TypeEnumRule{}, |
35 |
| - &rule.ScopeEnumRule{}, |
36 |
| - |
37 |
| - &rule.BodyMaxLineLenRule{}, |
38 |
| - &rule.FooterMaxLineLenRule{}, |
39 |
| - |
40 |
| - &rule.TypeCharsetRule{}, |
41 |
| - &rule.ScopeCharsetRule{}, |
42 |
| - |
43 |
| - &rule.TypeMaxLenRule{}, |
44 |
| - &rule.ScopeMaxLenRule{}, |
45 |
| - &rule.DescriptionMaxLenRule{}, |
46 |
| - |
47 |
| - &rule.TypeMinLenRule{}, |
48 |
| - &rule.ScopeMinLenRule{}, |
49 |
| - &rule.DescriptionMinLenRule{}, |
50 |
| -} |
51 |
| - |
52 | 21 | // GetConfig returns conf
|
53 | 22 | func GetConfig(flagConfPath string) (*lint.Config, error) {
|
54 | 23 | confFilePath, useDefault, err := GetConfigPath(flagConfPath)
|
@@ -93,48 +62,86 @@ func GetConfigPath(confFilePath string) (string, bool, error) {
|
93 | 62 | return filepath.Clean(confFilePath), false, nil
|
94 | 63 | }
|
95 | 64 |
|
96 |
| -// GetFormatter returns the formatter as defined in conf |
97 |
| -func GetFormatter(c *lint.Config) (lint.Formatter, error) { |
98 |
| - for _, f := range allFormatters { |
99 |
| - if f.Name() == c.Formatter { |
100 |
| - return f, nil |
101 |
| - } |
| 65 | +// Parse parse Config from given file |
| 66 | +func Parse(confPath string) (*lint.Config, error) { |
| 67 | + confBytes, err := os.ReadFile(confPath) |
| 68 | + if err != nil { |
| 69 | + return nil, err |
102 | 70 | }
|
103 |
| - return nil, fmt.Errorf("%s formatter not found", c.Formatter) |
| 71 | + |
| 72 | + conf := &lint.Config{} |
| 73 | + err = yaml.Unmarshal(confBytes, conf) |
| 74 | + if err != nil { |
| 75 | + return nil, err |
| 76 | + } |
| 77 | + |
| 78 | + err = Validate(conf) |
| 79 | + if err != nil { |
| 80 | + return nil, fmt.Errorf("config error: %w", err) |
| 81 | + } |
| 82 | + return conf, nil |
104 | 83 | }
|
105 | 84 |
|
106 |
| -// GetRules forms Rule object for rules which are enabled in config |
107 |
| -func GetRules(conf *lint.Config) ([]lint.Rule, error) { |
108 |
| - // rules lookup map |
109 |
| - rulesMap := map[string]lint.Rule{} |
110 |
| - for _, r := range allRules { |
111 |
| - rulesMap[r.Name()] = r |
| 85 | +// Validate parses Config from given data |
| 86 | +func Validate(conf *lint.Config) error { |
| 87 | + if conf.Formatter == "" { |
| 88 | + return errors.New("formatter is empty") |
112 | 89 | }
|
113 | 90 |
|
114 |
| - enabledRules := make([]lint.Rule, 0, len(conf.Rules)) |
| 91 | + // Check Severity Level of rule config |
| 92 | + for ruleName, r := range conf.Rules { |
| 93 | + switch r.Severity { |
| 94 | + case lint.SeverityError: |
| 95 | + case lint.SeverityWarn: |
| 96 | + default: |
| 97 | + return fmt.Errorf("unknown severity level '%s' for rule '%s'", r.Severity, ruleName) |
| 98 | + } |
| 99 | + } |
| 100 | + |
| 101 | + return nil |
| 102 | +} |
115 | 103 |
|
116 |
| - for ruleName, ruleConfig := range conf.Rules { |
117 |
| - r, ok := rulesMap[ruleName] |
118 |
| - if !ok { |
119 |
| - return nil, fmt.Errorf("unknown rule: %s", ruleName) |
| 104 | +// DefaultConfToFile writes default config to given file |
| 105 | +func DefaultConfToFile(isOnlyEnabled bool) error { |
| 106 | + outPath := filepath.Join(".", filepath.Clean(ConfFileName)) |
| 107 | + if isOnlyEnabled { |
| 108 | + confClone := &lint.Config{ |
| 109 | + Formatter: defConf.Formatter, |
| 110 | + Rules: map[string]lint.RuleConfig{}, |
120 | 111 | }
|
121 |
| - if ruleConfig.Enabled { |
122 |
| - err := r.Apply(ruleConfig.Argument, ruleConfig.Flags) |
123 |
| - if err != nil { |
124 |
| - return nil, err |
| 112 | + |
| 113 | + for ruleName, r := range defConf.Rules { |
| 114 | + if r.Enabled { |
| 115 | + confClone.Rules[ruleName] = r |
125 | 116 | }
|
126 |
| - enabledRules = append(enabledRules, r) |
127 | 117 | }
|
128 |
| - } |
129 | 118 |
|
130 |
| - return enabledRules, nil |
| 119 | + return WriteConfToFile(outPath, confClone) |
| 120 | + } |
| 121 | + return WriteConfToFile(outPath, defConf) |
131 | 122 | }
|
132 | 123 |
|
133 |
| -// GetLinter returns Linter for given confFilePath |
134 |
| -func GetLinter(conf *lint.Config) (*lint.Linter, error) { |
135 |
| - rules, err := GetRules(conf) |
| 124 | +// WriteConfToFile util func to write config object to given file |
| 125 | +func WriteConfToFile(outFilePath string, conf *lint.Config) (retErr error) { |
| 126 | + file, err := os.Create(outFilePath) |
136 | 127 | if err != nil {
|
137 |
| - return nil, err |
| 128 | + return err |
138 | 129 | }
|
139 |
| - return lint.NewLinter(conf, rules) |
| 130 | + defer func() { |
| 131 | + err1 := file.Close() |
| 132 | + if retErr == nil && err1 != nil { |
| 133 | + retErr = err1 |
| 134 | + } |
| 135 | + }() |
| 136 | + |
| 137 | + w := bufio.NewWriter(file) |
| 138 | + defer func() { |
| 139 | + err1 := w.Flush() |
| 140 | + if retErr == nil && err1 != nil { |
| 141 | + retErr = err1 |
| 142 | + } |
| 143 | + }() |
| 144 | + |
| 145 | + enc := yaml.NewEncoder(w) |
| 146 | + return enc.Encode(conf) |
140 | 147 | }
|
0 commit comments