Skip to content

Commit f4fe97b

Browse files
authored
Fix warning display issue for entering a title made of two words (JabRef#6054)
1 parent 6468f42 commit f4fe97b

File tree

4 files changed

+119
-11
lines changed

4 files changed

+119
-11
lines changed

CHANGELOG.md

+1
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,7 @@ Note that this project **does not** adhere to [Semantic Versioning](http://semve
6565
- We fixed an issue where the group and the link column were not updated after changing the entry in the main table. [#5985](https://github.com/JabRef/jabref/issues/5985)
6666
- We fixed an issue where reordering the groups was not possible after inserting an article. [#6008](https://github.com/JabRef/jabref/issues/6008)
6767
- We fixed an issue where citation styles except the default "Preview" could not be used. [#56220](https://github.com/JabRef/jabref/issues/5622)
68+
- We fixed an issue where a warning was displayed when the title content is made up of two sentences. [#5832](https://github.com/JabRef/jabref/issues/5832)
6869
- We fixed an issue where an exception was thrown when adding a save action without a selected formatter in the library properties [#6069](https://github.com/JabRef/jabref/issues/6069)
6970

7071
### Removed

src/main/java/org/jabref/logic/integrity/TitleChecker.java

+17-11
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
public class TitleChecker implements ValueChecker {
1313

1414
private static final Pattern INSIDE_CURLY_BRAKETS = Pattern.compile("\\{[^}\\{]*\\}");
15+
private static final Pattern DELIMITERS = Pattern.compile("\\.|\\!|\\?|\\;|\\:");
1516
private static final Predicate<String> HAS_CAPITAL_LETTERS = Pattern.compile("[\\p{Lu}\\p{Lt}]").asPredicate();
1617

1718
private final BibDatabaseContext databaseContext;
@@ -22,10 +23,13 @@ public TitleChecker(BibDatabaseContext databaseContext) {
2223

2324
/**
2425
* Algorithm:
25-
* - remove trailing whitespaces
26-
* - ignore first letter as this can always be written in caps
2726
* - remove everything that is in brackets
28-
* - check if at least one capital letter is in the title
27+
* - split the title into sub titles based on the delimiters
28+
* (defined in the local variable DELIMITERS, currently . ! ? ; :)
29+
* - for each sub title:
30+
* - remove trailing whitespaces
31+
* - ignore first letter as this can always be written in caps
32+
* - check if at least one capital letter is in the sub title
2933
*/
3034
@Override
3135
public Optional<String> checkValue(String value) {
@@ -37,9 +41,7 @@ public Optional<String> checkValue(String value) {
3741
return Optional.empty();
3842
}
3943

40-
String valueTrimmed = value.trim();
41-
String valueIgnoringFirstLetter = valueTrimmed.startsWith("{") ? valueTrimmed : valueTrimmed.substring(1);
42-
String valueOnlySpacesWithinCurlyBraces = valueIgnoringFirstLetter;
44+
String valueOnlySpacesWithinCurlyBraces = value;
4345
while (true) {
4446
Matcher matcher = INSIDE_CURLY_BRAKETS.matcher(valueOnlySpacesWithinCurlyBraces);
4547
if (!matcher.find()) {
@@ -48,11 +50,15 @@ public Optional<String> checkValue(String value) {
4850
valueOnlySpacesWithinCurlyBraces = matcher.replaceAll("");
4951
}
5052

51-
boolean hasCapitalLettersThatBibtexWillConvertToSmallerOnes = HAS_CAPITAL_LETTERS
52-
.test(valueOnlySpacesWithinCurlyBraces);
53-
54-
if (hasCapitalLettersThatBibtexWillConvertToSmallerOnes) {
55-
return Optional.of(Localization.lang("capital letters are not masked using curly brackets {}"));
53+
String[] splitTitle = DELIMITERS.split(valueOnlySpacesWithinCurlyBraces);
54+
for (String subTitle : splitTitle) {
55+
subTitle = subTitle.trim();
56+
if (!subTitle.isEmpty()) {
57+
subTitle = subTitle.substring(1);
58+
if (HAS_CAPITAL_LETTERS.test(subTitle)) {
59+
return Optional.of(Localization.lang("capital letters are not masked using curly brackets {}"));
60+
}
61+
}
5662
}
5763

5864
return Optional.empty();

src/test/java/org/jabref/logic/integrity/IntegrityCheckTest.java

+22
Original file line numberDiff line numberDiff line change
@@ -186,6 +186,17 @@ void testTitleChecks() {
186186
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a {Title}"), BibDatabaseMode.BIBTEX));
187187
assertCorrect(withMode(createContext(StandardField.TITLE, "{C}urrent {C}hronicle"), BibDatabaseMode.BIBTEX));
188188
assertCorrect(withMode(createContext(StandardField.TITLE, "{A Model-Driven Approach for Monitoring {ebBP} BusinessTransactions}"), BibDatabaseMode.BIBTEX));
189+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: This is a sub title 2"), BibDatabaseMode.BIBTEX));
190+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: this is a sub title 2"), BibDatabaseMode.BIBTEX));
191+
assertWrong(withMode(createContext(StandardField.TITLE, "This is a sub title 1: This is A sub title 2"), BibDatabaseMode.BIBTEX));
192+
assertWrong(withMode(createContext(StandardField.TITLE, "This is a sub title 1: this is A sub title 2"), BibDatabaseMode.BIBTEX));
193+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: This is {A} sub title 2"), BibDatabaseMode.BIBTEX));
194+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: this is {A} sub title 2"), BibDatabaseMode.BIBTEX));
195+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1...This is a sub title 2"), BibDatabaseMode.BIBTEX));
196+
assertWrong(withMode(createContext(StandardField.TITLE, "This is a sub title 1... this is a sub Title 2"), BibDatabaseMode.BIBTEX));
197+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is; A sub title 1.... This is a sub title 2"), BibDatabaseMode.BIBTEX));
198+
assertCorrect(withMode(createContext(StandardField.TITLE, "This!is!!A!Title??"), BibDatabaseMode.BIBTEX));
199+
assertWrong(withMode(createContext(StandardField.TITLE, "This!is!!A!TitlE??"), BibDatabaseMode.BIBTEX));
189200

190201
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a title"), BibDatabaseMode.BIBLATEX));
191202
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a Title"), BibDatabaseMode.BIBLATEX));
@@ -194,6 +205,17 @@ void testTitleChecks() {
194205
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a {Title}"), BibDatabaseMode.BIBLATEX));
195206
assertCorrect(withMode(createContext(StandardField.TITLE, "{C}urrent {C}hronicle"), BibDatabaseMode.BIBLATEX));
196207
assertCorrect(withMode(createContext(StandardField.TITLE, "{A Model-Driven Approach for Monitoring {ebBP} BusinessTransactions}"), BibDatabaseMode.BIBLATEX));
208+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: This is a sub title 2"), BibDatabaseMode.BIBLATEX));
209+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: this is a sub title 2"), BibDatabaseMode.BIBLATEX));
210+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: This is A sub title 2"), BibDatabaseMode.BIBLATEX));
211+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: this is A sub title 2"), BibDatabaseMode.BIBLATEX));
212+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: This is {A} sub title 2"), BibDatabaseMode.BIBLATEX));
213+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1: this is {A} sub title 2"), BibDatabaseMode.BIBLATEX));
214+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1...This is a sub title 2"), BibDatabaseMode.BIBLATEX));
215+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is a sub title 1... this is a sub Title 2"), BibDatabaseMode.BIBLATEX));
216+
assertCorrect(withMode(createContext(StandardField.TITLE, "This is; A sub title 1.... This is a sub title 2"), BibDatabaseMode.BIBLATEX));
217+
assertCorrect(withMode(createContext(StandardField.TITLE, "This!is!!A!Title??"), BibDatabaseMode.BIBLATEX));
218+
assertCorrect(withMode(createContext(StandardField.TITLE, "This!is!!A!TitlE??"), BibDatabaseMode.BIBLATEX));
197219
}
198220

199221
@Test
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
package org.jabref.logic.integrity;
2+
3+
import java.util.Optional;
4+
5+
import org.jabref.model.database.BibDatabaseContext;
6+
import org.jabref.model.database.BibDatabaseMode;
7+
8+
import org.junit.jupiter.api.BeforeEach;
9+
import org.junit.jupiter.api.Test;
10+
11+
import static org.junit.jupiter.api.Assertions.assertEquals;
12+
import static org.junit.jupiter.api.Assertions.assertNotEquals;
13+
14+
public class TitleCheckerTest {
15+
16+
private TitleChecker checker;
17+
18+
@BeforeEach
19+
public void setUp() {
20+
BibDatabaseContext databaseContext = new BibDatabaseContext();
21+
databaseContext.setMode(BibDatabaseMode.BIBTEX);
22+
checker = new TitleChecker(databaseContext);
23+
}
24+
25+
@Test
26+
public void FirstLetterAsOnlyCapitalLetterInSubTitle2() {
27+
assertEquals(Optional.empty(), checker.checkValue("This is a sub title 1: This is a sub title 2"));
28+
}
29+
30+
@Test
31+
public void NoCapitalLetterInSubTitle2() {
32+
assertEquals(Optional.empty(), checker.checkValue("This is a sub title 1: this is a sub title 2"));
33+
}
34+
35+
@Test
36+
public void TwoCapitalLettersInSubTitle2() {
37+
assertNotEquals(Optional.empty(), checker.checkValue("This is a sub title 1: This is A sub title 2"));
38+
}
39+
40+
@Test
41+
public void MiddleLetterAsOnlyCapitalLetterInSubTitle2() {
42+
assertNotEquals(Optional.empty(), checker.checkValue("This is a sub title 1: this is A sub title 2"));
43+
}
44+
45+
@Test
46+
public void TwoCapitalLettersInSubTitle2WithCurlyBrackets() {
47+
assertEquals(Optional.empty(), checker.checkValue("This is a sub title 1: This is {A} sub title 2"));
48+
}
49+
50+
@Test
51+
public void MiddleLetterAsOnlyCapitalLetterInSubTitle2WithCurlyBrackets() {
52+
assertEquals(Optional.empty(), checker.checkValue("This is a sub title 1: this is {A} sub title 2"));
53+
}
54+
55+
@Test
56+
public void FirstLetterAsOnlyCapitalLetterInSubTitle2AfterContinuousDelimiters() {
57+
assertEquals(Optional.empty(), checker.checkValue("This is a sub title 1...This is a sub title 2"));
58+
}
59+
60+
@Test
61+
public void MiddleLetterAsOnlyCapitalLetterInSubTitle2AfterContinuousDelimiters() {
62+
assertNotEquals(Optional.empty(), checker.checkValue("This is a sub title 1... this is a sub Title 2"));
63+
}
64+
65+
@Test
66+
public void FirstLetterAsOnlyCapitalLetterInEverySubTitleWithContinuousDelimiters() {
67+
assertEquals(Optional.empty(), checker.checkValue("This is; A sub title 1.... This is a sub title 2"));
68+
}
69+
70+
@Test
71+
public void FirstLetterAsOnlyCapitalLetterInEverySubTitleWithRandomDelimiters() {
72+
assertEquals(Optional.empty(), checker.checkValue("This!is!!A!Title??"));
73+
}
74+
75+
@Test
76+
public void MoreThanOneCapitalLetterInSubTitleWithoutCurlyBrackets() {
77+
assertNotEquals(Optional.empty(), checker.checkValue("This!is!!A!TitlE??"));
78+
}
79+
}

0 commit comments

Comments
 (0)