Konsolidiere Titelzeichen-Validierung in TitleCharacterRule
Doppelte private isAllowedTitleCharacters-Methoden in AiResponseValidator und TargetFilenameBuildingService werden durch eine kanonische TitleCharacterRule.isAllowed()-Methode ersetzt. Beide Services delegieren jetzt dorthin statt eigene Kopien zu pflegen. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
+1
-20
@@ -100,7 +100,7 @@ public final class AiResponseValidator {
|
||||
AiErrorClassification.FUNCTIONAL);
|
||||
}
|
||||
|
||||
if (!isAllowedTitleCharacters(title)) {
|
||||
if (!TitleCharacterRule.isAllowed(title)) {
|
||||
return AiValidationResult.invalid(
|
||||
"Title contains disallowed characters (only letters, digits, spaces, and hyphens are permitted): '"
|
||||
+ title + "'",
|
||||
@@ -137,25 +137,6 @@ public final class AiResponseValidator {
|
||||
return AiValidationResult.valid(proposal);
|
||||
}
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Helpers
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
/**
|
||||
* Returns {@code true} if every character in the title is a letter, digit, space, or hyphen.
|
||||
* <p>
|
||||
* Permits Unicode letters including German Umlauts (ä, ö, ü, Ä, Ö, Ü) and ß.
|
||||
*/
|
||||
private static boolean isAllowedTitleCharacters(String title) {
|
||||
for (int i = 0; i < title.length(); i++) {
|
||||
char c = title.charAt(i);
|
||||
if (!Character.isLetter(c) && !Character.isDigit(c) && c != ' ' && c != '-') {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns {@code true} if the title is a known generic placeholder.
|
||||
* Comparison is case-insensitive.
|
||||
|
||||
+1
-15
@@ -149,7 +149,7 @@ public final class TargetFilenameBuildingService {
|
||||
}
|
||||
|
||||
// After cleaning, verify that only letters, digits, spaces, and hyphens remain
|
||||
if (!isAllowedTitleCharacters(cleanedTitle)) {
|
||||
if (!TitleCharacterRule.isAllowed(cleanedTitle)) {
|
||||
return new InconsistentProposalState(
|
||||
"After Windows-compatibility cleaning, title contains disallowed characters "
|
||||
+ "(only letters, digits, spaces, and hyphens are permitted): '"
|
||||
@@ -165,20 +165,6 @@ public final class TargetFilenameBuildingService {
|
||||
// Helpers
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
/**
|
||||
* Returns {@code true} if every character in the title is a letter, a digit, space, or hyphen.
|
||||
* Unicode letters (including German Umlauts and ß) are permitted.
|
||||
*/
|
||||
private static boolean isAllowedTitleCharacters(String title) {
|
||||
for (int i = 0; i < title.length(); i++) {
|
||||
char c = title.charAt(i);
|
||||
if (!Character.isLetter(c) && !Character.isDigit(c) && c != ' ' && c != '-') {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes characters that are incompatible with Windows filenames.
|
||||
* <p>
|
||||
|
||||
+40
@@ -0,0 +1,40 @@
|
||||
package de.gecheckt.pdf.umbenenner.application.service;
|
||||
|
||||
/**
|
||||
* Canonical rule for allowed title characters.
|
||||
* <p>
|
||||
* A title may contain only Unicode letters (including German Umlauts and ß),
|
||||
* decimal digits, ASCII spaces, and hyphens ({@code -}).
|
||||
* All other characters are considered disallowed.
|
||||
* <p>
|
||||
* This class is the single authoritative implementation of the character-allowlist
|
||||
* rule. All services that need to validate or verify title characters must delegate
|
||||
* to {@link #isAllowed(String)} instead of maintaining their own copies.
|
||||
*/
|
||||
public final class TitleCharacterRule {
|
||||
|
||||
private TitleCharacterRule() {
|
||||
// utility class
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns {@code true} if every character in {@code title} is a letter, digit,
|
||||
* ASCII space, or hyphen ({@code -}).
|
||||
* <p>
|
||||
* Unicode letters — including German Umlauts (ä, ö, ü, Ä, Ö, Ü) and ß — are
|
||||
* permitted. An empty string is considered allowed.
|
||||
*
|
||||
* @param title the title to check; must not be null
|
||||
* @return {@code true} if all characters pass the allowlist; {@code false} otherwise
|
||||
* @throws NullPointerException if {@code title} is null
|
||||
*/
|
||||
public static boolean isAllowed(String title) {
|
||||
for (int i = 0; i < title.length(); i++) {
|
||||
char c = title.charAt(i);
|
||||
if (!Character.isLetter(c) && !Character.isDigit(c) && c != ' ' && c != '-') {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
+2
@@ -22,6 +22,8 @@
|
||||
* two-level persistence</li>
|
||||
* <li>{@link de.gecheckt.pdf.umbenenner.application.service.AiRequestComposer}
|
||||
* — Deterministic composition of AI request representations from prompt and document text</li>
|
||||
* <li>{@link de.gecheckt.pdf.umbenenner.application.service.TitleCharacterRule}
|
||||
* — Canonical character-allowlist rule for document titles (single authoritative implementation)</li>
|
||||
* </ul>
|
||||
*
|
||||
* <h2>Document processing flow ({@code DocumentProcessingCoordinator})</h2>
|
||||
|
||||
Reference in New Issue
Block a user