Passed
Pull Request — main (#50)
by Igor
02:03
created

it/choice.go   A

Size/Duplication

Total Lines 93
Duplicated Lines 0 %

Test Coverage

Coverage 100%

Importance

Changes 0
Metric Value
cc 13
eloc 50
dl 0
loc 93
ccs 20
cts 20
cp 1
crap 13
rs 10
c 0
b 0
f 0

7 Methods

Rating   Name   Duplication   Size   Complexity  
A it.ChoiceConstraint.When 0 3 1
A it.ChoiceConstraint.ValidateString 0 17 5
A it.ChoiceConstraint.Code 0 3 1
A it.IsOneOfStrings 0 11 2
A it.ChoiceConstraint.Message 0 4 1
A it.ChoiceConstraint.Name 0 2 1
A it.ChoiceConstraint.SetUp 0 6 2
1
package it
2
3
import (
4
	"strings"
5
6
	"github.com/muonsoft/validation"
7
	"github.com/muonsoft/validation/code"
8
	"github.com/muonsoft/validation/message"
9
)
10
11
// ChoiceConstraint is used to ensure that the given value corresponds to one of the expected choices.
12
type ChoiceConstraint struct {
13
	choices           map[string]bool
14
	choicesValue      string
15
	code              string
16
	messageTemplate   string
17
	messageParameters validation.TemplateParameterList
18
	isIgnored         bool
19
}
20
21
// IsOneOfStrings creates a ChoiceConstraint for checking that values are in the expected list of strings.
22
//
23
// Example
24
//  err := validator.ValidateString(&s, it.IsOneOfStrings("one", "two", "three"))
25
func IsOneOfStrings(values ...string) ChoiceConstraint {
26 1
	choices := make(map[string]bool, len(values))
27 1
	for _, value := range values {
28 1
		choices[value] = true
29
	}
30
31 1
	return ChoiceConstraint{
32
		choices:         choices,
33
		choicesValue:    strings.Join(values, ", "),
34
		code:            code.NoSuchChoice,
35
		messageTemplate: message.NoSuchChoice,
36
	}
37
}
38
39
// SetUp will return an error if the list of choices is empty.
40
func (c ChoiceConstraint) SetUp() error {
41 1
	if len(c.choices) == 0 {
42 1
		return errEmptyChoices
43
	}
44
45 1
	return nil
46
}
47
48
// Name is the constraint name.
49
func (c ChoiceConstraint) Name() string {
50 1
	return "ChoiceConstraint"
51
}
52
53
// Code overrides default code for produced violation.
54
func (c ChoiceConstraint) Code(code string) ChoiceConstraint {
55 1
	c.code = code
56 1
	return c
57
}
58
59
// Message sets the violation message template. You can set custom template parameters
60
// for injecting its values into the final message. Also, you can use default parameters:
61
//
62
//	{{ choices }} - a comma-separated list of available choices;
63
//	{{ value }} - the current (invalid) value.
64
func (c ChoiceConstraint) Message(template string, parameters ...validation.TemplateParameter) ChoiceConstraint {
65 1
	c.messageTemplate = template
66 1
	c.messageParameters = parameters
67 1
	return c
68
}
69
70
// When enables conditional validation of this constraint. If the expression evaluates to false,
71
// then the constraint will be ignored.
72
func (c ChoiceConstraint) When(condition bool) ChoiceConstraint {
73 1
	c.isIgnored = !condition
74 1
	return c
75
}
76
77
func (c ChoiceConstraint) ValidateString(value *string, scope validation.Scope) error {
78 1
	if c.isIgnored || value == nil || *value == "" {
79 1
		return nil
80
	}
81 1
	if c.choices[*value] {
82 1
		return nil
83
	}
84
85 1
	return scope.
86
		BuildViolation(c.code, c.messageTemplate).
87
		SetParameters(
88
			c.messageParameters.Prepend(
89
				validation.TemplateParameter{Key: "{{ value }}", Value: *value},
90
				validation.TemplateParameter{Key: "{{ choices }}", Value: c.choicesValue},
91
			)...,
92
		).
93
		CreateViolation()
94
}
95