Intellij doesnt break line in spring controller - java

When I press CTRL + ALT + L then every line gets breaked, except of a Controller line with annotations.
I set it up to wrap at 200 and it does so, just not on this as example:
I tried to set up the Code Style -> Java -> Wrapping and Braces.

As written in Oracle's Java tutorial
Annotations, a form of metadata, provide data about a program that is
not part of the program itself. Annotations have no direct effect on
the operation of the code they annotate.
Annotations have a number of uses, among them:
Information for the compiler — Annotations can be used by the
compiler to detect errors or suppress warnings.
Compile-time and
deployment-time processing — Software tools can process annotation
information to generate code, XML files, and so forth.
Runtime processing — Some annotations are available to be examined at
runtime.
They're not really directly executable and therefore not debuggable; for example what would you expect when putting a break point on #Override annotation?

Related

Is Java annotation processor capable of removing annotated code

As we all know, we can automagicaly generate code using custom annotations and Java annotation processors as guys at project Lombook do. But can we remove the annotated code from compiled sources ?
I've tried searching the web for it, but only things that appear are "generate your code" topics and tutorials on "how to generate server with one annotation".
It came to my mind while I was searching for ways to "compile out" debug messages from prod app. I can understand, that having the debug/test and production code is not a good practice, but sometimes it is needed to keep things simple. I think of few scenarios for this:
make debug only, laggy code used in developer-only version of code that can have different levels of importance for example:
#Debug(0) void cpuLightFunction(){}
#Debug(100) void cpuHeavyFunction(){}
void doWork(){
cpuLightFunction();
cpuHeavyFunction();
}
In annotation processing step we could use some option to define max level of #Debug annotations that would be compiled. Any usage of #Debug with higher level would produce error or warning in the same way as #Deprecated
platform specyfic code versions - create custom #Platform(ANDROID) void doSomething() and #Plaform(IOS) void doSomething functions that run only on given plaform to get rid of polymorphic void doSomething(AndroidPlatform) or void doSomethingAndroid() code
have parts of code that are conditionally compiled:
#Optional("NetworkStub")
class NetworkStub{
// ...
}
#Optional("PaymentStub")
class PaymentStub{
// ...
}
and only use compiler/annotation processor options to enable/disable parts of the code, for example -Aoptional="NetworkStub" that would only compile code related to NetworkStub in the code and remove all code touching PaymentStub.
You can do this by writing an annotation processor that traverses and modifies the program's AST (abstract syntax tree) during compilation, before code generation.
That is how Project Lombok works.
This question is a near-duplicate of How to write a Java annotation processor?, but the accepted answer to that question says it's impossible, which is factually wrong.

Annotation Processing Compilation Steps

I read in this article(https://www.javacodegeeks.com/2015/01/how-to-process-java-annotations.html) that Annotation Processing has multiple rounds:
Annotation processing happens in separate stages, called rounds. During each round, a processor gets a chance to process the annotations it is interested in.
The annotations to process and the elements they are present on are available via the RoundEnvironment parameter passed into the process() method.
If annotation processors generate new source or class files during a round, then the compiler will make those available for processing in the next round. This continues until no more new files are generated.
The last round contains no input, and is thus a good opportunity to release any resources the processor may have acquired.
Can someone explain to my what it means by rounds? So for example let's say we have an annotation Metrics.java, when the compiler is parsing through the java source code it will first find all the elements that use this annotation and then at the end of compilation run the annotation process for that specific Metrics annotation where the RoundEnvironment passed in will contain all the elements that have the Metrics annotation?
Or anytime the compiler sees a annotation it will immediately run the annotation if it has a retention type of Class or Source. Otherwise it will not run the annotation for that annotation until runtime since it has a retention type of Runtime?
as far as i understand, while parsing a java file compiler gathers all annotations seen in it then goes for processing them using an annotation processor that we already prepared(first round).suppose annotation processor creates a new source file(.java) and has used annotation in it,here compiler goes for parsing that file and gathering its annotations then goes for processing them using annotation processors(second round).and this continue until in last java file(which created via annotation processor or not) we have no annotation in it.
and annotation processing is a part of javac that we should ask for enabling it(that we have some ways depend on environment like maven, command line, IDEs, and so on).
annotation processing doesn't run immediately by meeting first annotation in the source file and Retention policy isn't matter too.

Is it possible to detect which deprecated classes are actively used?

I have a relatively complex java project, with many classes that are probably not used.
Static analysis of the code base is relevant for some of the classes, but some are loaded dynamically (network services, persisted data, etc.)
Is there a method to get a list of deprecated classes that were actively used in the jvm, so I can know if those classes are used?
[I know there may be "sleeper classes" that are used only rarely, but that's a risk I can take]
The JVM may have an option to print information about all used classes. For example:
java -verbose:class ...
You still would have to filter out the deprecated ones by some other means.
You can try to compile with -deprecation (or -Xlint:deprecation) to see the uses of deprecated APIs if you have to sourcecode (I guess you have it)
I could think of the following :
Add static initializer to each of your classes in the form
static {
// here you can get creative :
// either do some writing to a file with each class printing its name
// or do System.err outputing the class name, then later fetching the entire output.
}
If you are too lazy to manually add the piece of code you could write simple program to append this initializer to all files ending with .java.
This is simple way of getting a list of all the classes that are being used ( I think).
Best of luck!
There are tools like UCDetector which I've used in the past. But that requires manual assessments which can be painful for large projects. You can do text analysis like below:
Listing active usage deprecated methods
For static code analysis, list down deprecated methods of which source is already available using an IDE.
In Eclipse, goto Window -> Preferences -> Java -> Compiler -> Errors/Warnings -> Deprecated and restricted API : Set level to WARNING and check the items besides.
In Problems view, click the down button near the tab -> Group By -> Java Problem Type
You will be able to see Deprecation usage list grouped together, copy the contents as text, which you can use to further prepare scripts/excel for analysis
Use a simple text editor to find and replace "from the type " and " is deprecated" with tab characters
Copy the contents to a spreadsheet. You will have a list of classes which contain deprecated methods but have active usage.
Listing inactive usage deprecated methods
List down the class and method names by using similar approach above (For method name replace the text "The method " and " from the type " with tab characters).
This list minus the previous list is the inactive methods list.
Listing dynamic deprecated methods
For dynamic code using reflections etc, there is no single bullet approach. You can do filtering of basic stuff using the method names.
List down the method names by using similar approach above (Replace the text "The method " and " from the type " with tab characters).
For the unique set of method names, loop to use a grep script. This type of search can be slow even for small projects. But just in case you 'ld want to invest the time.
Remove them all and try to run your application. Every time you get a ClassNotFoundException for one of them, write it down and add the class back. Rinse and repeat.

Using an Annotation Processor to create a list of classes with a certain annotation

I have a custom annotation that I've implemented and I'd like to use an annotation processor to generate a list of all the classes in my app that use that particular annotation.
I've found this tutorial which describes how to generate a class file using an annotation processor, so it should be quite easy to generate a class for each class with my annotation.
What I can't figure out is how I can collect all of that information into a single class. There doesn't seem to be a way to modify a class, so I can't append new items to the list once the class has been generated the first time.
Is there a way to use an annotation processor to generate a method that will return the list of all classes in an app that are annotated with a particular annotation?
Generated classes do not necessarily have to correspond one-to-one to the input classes being processed. Plus, you can search for classes (Elements) that are annotated with a given annotation via the RoundEnvironment:
roundEnvironment.getElementsAnnotatedWith(MyAnnotation.class)
From this you can generate a single class with a method that returns a collection of the classes found.
A couple issues around this to highlight:
Annotation processors can run along with other annotation processors and thus have to deal with classes generated at compile time. To aid this, Java annotation processing is performed in rounds to allow processors to catch the outputs of others. To be compatible with other processors you need to gracefully handle the ErrorType.
Only classes in the current compilation pass are returned from the RoundEnvironmnet methods so classes in external libraries will not be included.
IDEs (cough cough Eclipse) implement the annotation processing facilities of Java differently which can be a problem for processors that require a full non-partial compilation like I've described.
Coincidentally, I created a similar project recently that does what you are looking for:
https://github.com/johncarl81/silver
Silver is very much a WIP and uses a lot of library code to accomplish the task, but it may give you an idea for what's possible.

Explanation about Annotations

Can anyone please explain what the following two paragraphs mean, in simple english? (Taken from http://www.ibm.com/developerworks/java/library/j-cwt08025.html)
"Annotations are more flexible in
terms of how you use them, with
options for whether the annotation
information is to be included in class
files output by the compiler and made
available to the application at run
time"
Not sure what these means. Can Annotations be configured to optionally change the bytecode?
While annotations are ideal for
metadata that relates to a particular
component, they are not well suited to
metadata with cross-component
application.
IMHO most web applications would be cross-component ones. What is the author trying to say here?
Annotations are more flexible in terms
of how you use them, with options for
whether the annotation information is
to be included in class files output
by the compiler and made available to
the application at run time
This, I think, refers to the fact that Java5 annotations can be dropped by the compiler, whereas some can be retained in the bytecode. This is controlled by the #Retention annotation that is placed on your annotation type, e.g
#Documented
#Retention(value=RUNTIME)
public #interface Deprecated
This indicates that the #Deprecated annotation will be present in the bytecode, and will also be visible to reflection. java.lang.annotation.RetentionPolicy defines the different options.
"Annotations are more flexible in terms of how you use them, with options for whether the annotation information is to be included in class files output by the compiler and made available to the application at run time"
It is more flexible than XDoclet because:
it can be used from the source code (like XDoclet)
it can be used at runtime, when you only have the byte-code and not the source code (unlike XDoclet)
While annotations are ideal for metadata that relates to a particular component, they are not well suited to metadata with cross-component application.
Annotations (like XDoclet) have one interesting feature, as opposed to an external Xml for example :
Annotations live in the code, so it is natural for them to be applied to the code they are defined on. You don't have to specify (using some complex syntax) to what piece of code they apply. Examples:
if an annotation is defined on a method, it applies naturally to that method
if an annotation is defined on a field, it applies naturally to that field
if an annotation is defined on a class, it applies naturally to that class
if an annotation is defined on a package, it applies naturally to that package
If you want to have the same in an external Xml file, you have to use a complex syntax to identify the piece of code you refer to. So that makes them very easy to apply.
Also, in case of a code refactoring (like renaming), annotations continue to work just fine, while an external xml would have to be changed to point to the new class or method name.
I don't believe that in a web application, most things are cross-component.
If you defined Persistance (to a database) of an Entity, like what is the table where this class should be persisted, it is not something global to all Entities, it only affects the current Entity.
same for many other examples...

Categories