Type safety using IntDef - java

I am trying to replace some of the enumerations in my source with IntDef annotation. I have been following this documentation.
I have a variable for holding a ViewMode which was previously an enumeration. Now I have changed it to some thing like below.
#Retention(RetentionPolicy.SOURCE)
#IntDef({ViewMode.VIEW_MODE_LIST_VIEW, ViewMode.VIEW_MODE_CARD_VIEW})
public #interface ViewMode {
int VIEW_MODE_LIST_VIEW = 0;
int VIEW_MODE_CARD_VIEW = 1;
}
#ViewMode
public int currentViewMode = ViewMode.VIEW_MODE_LIST_VIEW;
Now to test whether this is safe or not I have done the following in a method
this.currentViewMode = 987; //currentViewMode should be 0 or 1. Nothing else.
But this is now not giving me a compilation error. Am I missing something here?

You will not get a compilation error, because the enumerated annotations are just lint checks: see Improve Your Code with Lint
You should see the error-marker directly in Android Studio or when you run android lint checks from the command line: see Improve Your Code with Lint
Note: you can also configure your build to automatically run the lint checks:
see SO: Run lint when building android studio projects
But running the linter takes some time, so you may choose to run it only for your release builds or only on your CI server.

Related

New value added to Java Enum not available during debug

I am having the following problem:
I have an Enum that was originally declared with 5 elements.
public enum GraphFormat {
DOT,
GML,
PUML,
JSON,
NEO4J,
TEXT {
#Override
public String getFileExtension() {
return ".txt";
}
};
Now I need to add an additional element to it (NEO4J). When I run my code or try to debug it I am getting an exception because the value can't be found in the enum.
I am using IntelliJ as my IDE, and have cleaned the cache, force a rebuild, etc.. and nothing happens. When I look at the .class file created on my target folder, it also has the new element.
Any ideas on what could be causing this issue ?
I found my problem and want to share here what was causing it. My code was actually for a Maven plug-in which I was pointing to another project of mine to run it as a goal. However the pom.xml of my target test project was pointing to the original version of the plug-in instead of the one I am working on, and that version of course is outdated and does not include the new value. Thank you.

Eclipse flags (working) code as compilation error and will not run

I have some fairly complex code that uses Javaslang. If I compile it into a jar, it runs fine. However, when I try to step into it in Eclipse for debugging, Eclipse flags it as a compilation error and dies when it reaches that line. The particularly weird part is that this worked a week ago, and the code has not changed in the interim.
Things I have tried:
clean project (including unchecking 'build automatically')
delete project from Eclipse, delete .project and .settings, re-import
from scratch
delete project from Eclipse, delete .project, .classpath, .settings, do mvn eclipse:eclipse, reimport
Maven builds this without errors [both within Eclipse and from the command line]. I can run the project this depends on and have it access this code from the JAR, so I know it works. I just cannot have Eclipse access the code from the project, either in 'run' or 'debug' mode.
Seq<Tuple2<StateProbabilityVector, ScenData>> resultStateProbs =
futures.
flatMap(Future::get).
toList();
// Update the target counts.
// THIS ENTIRE STATEMENT IS THE ERROR
Seq<Tuple2<ScenState, Probability>> result =
resultStateProbs.flatMap(tuple -> tuple.apply((spv, baTargetCount) ->
{
return spv.getStateProbList().
peek(sp -> logger.debug("Checking if {} > {}: {}",
sp.getProbability(),
intermediateMinProb,
sp.getProbability().greaterThan(intermediateMinProb))).
filter(sp -> sp.getProbability().greaterThan(intermediateMinProb)).
map(sp -> updateScenarioData(sp, baTargetCount, dupStateInfo));
}));
// signature for updateScenarioData
protected abstract Tuple2<ScenState, Probability> updateScenarioData(StateProbability stateProb,
ScenData scenData,
DSI dupStateInfo);
// truncated def of StateProbabilityVector
#Getter #ToString #Builder
public class StateProbabilityVector {
#NonNull
private final Seq<StateProbability> stateProbList;
}
So the types are all correct, but Eclipse claims:
> Type mismatch: cannot convert from Object to Iterable<? extends
> Object>
> Type mismatch: cannot convert from Seq<Object> to
> Seq<Tuple2<ScenState,Probability>>
As NĂ¡ndor comments, this is probably down to a difference between the Eclipse compiler and javac, and the problem can probably be solved with a type witness in the right place. To find the right place, I would start by breaking up the functional method chain and extracting some local variables:
Seq<Tuple2<ScenState, Probability>> result =
resultStateProbs.flatMap(tuple -> {
Seq<Tuple2<ScenState, Probability>> filteredAndUpdated =
tuple.apply((spv, baTargetCount) -> {
Seq<StateProbability> stateProbList = spv.getStateProbList();
stateProbList.peek(sp -> {
logger.debug("Checking if {} > {}: {}", sp.getProbability(), intermediateMinProb, sp.getProbability().greaterThan(intermediateMinProb));
});
Seq<StateProbability> filtered = stateProbList.filter(sp ->
sp.getProbability().greaterThan(intermediateMinProb));
Seq<Tuple2<ScenState, Probability>> updated = filtered.map(sp ->
updateScenarioData(sp, baTargetCount, dupStateInfo));
return updated;
});
return filteredAndUpdated;
});
If you use Eclipse's extract variable refactoring, that by itself may tell you where it's inferring the wrong types, and explicitly declaring the correct types of the local variables might be enough to fix the problem all by itself.
If not, it should at least narrow the error down, and show you exactly where in the call chain Eclipse is having trouble. You can then probably fix it with type witnesses or, if all else fails, explicit casts, and then (with that type information added) perhaps inline the variables again, although this code is dense enough that I might leave them in.
Side notes:
peek() will only only debug the first StateProbability -- is that your intent?
consider adding a greaterThan() method to StateProbability so you don't have to repeatedly call getProbability().greaterThan(). (If the answer to #1 is "no", this method would also be a good place to put the debug statement.)
consider adding a method on SceneState that would return a prefiltered list, like Seq<StateProbability> SceneState.allGreaterThan(Probability).

JavaFX: Getting Stage of running Applications

For testing a application with TestFX i need to get the actual primary stage of a running application. This means that i haven't the code, i can just run the application through a jar.
Is there any possible solution for this? Scenic View does this already, but i was not able to reproduce this functionallity, especially because it seems that they use the deprecated funtion
Windows.impl_getWindows
which is not working in my case.
Try this:
import com.sun.javafx.robot.impl.FXRobotHelper;
static Collection<Stage> getAllJavaFXStages() {
try {
return FXRobotHelper.getStages();
} catch ( NullPointerException npe ) {
// nasty NPE if no stages exist
return Collections.emptyList();
}
}
```
Based on my own testing framework code: Automaton.
EDIT:
If you want to get a Stage from a different JVM instance than where you're running your code, then there's no simple way.
You're right, ScenicView does it, but it uses tools.jar to do it. This is not a standard jar you get in your runtime, so you must add it manually (placing it in jre/lib/ext should do it, you'll normally find it in lib only).
I tracked down the code where ScenicView seems to be doing it in their BitBucket repo.
Check the function getRunningJavaFXApplications for example.
Have fun using that in your tests!

Error debugging CGLIB FastClass on eclipse

I'm trying to debug an java eclipse project with some problem!
I'm starting using CGLIB to make faster reflection calls using the index metod.
example
FastClass fastClass = FastClass.create(getClass());
int index = fastClass.getIndex("methodName", new Class[] { Object.class });
fastClass.invoke(index, this, new Object[] { obj } );
now when i try to put a breakpoint into a class that is called by fastreflection method this is the eclipse output.
I try to change compiler option on generate line number with no results.
I also upload an eclipse project (built with Juno version) that replicates the problem!!
http://www.filefactory.com/file/4zryz3gjgbyh/n/FastDebug.rar
Thanks!
I "resolved"(understand) the problem, but it is not a problem with Eclipse. When you launch
the program this line: FastClass.create(ReflectionTarget.class); ends up
creating an entirely new version of the compiled class removing all
non-essential stuff from the classfile to make it "fast" - that includes all
the line number / debug infos, which means the breakpoint cannot be set in it.
http://cglib.sourceforge.net/xref/net/sf/cglib/core/package-summary.html
There's no javadoc and you need to read the source but now i understand this is not a
problem but a feature of this method to make fast reflection!

Sonar Java Web Client: Authors by line null

When running the following code on my Sonar, measure returns null. (Should return something on the lines of "1=author;2=author..."). However it works on nemo.sonarsource.org.
Other measures eg: violation work correctly on mine so this is probably not a question of faulty code. I suspect I need to configure Sonar somehow?
private final Sonar sonar;
public String getAuthors(String resourceKey){
return getMeasure(resourceKey, "authors_by_line").getData();
}
private Measure getMeasure(String resourceKey, String measureName){
Resource resource = sonar.find(ResourceQuery.createForMetrics(
resourceKey, measureName));
Measure measure = resource.getMeasure(measureName);
return measure;
}
You must have installed the SCM Activity plugin and enabled it (in Sonar settings, see the documentation on our Wiki) in order to be able to get this metric.
Then, once you have reanalysed your project, you'll get the expected behaviour.

Categories