Skip to content

Commit b5f60f1

Browse files
authored
Validate issue regex (#21)
* Guard against invalid or empty issue regex * Add a unit test for invalid regex * Prevent collision with default funcname arg in some shells * Add end-to-end test for empty issue regex
1 parent 2988a91 commit b5f60f1

File tree

4 files changed

+107
-24
lines changed

4 files changed

+107
-24
lines changed

e2e.sh

Lines changed: 58 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -59,8 +59,8 @@ pass_test() {
5959
# MARK: - Test Cases
6060

6161
test_commit_from_current_directory_without_config() {
62-
FUNCNAME="test_commit_from_current_directory_without_config"
63-
start_test $FUNCNAME
62+
TESTNAME="test_commit_from_current_directory_without_config"
63+
start_test $TESTNAME
6464

6565
setup_test_repository &&\
6666
git checkout -b 1-initial-branch && \
@@ -75,20 +75,20 @@ test_commit_from_current_directory_without_config() {
7575

7676
# Check if the commit was successful
7777
if [ $? -ne 0 ]; then
78-
fail_test $FUNCNAME
78+
fail_test $TESTNAME
7979
fi
8080

8181
# Check if the commit message is correct
8282
if [ "$(git log -1 --pretty=%B)" != '#1: Hello, git!' ]; then
83-
fail_test $FUNCNAME
83+
fail_test $TESTNAME
8484
fi
8585

86-
pass_test $FUNCNAME
86+
pass_test $TESTNAME
8787
}
8888

8989
test_use_config_from_current_directory() {
90-
FUNCNAME="test_use_config_from_current_directory"
91-
start_test $FUNCNAME
90+
TESTNAME="test_use_config_from_current_directory"
91+
start_test $TESTNAME
9292

9393
setup_test_repository &&\
9494
git checkout -b feature/DEV-38-setup-new-module && \
@@ -114,20 +114,20 @@ test_use_config_from_current_directory() {
114114

115115
# Check if the commit was successful
116116
if [ $? -ne 0 ]; then
117-
fail_test $FUNCNAME
117+
fail_test $TESTNAME
118118
fi
119119

120120
# Check if the commit message is correct
121121
if [ "$(git log -1 --pretty=%B)" != '[DEV-38] Add a new file' ]; then
122-
fail_test $FUNCNAME
122+
fail_test $TESTNAME
123123
fi
124124

125-
pass_test $FUNCNAME
125+
pass_test $TESTNAME
126126
}
127127

128128
test_commit_from_subdirectory() {
129-
FUNCNAME="test_commit_from_subdirectory"
130-
start_test $FUNCNAME
129+
TESTNAME="test_commit_from_subdirectory"
130+
start_test $TESTNAME
131131

132132
setup_test_repository &&\
133133
git checkout -b prepare-for-cfg13 && \
@@ -157,22 +157,22 @@ test_commit_from_subdirectory() {
157157
# Check if the commit was successful
158158
if [ $? -ne 0 ]; then
159159
cd ..
160-
fail_test $FUNCNAME
160+
fail_test $TESTNAME
161161
fi
162162

163163
# Check if the commit message is correct
164164
if [ "$(git log -1 --pretty=%B)" != '(cfg13) Do something very useful' ]; then
165165
cd ..
166-
fail_test $FUNCNAME
166+
fail_test $TESTNAME
167167
fi
168168

169169
cd ..
170-
pass_test $FUNCNAME
170+
pass_test $TESTNAME
171171
}
172172

173173
test_set_correct_author() {
174-
FUNCNAME="test_set_correct_author"
175-
start_test $FUNCNAME
174+
TESTNAME="test_set_correct_author"
175+
start_test $TESTNAME
176176

177177
EXPECTED_AUTHOR_NAME="John Doe"
178178
EXPECTED_EMAIL="johntheprogrammer@commit.commit"
@@ -192,31 +192,65 @@ test_set_correct_author() {
192192

193193
# Check if the commit was successful
194194
if [ $? -ne 0 ]; then
195-
fail_test $FUNCNAME
195+
fail_test $TESTNAME
196196
fi
197197

198198
# Check if the commit message is correct
199199
if [ "$(git log -1 --pretty=%B)" != '#1: Hello, git!' ]; then
200-
fail_test $FUNCNAME
200+
fail_test $TESTNAME
201201
fi
202202

203203
# Check if the commit author name is correct
204204
ACTUAL_AUTHOR_NAME=$(git log -1 --pretty=%an)
205205
echo "Author name: ${ACTUAL_AUTHOR_NAME}"
206206
if [ "${ACTUAL_AUTHOR_NAME}" != "${EXPECTED_AUTHOR_NAME}" ]; then
207207
echo "Incorrect author name: expected ${EXPECTED_AUTHOR_NAME}, got ${ACTUAL_AUTHOR_NAME}"
208-
fail_test $FUNCNAME
208+
fail_test $TESTNAME
209209
fi
210210

211211
# Check if the commit author email is correct
212212
ACTUAL_EMAIL=$(git log -1 --pretty=%ae)
213213
echo "Author email: ${ACTUAL_EMAIL}"
214214
if [ "${ACTUAL_EMAIL}" != "${EXPECTED_EMAIL}" ]; then
215215
echo "Incorrect author email: expected ${EXPECTED_EMAIL}, got ${ACTUAL_EMAIL}"
216-
fail_test $FUNCNAME
216+
fail_test $TESTNAME
217217
fi
218218

219-
pass_test $FUNCNAME
219+
pass_test $TESTNAME
220+
}
221+
222+
test_use_config_with_empty_regex() {
223+
TESTNAME="test_use_config_with_empty_regex"
224+
start_test $TESTNAME
225+
226+
setup_test_repository &&\
227+
git checkout -b feature/WIP-88-add-privacy-manifest && \
228+
229+
# Write a config file
230+
echo '
231+
{
232+
"issueRegex": ""
233+
}
234+
' > .commit.json && \
235+
236+
# Create a new file
237+
echo "Hello, World!" > hello && \
238+
239+
git add hello && \
240+
241+
# Commit the file
242+
echo "Expecting exit with error..." && \
243+
../bin/commit "Add missing privacy manifest"
244+
245+
# Check if the commit was successful
246+
if [ $? -eq 0 ]; then
247+
echo "Expected exit with error, but the commit was successful"
248+
fail_test $TESTNAME
249+
fi
250+
251+
echo "Failed with error as expected!"
252+
pass_test $TESTNAME
253+
220254
}
221255

222256
# MARK: - Run Tests
@@ -227,4 +261,5 @@ setup_global_git_config
227261
test_commit_from_current_directory_without_config
228262
test_use_config_from_current_directory
229263
test_commit_from_subdirectory
230-
test_set_correct_author
264+
test_set_correct_author
265+
test_use_config_with_empty_regex

internal/config/config.go

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@ package config
22

33
import (
44
"encoding/json"
5+
"errors"
6+
"regexp"
57

68
"github.com/artem-y/commit/internal/helpers"
79
)
@@ -44,6 +46,10 @@ func ReadCommitConfig(fileReader FileReading, configFilePath string) (CommitConf
4446

4547
cfg := makeConfig(cfgDto)
4648

49+
if err := validateRegex(cfg.IssueRegex); err != nil {
50+
return CommitConfig{}, err
51+
}
52+
4753
return cfg, nil
4854
}
4955

@@ -85,3 +91,13 @@ func makeConfig(cfgDto commitConfigDTO) CommitConfig {
8591

8692
return cfg
8793
}
94+
95+
// Validate the issue regex
96+
func validateRegex(rawString string) error {
97+
if rawString == "" {
98+
return errors.New("Issue regex can't be empty. Please update the config file.")
99+
}
100+
101+
_, err := regexp.Compile(rawString)
102+
return err
103+
}

internal/config/config_test.go

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -138,6 +138,38 @@ func Test_ReadCommitConfig_WhenOnlyRegexInConfix_ReturnsConfigWithRegex(t *testi
138138
}
139139
}
140140

141+
func Test_ReadCommitConfig_WhenIssueRegexIsEmpty_ReturnsError(t *testing.T) {
142+
// Arrange
143+
var mock *mocks.FileReadingMock = &mocks.FileReadingMock{}
144+
configJson := "{\"issueRegex\":\"\"}"
145+
mock.Results.ReadFile.Success = []byte(configJson)
146+
147+
// Act
148+
_, err := config.ReadCommitConfig(mock, "some/path")
149+
150+
// Assert
151+
if err == nil {
152+
t.Error("Expected an error, got `nil`")
153+
}
154+
155+
}
156+
157+
func Test_ReadCommitConfig_WhenIssueRegexIsInvalid_ReturnsError(t *testing.T) {
158+
// Arrange
159+
var mock *mocks.FileReadingMock = &mocks.FileReadingMock{}
160+
configJson := "{\"issueRegex\":\"(123\"}"
161+
mock.Results.ReadFile.Success = []byte(configJson)
162+
163+
// Act
164+
_, err := config.ReadCommitConfig(mock, "some/path")
165+
166+
// Assert
167+
if err == nil {
168+
t.Error("Expected an error, got `nil`")
169+
}
170+
171+
}
172+
141173
func Test_MakeDefaultConfig_CreatesConfigWithDefaultValues(t *testing.T) {
142174
// Arrange
143175
expectedConfig := config.CommitConfig{

internal/user/user.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ import (
44
"fmt"
55
"os"
66

7-
"github.com/artem-y/commit/internal/helpers"
7+
"github.com/artem-y/commit/internal/helpers"
88

99
"github.com/go-git/go-git/v5"
1010
"github.com/go-git/go-git/v5/config"

0 commit comments

Comments
 (0)