This is an automated email from the ASF dual-hosted git repository.

jamesbognar pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/juneau.git


The following commit(s) were added to refs/heads/master by this push:
     new e79e7da5b8 Unit tests
e79e7da5b8 is described below

commit e79e7da5b8047c98d1eb6995510678df19a14f3d
Author: James Bognar <[email protected]>
AuthorDate: Mon Dec 1 06:54:48 2025 -0800

    Unit tests
---
 .../java/org/apache/juneau/common/utils/StringFormat.java     | 11 +++++------
 .../org/apache/juneau/common/utils/StringFormat_Test.java     |  9 +++++++++
 2 files changed, 14 insertions(+), 6 deletions(-)

diff --git 
a/juneau-core/juneau-common/src/main/java/org/apache/juneau/common/utils/StringFormat.java
 
b/juneau-core/juneau-common/src/main/java/org/apache/juneau/common/utils/StringFormat.java
index 416c87a09a..8de20c61d2 100644
--- 
a/juneau-core/juneau-common/src/main/java/org/apache/juneau/common/utils/StringFormat.java
+++ 
b/juneau-core/juneau-common/src/main/java/org/apache/juneau/common/utils/StringFormat.java
@@ -212,12 +212,6 @@ public final class StringFormat {
 
                @Override
                void append(StringBuilder sb, Object[] args, Locale locale) {
-                       // %n is special - it doesn't consume an argument, just 
outputs a line separator
-                       if (format == 'n') {
-                               sb.append(System.lineSeparator());
-                               return;
-                       }
-
                        // String.format() throws 
MissingFormatArgumentException when argument is missing
                        if (args == null || index >= args.length || index < 0) {
                                throw new 
MissingFormatArgumentException(content);
@@ -530,6 +524,11 @@ public final class StringFormat {
                                        tokens.add(new LiteralToken("%"));
                                        state = S1;
                                        mark = i;
+                               } else if (ch == 'n') {
+                                       // %n is special - it doesn't consume 
an argument, so handle it as a literal token
+                                       tokens.add(new 
LiteralToken(System.lineSeparator()));
+                                       state = S1;
+                                       mark = i;
                                } else if (ch == 't' || ch == 'T') {
                                        // Do nothing.  Part of 2-character 
time conversion.
                                } else if 
(PRINTF_CONVERSION_CHARS.contains(ch)) {
diff --git 
a/juneau-utest/src/test/java/org/apache/juneau/common/utils/StringFormat_Test.java
 
b/juneau-utest/src/test/java/org/apache/juneau/common/utils/StringFormat_Test.java
index 026e207c4a..d9d463135c 100644
--- 
a/juneau-utest/src/test/java/org/apache/juneau/common/utils/StringFormat_Test.java
+++ 
b/juneau-utest/src/test/java/org/apache/juneau/common/utils/StringFormat_Test.java
@@ -273,6 +273,10 @@ class StringFormat_Test extends TestBase {
                assertStringFormat("Value: %B", true);
                assertStringFormat("Char: %C", 'a');
                assertStringFormat("Float: %F", 3.14);
+               // %n doesn't consume an argument - test sequential index 
behavior
+               assertStringFormat("Line 1%nLine 2");
+               assertStringFormat("First: %s%nSecond: %s", "one", "two");
+               assertStringFormat("%s %n %s", "first", "second");
 
                // Errors
                assertStringFormat("Hello %s");
@@ -382,6 +386,11 @@ class StringFormat_Test extends TestBase {
                assertEquals("[L:Month: ][S:z0:%tm]", fs("Month: 
%tm").toPattern());  // %tm is 2-character time conversion
                assertEquals("[L:Year: ][S:z0:%tY]", fs("Year: 
%tY").toPattern());  // %tY is 2-character time conversion
                assertEquals("[L:Date: ][S:z0:%TD]", fs("Date: 
%TD").toPattern());  // %TD is 2-character time conversion
+
+               // %n doesn't consume an argument - it's handled as a 
LiteralToken
+               var lineSep = System.lineSeparator();
+               assertEquals("[L:Line 1][L:" + lineSep + "][L:Line 2]", 
fs("Line 1%nLine 2").toPattern());
+               assertEquals("[S:s0:%s][L: ][L:" + lineSep + "][L: ][S:s1:%s]", 
fs("%s %n %s").toPattern());  // %n is a literal, so second %s gets index 1
        }
 
        @Test void a10_veryLongPattern() {

Reply via email to