2023-05-03 11:06:20 +02:00
== Why is this an issue?
2023-10-18 15:35:51 +02:00
A `printf-`-style format string is a string that contains placeholders, usually represented by special characters such as "%s" or "{}", depending on the technology in use. These placeholders are replaced by values when the string is printed or logged.
2021-09-21 15:40:35 +02:00
2023-10-18 15:35:51 +02:00
Because `printf`-style format strings are interpreted at runtime, rather than validated by the compiler, they can contain errors that result in the wrong strings being created.
2021-09-21 15:40:35 +02:00
2023-10-18 15:35:51 +02:00
This rule checks whether every format string specifier can be correctly matched with one of the additional arguments when calling the following methods:
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
* https://docs.oracle.com/javase/8/docs/api/java/lang/String.html#format-java.lang.String-java.lang.Object...-[`java.lang.String#format`]
* https://docs.oracle.com/javase/8/docs/api/java/util/Formatter.html#format-java.lang.String-java.lang.Object...-[`java.util.Formatter#format`]
* https://docs.oracle.com/javase/8/docs/api/java/io/PrintStream.html#format-java.lang.String-java.lang.Object...-[`java.io.PrintStream#format`]
* https://docs.oracle.com/javase/8/docs/api/java/text/MessageFormat.html#format-java.lang.String-java.lang.Object...-[`java.text.MessageFormat#format`]
* https://docs.oracle.com/javase/8/docs/api/java/io/PrintWriter.html#format-java.lang.String-java.lang.Object...-[`java.io.PrintWriter#format`]
* https://docs.oracle.com/javase/8/docs/api/java/io/PrintStream.html#printf-java.lang.String-java.lang.Object...-[`java.io.PrintStream#printf`]
* https://docs.oracle.com/javase/8/docs/api/java/io/PrintWriter.html#printf-java.lang.String-java.lang.Object...-[`java.io.PrintWriter#printf`]
* https://docs.oracle.com/en/java/javase/17/docs/api/java.base/java/lang/String.html#formatted(java.lang.Object...)[`java.lang.String#formatted`] (since Java 15)
* logging methods of https://www.slf4j.org/api/org/slf4j/Logger.html[`org.slf4j.Logger`], https://docs.oracle.com/javase/8/docs/api/java/util/logging/Logger.html[`java.util.logging.Logger`], https://logging.apache.org/log4j/2.x/javadoc/log4j-api/org/apache/logging/log4j/Logger.html[`org.apache.logging.log4j.Logger`].
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
== How to fix it
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
A `printf-`-style format string is a string that contains placeholders, which are replaced by values when the string is printed or logged. Mismatch in the format specifiers and the arguments provided can lead to incorrect strings being created.
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
To avoid issues, a developer should ensure that the provided arguments match format specifiers.
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
=== Code examples
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
==== Noncompliant code example
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
[source,java,diff-id=1,diff-type=noncompliant]
2023-10-16 16:34:38 +02:00
----
2023-10-18 15:35:51 +02:00
String.format("Too many arguments %d and %d", 1, 2, 3); // Noncompliant; the third argument '3' is unused
String.format("First {0} and then {1}", "foo", "bar"); //Noncompliant. It appears there is confusion with the use of "java.text.MessageFormat"; parameters "foo" and "bar" will be ignored here
2023-10-16 16:34:38 +02:00
org.slf4j.Logger slf4jLog;
2023-10-18 15:35:51 +02:00
slf4jLog.debug("The number: ", 1); // Noncompliant - String contains no format specifiers.
----
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
==== Compliant solution
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
[source,java,diff-id=1,diff-type=compliant]
2023-10-16 16:34:38 +02:00
----
2023-10-18 15:35:51 +02:00
String.format("Too many arguments %d and %d", 1, 2);
String.format("First %s and then %s", "foo", "bar");
2023-10-16 16:34:38 +02:00
2023-10-18 15:35:51 +02:00
org.slf4j.Logger slf4jLog;
slf4jLog.debug("The number: {}", 1);
----
2021-09-21 15:40:35 +02:00
2023-05-03 11:06:20 +02:00
== Resources
2021-09-21 15:40:35 +02:00
* https://wiki.sei.cmu.edu/confluence/x/J9YxBQ[CERT, FIO47-C.] - Use valid format strings
2023-10-18 15:35:51 +02:00
* https://docs.oracle.com/javase/8/docs/api/java/text/MessageFormat.html[java.text.MessageFormat]
2021-06-02 20:44:38 +02:00
2021-06-03 09:05:38 +02:00
ifdef::env-github,rspecator-view[]
2021-09-20 15:38:42 +02:00
'''
== Implementation Specification
(visible only on this page)
2021-06-08 15:52:13 +02:00
'''
2021-06-02 20:44:38 +02:00
== Comments And Links
(visible only on this page)
include::../comments-and-links.adoc[]
2023-06-22 10:38:01 +02:00
2021-06-03 09:05:38 +02:00
endif::env-github,rspecator-view[]