fortify / fcli

fcli is a command-line utility for interacting with various Fortify products
https://fortify.github.io/fcli/
Other
31 stars 19 forks source link

-o 'expr={id}\n' as example in docs #332

Closed xakrurychle closed 1 year ago

xakrurychle commented 1 year ago

fcli -V fcli version 0.20230629.082654-dev_develop, built on 2023-06-29 08:27:42

Wrong exemplary command from https://fortify.github.io/fcli/dev_2.0.0-beta/#_fcli_variables

fcli state variable contents myVersions -o 'expr={id}\n' --output-to-file myVersionIds.txt This \n needs to have space, otherwise it fails with error below

The space before \n leaves trailing white space which is a potential breaking point in automation scenarios.

java.lang.StringIndexOutOfBoundsException: begin 1, end 0, length 1 at java.base@17.0.7/java.lang.String.checkBoundsBeginEnd(String.java:4602) at java.base@17.0.7/java.lang.String.substring(String.java:2705) at org.springframework.expression.spel.ast.StringLiteral.(StringLiteral.java:44) at com.fortify.cli.common.spring.expression.AbstractSpelNodeVisitor.visit(AbstractSpelNodeVisitor.java:30) at com.fortify.cli.common.output.writer.record.expr.ExprRecordWriter$OutputExpressionValidator.visit(ExprRecordWriter.java:93) at java.base@17.0.7/java.util.Spliterators$ArraySpliterator.forEachRemaining(Spliterators.java:992) at java.base@17.0.7/java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:762) at com.fortify.cli.common.output.writer.record.expr.ExprRecordWriter$OutputExpressionValidator.visit(ExprRecordWriter.java:91) at com.fortify.cli.common.spring.expression.AbstractSpelNodeVisitor.visit(AbstractSpelNodeVisitor.java:21) at com.fortify.cli.common.output.writer.record.expr.ExprRecordWriter.(ExprRecordWriter.java:50) at com.fortify.cli.common.output.writer.record.expr.ExprRecordWriterFactory.createRecordWriter(ExprRecordWriterFactory.java:34) at com.fortify.cli.common.output.writer.output.standard.StandardOutputWriter$OutputRecordWriter.(StandardOutputWriter.java:354) at com.fortify.cli.common.output.writer.output.standard.StandardOutputWriter$OutputAndVariableRecordWriter.(StandardOutputWriter.java:244) at com.fortify.cli.common.output.writer.output.standard.StandardOutputWriter.write(StandardOutputWriter.java:66) at com.fortify.cli.common.output.cli.mixin.AbstractOutputHelperMixin.write(AbstractOutputHelperMixin.java:68) at com.fortify.cli.common.output.cli.cmd.AbstractOutputCommand.run(AbstractOutputCommand.java:45) at picocli.CommandLine.executeUserObject(CommandLine.java:2104) at picocli.CommandLine$RunLast.executeUserObjectOfLastSubcommandWithSameParent(CommandLine.java:2539) at picocli.CommandLine$RunLast.handle(CommandLine.java:2531) at picocli.CommandLine$RunLast.handle(CommandLine.java:2493) at picocli.CommandLine$AbstractParseResultHandler.execute(CommandLine.java:2351) at picocli.CommandLine$RunLast.execute(CommandLine.java:2495) at picocli.CommandLine.execute(CommandLine.java:2248) at com.fortify.cli.app.FortifyCLI.execute(FortifyCLI.java:86) at com.fortify.cli.app.FortifyCLI.main(FortifyCLI.java:68)

I've encoutered other situations, where the success of the command is dependant on whether \n is spaced or not. Can this potentially be unified?

rsenden commented 1 year ago

@xakrurychle Thanks for reporting. I've confirmed this issue on both 2.0.0-beta and develop. This looks like a bug in the Spring Expression Language interpreter, so we'll need to check whether a patch is available. This exception actually occurs on any single-character string literal (with \n being interpreted as single new-line character).

For example, the following commands all result in the same exception:

fcli ssc appversion list -o 'expr=.{id}'
fcli ssc appversion list -o 'expr={id}.'
fcli ssc appversion list -o 'expr={id}.{name} \n'

Whereas the following commands work just fine:

fcli ssc appversion list -o 'expr=..{id}'
fcli ssc appversion list -o 'expr={id}..'
fcli ssc appversion list -o 'expr={id}..{name} \n'

The exception occurs on the following line in org.springframework.expression.spel.ast.StringLiteral: image

Here, value contains each individual string literal, like . or .. from the commands above, failing if value contains only a single character.

rsenden commented 1 year ago

After having a closer look, this exception is caused by our code that validates these expressions. During validation, we construct a new StringLiteral instance in AbstractSpelNodeVisitor::visit(Expression) without enclosing the value in quotes, whereas StringLiteral does expect surrounding quotes.