spring-boot icon indicating copy to clipboard operation
spring-boot copied to clipboard

Enable ANSI output on Windows automatically

Open ViliusS opened this issue 2 years ago • 5 comments

Windows supports ANSI encoding since Windows 10 version 1909. All you need to do is call ENABLE_VIRTUAL_TERMINAL_PROCESSING when calling console API.

IntelliJ does this automatically. image All software running via the new Windows Terminal, including Java, does this as well. image

Old Windows command prompt doesn't do this by default for compatibility reasons, but new Java versions will make it possible for workaround even for older Windows versions https://stackoverflow.com/questions/74319252/printing-ansi-color-codes-in-java-works-on-vs-code-terminal-but-not-in-cmd

My proposal is to enable ANSI coloring on Windows by default.

Patch should be compatible with both 3.x and 2.7.x branches.

ViliusS avatar Apr 02 '23 17:04 ViliusS

Old Windows command prompt doesn't do this by default for compatibility reasons, but new Java versions will make it possible for workaround even for older Windows versions

Thanks for the PR. Just so that I confirm I understood it, this PR would then break those clients, right? (by returning true instead of checking the windows flag). If so, I don't think we should merge this. Is there a way to check that ENABLE_VIRTUAL_TERMINAL_PROCESSING was set from the Java process?

snicoll avatar Apr 03 '23 14:04 snicoll

It won't break, it will just show ANSI symbols in their raw form.

Sadly there is no easy way to check or set Windows API flags in Java process. At least not without using JNI, JNA or similar boilerplate alternative. As mentioned, JDK 19 preview has SymbolLookup.libraryLookup() implemented which would allow this directly, however even then Java needs to load kernel32.dll library to access Windows API, which is maybe a bit too much just for colors :)

I do not believe stripping Windows IntelliJ or Terminal users from automatic ANSI coloring for those running Spring Boot via old cmd is a great compromise. If compatibility is such a big issue here, I think applying this to 3.x and mentioning in the Release notes would be enough. Anyone running old console can just disable it via spring.output.ansi.enabled=never

ViliusS avatar Apr 03 '23 16:04 ViliusS

It won't break, it will just show ANSI symbols in their raw form.

That's what I meant by breaking. Going through a readable log (without colors) to this is certainly a behavioral breaking change.

If compatibility is such a big issue here, I think applying this to 3.x and mentioning in the Release notes would be enough. Anyone running old console can just disable it via spring.output.ansi.enabled=never

Compatibility is important. One can argue that those who can benefit from the improved support could set that exact same property, isn't it?

snicoll avatar Apr 04 '23 11:04 snicoll

I agree. It's probably a matter of what user base is in majority: IntellJ/Eclipse/Windows Terminal users vs Windows cmd users. And not a question of if but when to break compatibility, else innovation stops completely.

In this day and age, I think breaking compatibility in 3.1.x is reasonable.

ViliusS avatar Apr 04 '23 12:04 ViliusS

IMO, it's too late to make this change in 3.1.x as we don't have enough time to get feedback from the community. I think we should merge it early in 3.2 instead.

wilkinsona avatar May 02 '23 11:05 wilkinsona

I'm not sure that we should merge this one or not. I think it might be quite annoying for those that still use cmd.exe. Perhaps we can take another look at https://github.com/fusesource/jansi which has a Kernel32 class implemented using JNI.

philwebb avatar Jun 02 '23 04:06 philwebb

I have actually looked at jansi code before, but I could not come up with a working solution. My knowledge of Java is limited :|

If someone could come up with different solution that would be great, however in my opinion loading Kernel32.dll just for this reason is a little bit of waste of resources.

ViliusS avatar Jun 02 '23 05:06 ViliusS

Thanks for the suggestion but we have decided that we do not want to merge this change as we feel that the risk of breaking existing users is too high. Those using a shell that supports ansi colouring can add SPRING_OUTPUT_ANSI_ENABLED=always to their environment. Thanks anyway for the PR.

wilkinsona avatar Jun 21 '23 15:06 wilkinsona